-
-
Save moritzuehling/790e64ab14de0579c302a2d489233e1e to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
; Invariant: LockBuffer has been called on the currently targeted buffer. | |
Function AACircle(x#, y#, radius#, r, g, b) | |
; Which area do I need to scan? | |
Local minX = Floor(x - radius#), maxX = Ceil(x + radius#) | |
Local minY = Floor(y - radius#), maxY = Ceil(y + radius#) | |
; The distance between the circles (on the x / y axis, and total) | |
Local dx#, dy#, distance# | |
; How many pixels do their radii overlap? | |
Local overlap#, invOverlap# | |
; To calculate the overlap | |
Local radiDistance# = .5 + radius# | |
Local tr, tg, tb | |
Local oldColor, oldR, oldB, oldG | |
; We pre-calculate this to save it later. | |
Local defaultColor = (r Shl 16) + (g Shl 8) + (b) | |
; This is used in distance calclulations to correctly align the compared pixel | |
Local mx# = x# - .5, my# = y# - .5 | |
; What is the big idea? | |
; We decide for each pixel if it's inside or outside the circle | |
; or on the border. | |
; To do this we imagine each pixel is a small cirlce of the radius .5 | |
; which is an okay-ish approximation. | |
; Then we calculate by how much they would overlap | |
; and use that to approximate the color | |
; it's an okay-ish measure, nothing fancy - but it works and | |
; looks good, without doing fancy math. | |
For px = minX To maxX | |
; In theory I could do some fancy math with sin / cos here to skip some pixels, but meh | |
; I think the one sqrt per pixel is faster than the two trigonometric functions per row | |
; for the small circles I draw. If you draw a big circle this changes, and you totally | |
; should fix this. | |
For py = minY To maxY | |
dx# = (px - mx#) | |
dy# = (py - my#) | |
distance# = Sqr(dx# * dx# + dy# * dy#) | |
overlap# = -(distance# - radiDistance#) | |
If (overlap > 0) Then | |
If (overlap >= 1) Then | |
WritePixelFast px, py, defaultColor | |
Else | |
oldColor = ReadPixelFast(px, py) | |
If (oldColor <> defaultColor) Then | |
oldB = oldColor And 255 | |
oldG = (oldColor Shr 8) And 255 | |
oldR = (oldColor Shr 16) And 255 | |
invOverlap# = 1 - overlap | |
tr = r * overlap + oldR * invOverlap | |
tg = g * overlap + oldG * invOverlap | |
tb = b * overlap + oldB * invOverlap | |
End If | |
WritePixelFast px, py, (tr Shl 16) + (tg Shl 8) + (tb) | |
End If | |
End If | |
Next | |
Next | |
End Function |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment