Created
February 25, 2025 14:44
-
-
Save Willem3141/f12aad032efeb09eca0da64fe7e98e26 to your computer and use it in GitHub Desktop.
Ipelet that applies point-line duality
This file contains hidden or 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
label = "Duality" | |
about = [[ | |
Applies point-line duality to line segments and marks. | |
]] | |
function dualize(model,num) | |
local t = { label = label, | |
pno = model.pno, | |
vno = model.vno, | |
original = model:page():clone(), | |
undo = _G.revertOriginal | |
} | |
-- scale factor for the slope value of lines | |
-- in other words, if I put a mark at x-coordinate 1, | |
-- then it'll get dualized to a line with slope slopeScale | |
local slopeScale = 1.0 / 32 | |
t.redo = function (t, doc) | |
-- get the current page | |
local p = doc[t.pno] | |
layer = p:addLayer(nil) | |
p:setActive(1, layer) | |
p:setVisible(1, layer, true) | |
-- make sure to iterate over the copy | |
for i,obj,sel,layer in t.original:objects() do | |
if sel and obj:type() == "path" then | |
shape = obj:shape() | |
if #shape == 1 then | |
curve = shape[1] | |
if curve.type == 'curve' and #curve == 1 then | |
segment = curve[1] | |
if segment.type == 'segment' then | |
startPoint = segment[1] | |
endPoint = segment[2] | |
dx = endPoint.x - startPoint.x | |
dy = endPoint.y - startPoint.y | |
if dx == 0 then | |
model:warning('Vertical line detected; ignoring it') | |
else | |
a = dy / dx | |
b = startPoint.y - a * startPoint.x | |
-- create a mark at (a, -b) | |
mark = ipe.Reference(model.attributes, 'mark/disk(sx)', ipe.Vector(a / slopeScale, -b)) | |
p:insert(nil, mark, 0, layer) | |
end | |
end | |
end | |
end | |
end | |
if sel and obj:type() == "reference" then | |
local a = slopeScale * obj:position().x | |
local b = -obj:position().y | |
-- create a line | |
local startPoint = ipe.Vector(-250, a * -250 + b) | |
local endPoint = ipe.Vector(250, a * 250 + b) | |
local segment = { type = 'curve', closed = false } | |
segment[1] = { type = 'segment', startPoint, endPoint } | |
mark = ipe.Path(model.attributes, {segment}) | |
p:insert(nil, mark, 0, layer) | |
end | |
end | |
end | |
model:register(t) | |
end | |
---------------------------------------------------------------------- | |
methods = { | |
{ label = "Dualize", run=dualize } | |
} | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment