Skip to content

Instantly share code, notes, and snippets.

@Fraktality
Created July 8, 2019 21:36
Show Gist options
  • Save Fraktality/4abc46547838fd0f15d641ad1466765f to your computer and use it in GitHub Desktop.
Save Fraktality/4abc46547838fd0f15d641ad1466765f to your computer and use it in GitHub Desktop.
-- Various ways of testing a screen point against a GuiBase2d
-- Note: Rounded rect corner radius is inferred from SliceCenter.Min.X
local cos = math.cos
local min = math.min
local rad = math.rad
local sin = math.sin
return {
-- Axis-aligned rectangle
aaRect = function(gui, x, y)
x, y = x + 0.5, y + 0.5
local position = gui.AbsolutePosition
local p0x, p0y = position.x, position.y
if x >= p0x and y >= p0y then
local s = gui.AbsoluteSize
return x < p0x + s.x and y < p0y + s.y
end
return false
end,
-- Rectangle, accounting for rotation
rect = function(gui, x, y)
x, y = x + 0.5, y + 0.5
local position = gui.AbsolutePosition
local size = gui.AbsoluteSize
local p0x, p0y = position.x, position.y
local sx, sy = size.x*0.5, size.y*0.5
local cx, cy = p0x + sx, p0y + sy
if (x - cx)*(x - cx) + (y - cy)*(y - cy) > sx*sx + sy*sy then
return false
end
local rotationDeg = gui.AbsoluteRotation
if rotationDeg%180 ~= 0 then
if rotationDeg%90 ~= 0 then
local rotationRad = rad(rotationDeg)
local c = cos(rotationRad)
local s = sin(rotationRad)
x, y =
cx + c*(x - cx) + s*(y - cy),
cy - s*(x - cx) + c*(y - cy)
else
x, y =
cx - cy + y,
cx + cy - x
end
end
return x >= p0x and y >= p0y and x < cx + sx and y < cy + sy
end,
-- Axis-aligned rounded rectangle
aaRoundedRect = function(gui, x, y)
x, y = x + 0.5, y + 0.5
local position = gui.AbsolutePosition
local p0x, p0y = position.x, position.y
if x >= p0x and y >= p0y then
local size = gui.AbsoluteSize
local sx, sy = size.x, size.y
local p1x = p0x + sx
local p1y = p0y + sy
if x < p1x and y < p1y then
loca l r = min(gui.SliceCenter.Min.x, sx*0.5, sy*0.5)
if (x >= p0x + r and x + r < p1x) or (y >= p0y + r and y + r < p1y) then
return true
end
local cx = x - (x > p0x + sx*0.5 and p1x - r or p0x + r)
local cy = y - (y > p0y + sy*0.5 and p1y - r or p0y + r)
return cx*cx + cy*cy < r*r
end
end
return false
end,
-- Rounded rectangle, accounting for rotation
roundedRect = function(gui, x, y)
x, y = x + 0.5, y + 0.5
local position = gui.AbsolutePosition
local size = gui.AbsoluteSize
local p0x, p0y = position.x, position.y
local sx, sy = size.x*0.5, size.y*0.5
local cx, cy = p0x + sx, p0y + sy
if (x - cx)*(x - cx) + (y - cy)*(y - cy) > sx*sx + sy*sy then
return false
end
local rotationDeg = gui.AbsoluteRotation
if rotationDeg%180 ~= 0 then
if rotationDeg%90 ~= 0 then
local rotationRad = rad(rotationDeg)
local c = cos(rotationRad)
local s = sin(rotationRad)
x, y =
cx + c*(x - cx) + s*(y - cy),
cy - s*(x - cx) + c*(y - cy)
else
x, y =
cx - cy + y,
cx + cy - x
end
end
local p1x = cx + sx
local p1y = cy + sy
if x >= p0x and y >= p0y and x < p1x and y < p1y then
local r = min(gui.SliceCenter.Min.x, sx, sy)
if (x >= p0x + r and x + r < p1x) or (y >= p0y + r and y + r < p1y) then
return true
end
cx = x - (x > cx and p1x - r or p0x + r)
cy = y - (y > cy and p1y - r or p0y + r)
return cx*cx + cy*cy < r*r
end
return false
end,
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment