I have a small python project, which draws graphics and text onto a graphics context using MacOS's Core Graphics APIs. The idea is to make it easy for the user to write a few short lines, in order to add graphics to a page.
Currently, I'm committing the cardinal sin of a global variable for the graphics context, which each function then draws into. I realise that what I probably ought to do is to create some kind of object, and have the functions as object methods.
While I understand the principle of objects and methods, I'm not very good at conceptualising how they ought to work. Any help with the concept would be very welcome.
# Use inches instead of points e.g. "inch(1.5)"
# Use centimetres instead of points e.g. "cm(2.5)"
#  HERE IS WHERE YOU WRITE YOUR PAGE!
The ultimate goal is to turn this into a python library, so that a short script can import the library and then use a few lines to do some drawing.
How to make an object out of that ?
Sure we did it, but what's the point, we don't code Java here, we do Python. A class is as way to organise data, not functions.
# if you're a great programmer, you can make the following method properties.
Why is that useful ? Because you can add methods and data and it scales.
Here, color is an immutable.
You don't pollute globals with constants.
The example above can be used like this.
But the shape class is kind of dirty in the way it implicitly creates a canvas and redraws.
This is an interesting project. Is your goal to simplify the use of CoreGraphics from Python? What's the advantage of using your python module over just importing Quartz and using it directly? That's not intended as a criticism, but a serious question. The answer will inform how you design the interface for your library.
Also, why are you changing the constant name pi to PI?
Your naming is also inconsistent. You have makeRectangle() (which draws a rectangle rather than making one) and then just line() and circle(). These should all be something like fillRectangle(), strokeLine() and fillAndStrokeCircle(). Also, it would make sense to have the same forms for all shapes - fillRectangle(), strokeRectangle(), fillCircle(), strokeCircle(), etc.
Looking at the Quartz.framework headers, there is an object model immediately suggested to me. The main object in CoreGraphics is the CGContext. The header treats it as an opaque pointer, but we can assume for our purposes that it points to some sort of object behind-the-scenes. You could mimic that, offering a Context or DrawingContext class.
CoreGraphics also has several data types that it passes around, such as CGPoint, CGRect, and CGColor. These would make good classes, as well. And it turns out that python supports some operator overloading so you can make some useful methods like overloading + and - for easy use of points as vectors.
Now all of this might not be the right abstraction for your library. (Though it might be useful internally for it.) The right abstraction will depend on your goals. But most modern graphics APIs have a concept of some sort of context to draw into and a set of methods to do the drawing of various types of primitives (shapes, images, text, etc.). So it's a decent model to follow.
Not the answer you're looking for? Browse other questions tagged python graphics macos or ask your own question.