I'm working on some code involving use of the pygame library to draw a circle to a surface. The code to draw the circle looks something like the following:
surf = pygame.Surface((2000,2000))
pygame.draw.circle(surf,
pygame.Color("white"),
(1000,1000),
508,
50)
The problem is that the resulting circle has artifacts
Is there anyway to draw a circle like this without getting these artifacts?
What you see is most likely a problem with pygame.draw.circle implementation. Most likely pygame developer foolishly assumed that you can draw thick circle by drawing several circles in sequence, increasing radius by one for every circle. That's not going to work in practice and you'll get moire pattern like the one you see. Try increasing circle line thickness by 100 or 200 and see what happens. If it gets worse, then it is pygame.draw.circle
's fault.
A solution would be to provide your own circle rendering routine. This can be certainly be done, but for optimum performance it makes sense to do it in C/C++ extension module for pygame OR using OpenGL (with or without fragment shaders).
To get a perfect circle for every scanline you'll have to calculate start and end of filled area for every scanline. It might be possible to do this in python with tolerable performance by using pygame.draw.line to draw individual scanlines.
This bug is mentioned in the comments for the circle and arc methods. There's one workaround in the comments of the draw.circle documentation. This is adapted from that workaround:
def draw_outlined_circle(surf, color, origin, radius, thickness):
width = radius * 2 + thickness * 2
background = (0, 0, 0, 0)
circle = pygame.Surface((width, width)).convert_alpha()
rect = circle.get_rect()
circle.fill(background)
pygame.draw.circle(circle, color, rect.center, radius)
pygame.draw.circle(circle, background, rect.center, radius - thickness)
surf.blit(circle, (origin[0] - (rect.w / 2), origin[1] - (rect.w / 2)))
This method uses an extra Surface
and draws two circles: a smaller circle inside of a larger one to achieve the same effect. The smaller circle's fill color has an alpha of 0, so the full circle's center appears transparent.
EDIT: From the above comment, I see the behavior is mentioned in the pygame FAQ as well.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With