1

I am currently designing basic pygame projects. Random projects actually, which are just random ideas pop into my head during common daytime. One of them is a wall clock. Where I use sin, cos functions to draw hour hand, minute hand etc..

As a result of these functions, I obtain float values. Which pygame does not allow. So I round and int() all values before using them in drawing functions. This makes sense because of pixels can't be partially filled. However, I think this results in bad drawings.

pygame clock

The Image above is the clock drawn by the pygame module. As you see the handles are somewhat leaning. Not straight.

I also implemented this in codeskulptor. Which is a python2 environment for basic game(or any graphical) programming. Has nice and clear functions, very easy to use indeed. The float values I use in that no needs conversion and accepted directly. I do not know how it handles it, but it is clearly better. Obviously not just rounding and integering(does this word exist ?) values. Let me show you the clock drawn in codeskuptor:

codeskuptor clock

As you can see, the edges are more smooth. The lines does not end sloped, but straight. It is clearly a better drawing than the pygame one.

But the thing is, codeskuptor does not implement many modules and built-in functions that is harder than beginning level knowledge. Also it doesn't support a well-known compiler(basically not a python module). So can't work on computer and can not be compiled with py2exe, pyinstaller as such.

So I wan't to implement all this in pygame, and get smooth results just like in codeskulptor. Maybe a better way to handle float points for drawing. Any idea or knowledge in this area would be greatly appreciated.

My code for codeskuptor(Does not show realtime)

My code for pygame

The codes does not supply proper commenting because they were just a late-night fun nothing more. I'll explain any necessary parts.

Rockybilly
  • 2,938
  • 1
  • 13
  • 38
  • 1
    "integering" is accurately captured in the word "rounding" :) Have you tried the [`aaline`](http://www.pygame.org/docs/ref/draw.html#pygame.draw.aaline) function to draw antialiased lines? – user812786 Feb 09 '16 at 22:05
  • Well in that i meant round(3.4) gives you 3.0 then you need int() :) let me checkout aaline – Rockybilly Feb 09 '16 at 22:06
  • Drawing circles is also a bit off. Like when you draw a thick circle. There are empty dots on the drawing that makes it look bad. Maybe a thing with all pygame drawing. – Rockybilly Feb 09 '16 at 22:09
  • Judging by [the comments on draw_circle](http://www.pygame.org/docs/ref/draw.html#comment_pygame_draw_circle) this is a common issue with pygame and they don't have a built-in antialiasing for circles. The gfxdraw module does have an [`aacircle`](http://www.pygame.org/docs/ref/gfxdraw.html#pygame.gfxdraw.aacircle) method but it's marked as experimental.. – user812786 Feb 09 '16 at 22:11
  • I am guessing aaline does not let setting width(which is a huge downside). Codeskulptor drawing methods for browser is defined in javascript. Maybe pygame source code could benefit from those and implement for better results. – Rockybilly Feb 09 '16 at 22:15

1 Answers1

1

To summarize the comments above, the issue you've noticed here is antialiasing. For the lines, pygame provides the aaline function, which can be used to draw a single line. Unfortunately, this does not support a varying thickness. Potential workarounds could be drawing a line of the correct thickness and drawing an aaline on either side of it, or drawing the line using an aapolygon (from the gfxdraw module).

The standard draw module does not include antialiased circles, but you can use another function from gfxdraw to draw an antialiased circle, aacircle.

It is important to note that the gfxdraw module is labeled "experimental", so the functions are not guaranteed to persist across versions of pygame. But for your quick projects that might not be a concern.

As for CodeSkulptor, they are rendering the lines on an HTML5 <canvas> element, which according to this question has anti-aliasing turned on by default.

Community
  • 1
  • 1
user812786
  • 4,302
  • 5
  • 38
  • 50
  • Thanks for the answer. Though I was expecting a comprehensive answer that covers the fundamentals of drawing, its not your fault that pygame does not support sufficent functions. So I accept your answer. – Rockybilly Feb 09 '16 at 22:32
  • Not sure what you mean by fundamentals? I was focusing on the specific question you posed rather than computer graphics in general. Looking up "antialiasing" would be a good start there, possibly looking at pygame source if you want to learn more about how that specifically draws. Basically, you have to map functions to pixels, but you can't draw on half a pixel, so you end up with jagged edges, or "aliasing". Antialiasing tries to smooth this out by computing some in-between color for the edge pixels. – user812786 Feb 09 '16 at 22:46
  • I figured I might use aapolygon for my purpose. – Rockybilly Feb 10 '16 at 09:22