fixed issues in paperfold
This commit is contained in:
parent
9d6d01f845
commit
89b478fd47
@ -37,23 +37,27 @@
|
||||
<param name="fontSize" type="int" min="1" max="100" gui-text="Label font size (%)">15</param>
|
||||
<param name="flipLabels" type="bool" gui-text="Flip labels">false</param>
|
||||
<param name="dashes" type="bool" gui-text="Dashes for cut/coplanar lines">true</param>
|
||||
<param name="saturationsForAngles" type="bool" gui-text="Adjust color saturation for folding edges" gui-description="The larger the angle the darker the color">false</param>
|
||||
<param name="edgeStyle" type="optiongroup" appearance="combo" gui-text="Edge style">
|
||||
<option value="regular">regular</option>
|
||||
<option value="saturationsForAngles">saturations for angles</option>
|
||||
<option value="opacitiesForAngles">opacities for angles</option>
|
||||
</param>
|
||||
<param name="separateGluePairsByColor" type="bool" gui-text="Separate glue tab pairs by color" gui-description="Generates random color sets for glue tab pairs">false</param>
|
||||
<param name="colorValleyCut" type="color" appearance="colorbutton" gui-text="Valley cut edges">255</param>
|
||||
<param name="colorMountainCut" type="color" appearance="colorbutton" gui-text="Mountain cut edges">1968208895</param>
|
||||
<param name="colorCutEdges" type="color" appearance="colorbutton" gui-text="Cut edges">255</param>
|
||||
<param name="colorCoplanarEdges" type="color" appearance="colorbutton" gui-text="Coplanar edges">1943148287</param>
|
||||
<param name="colorValleyPerforates" type="color" appearance="colorbutton" gui-text="Valley perforation edges">3422552319</param>
|
||||
<param name="colorMountainPerforates" type="color" appearance="colorbutton" gui-text="Mountain perforation edges">879076607</param>
|
||||
<param name="colorValleyFolds" type="color" appearance="colorbutton" gui-text="Valley fold edges">3422552319</param>
|
||||
<param name="colorMountainFolds" type="color" appearance="colorbutton" gui-text="Mountain fold edges">879076607</param>
|
||||
</vbox>
|
||||
</hbox>
|
||||
</page>
|
||||
<page name="tab_postprocessing" gui-text="Post Processing">
|
||||
<label appearance="header">Joinery</label>
|
||||
<label>Joinery only works on ungrouped paths.</label>
|
||||
<label>Joinery is a tool to add interlockings, tabs and other connectors to your edges. It only works on ungrouped paths (flat structure).</label>
|
||||
<param name="joineryMode" type="bool" gui-text="Enable joinery mode" gui-description="Makes flat file instead creating groups. Guarantees compability for joinery.">false</param>
|
||||
<label appearance="url">https://clementzheng.github.io/joinery</label>
|
||||
<label appearance="url">https://www.instructables.com/Joinery-Joints-for-Laser-Cut-Assemblies</label>
|
||||
<label appearance="header">Origami Simulator</label>
|
||||
<label>Simulate your foldings in 3D! See Origami Simulator: "File" -> "Design Tips" -> "Importing SVG"</label>
|
||||
<label appearance="url">https://origamisimulator.org</label>
|
||||
<label appearance="url">https://github.com/amandaghassaei/OrigamiSimulator</label>
|
||||
<param name="origamiSimulatorMode" type="bool" gui-text="Enable origami simulator mode" gui-description="Overwrites styles to be compatible to origami simulator.">false</param>
|
||||
|
@ -37,17 +37,19 @@ Module licenses
|
||||
possible import file types -> https://www.graphics.rwth-aachen.de/media/openmesh_static/Documentations/OpenMesh-8.0-Documentation/a04096.html
|
||||
|
||||
todo:
|
||||
- debug coplanar color for edges for some cases
|
||||
- make angleRange global for complete unfolding (to match glue pairs between multiple unfoldings)
|
||||
- option to render all triangles in a detached way (overlapping lines/independent) + merge coplanar adjacent triangles to polygons
|
||||
- write tab and slot generator (like joinery/polyhedra extension)
|
||||
- fstl preview
|
||||
- origami simulator docu + add support for opacities
|
||||
- fix line: dualGraph.add_edge(face1.idx(), face2.idx(), idx=edge.idx(), weight=edgeweight) # #might fail without throwing any error ...
|
||||
- fix line: dualGraph.add_edge(face1.idx(), face2.idx(), idx=edge.idx(), weight=edgeweight) # #might fail without throwing any error (silent aborts) ...
|
||||
"""
|
||||
|
||||
class Unfold(inkex.EffectExtension):
|
||||
|
||||
angleRangeCalculated = False #set to true after first calculation iteration (needed globally)
|
||||
minAngle = 0
|
||||
minAngle = 0
|
||||
angleRange = 0
|
||||
|
||||
# Compute the third point of a triangle when two points and all edge lengths are given
|
||||
def getThirdPoint(self, v0, v1, l01, l12, l20):
|
||||
v2rotx = (l01 ** 2 + l20 ** 2 - l12 ** 2) / (2 * l01)
|
||||
@ -112,9 +114,9 @@ class Unfold(inkex.EffectExtension):
|
||||
|
||||
|
||||
# Functions for visualisation and output
|
||||
def addVisualisationData(self, mesh, unfoldedMesh, originalHalfedges, unfoldedHalfedges, glueNumber, foldingDirection):
|
||||
def addVisualisationData(self, mesh, unfoldedMesh, originalHalfedges, unfoldedHalfedges, glueNumber, dihedralAngles):
|
||||
for i in range(3):
|
||||
foldingDirection[unfoldedMesh.edge_handle(unfoldedHalfedges[i]).idx()] = round(math.degrees(mesh.calc_dihedral_angle(originalHalfedges[i])), self.options.roundingDigits)
|
||||
dihedralAngles[unfoldedMesh.edge_handle(unfoldedHalfedges[i]).idx()] = round(math.degrees(mesh.calc_dihedral_angle(originalHalfedges[i])), self.options.roundingDigits)
|
||||
# Information, which edges belong together
|
||||
glueNumber[unfoldedMesh.edge_handle(unfoldedHalfedges[i]).idx()] = mesh.edge_handle(originalHalfedges[i]).idx()
|
||||
|
||||
@ -129,8 +131,7 @@ class Unfold(inkex.EffectExtension):
|
||||
|
||||
isFoldingEdge = np.zeros(numUnfoldedEdges, dtype=bool) # Indicates whether an edge is folded or cut
|
||||
glueNumber = np.empty(numUnfoldedEdges, dtype=int) # Saves with which edge is glued together
|
||||
foldingDirection = np.empty(numUnfoldedEdges, dtype=float) # Valley folding or mountain folding
|
||||
|
||||
dihedralAngles = np.empty(numUnfoldedEdges, dtype=float) # Valley folding or mountain folding
|
||||
connections = np.empty(numFaces, dtype=int) # Saves which original triangle belongs to the unrolled one
|
||||
|
||||
# Select the first triangle as desired
|
||||
@ -185,7 +186,21 @@ class Unfold(inkex.EffectExtension):
|
||||
# Associated triangle in 3D mesh
|
||||
connections[unfoldedFace.idx()] = startingTriangle.idx()
|
||||
# Folding direction and adhesive number
|
||||
self.addVisualisationData(mesh, unfoldedMesh, originalHalfEdges, unfoldedHalfEdges, glueNumber, foldingDirection)
|
||||
self.addVisualisationData(mesh, unfoldedMesh, originalHalfEdges, unfoldedHalfEdges, glueNumber, dihedralAngles)
|
||||
|
||||
if self.angleRangeCalculated is False:
|
||||
self.minAngle = min(dihedralAngles)
|
||||
self.maxAngle = max(dihedralAngles)
|
||||
#sometimes weird large value are returned, like -34345645435464565453356788761029782
|
||||
if self.minAngle < -180.0:
|
||||
self.minAngle = -180.0
|
||||
if self.maxAngle > 180.0:
|
||||
self.maxAngle = 180.0
|
||||
self.angleRange = self.maxAngle - self.minAngle
|
||||
#self.msg(minAngle)
|
||||
#self.msg(maxAngle)
|
||||
#self.msg(angleRange)
|
||||
self.angleRangeCalculated = True
|
||||
|
||||
halfEdgeConnections = {firstHalfEdge.idx(): firstUnfoldedHalfEdge.idx(),
|
||||
secondHalfEdge.idx(): secondUnfoldedHalfEdge.idx(),
|
||||
@ -243,7 +258,7 @@ class Unfold(inkex.EffectExtension):
|
||||
isFoldingEdge[unfoldedLastEdge.idx()] = True
|
||||
|
||||
# Gluing number and folding direction
|
||||
self.addVisualisationData(mesh, unfoldedMesh, originalHalfEdges, unfoldedHalfEdges, glueNumber, foldingDirection)
|
||||
self.addVisualisationData(mesh, unfoldedMesh, originalHalfEdges, unfoldedHalfEdges, glueNumber, dihedralAngles)
|
||||
|
||||
# Related page
|
||||
connections[newface.idx()] = dualEdge[1]
|
||||
@ -252,15 +267,16 @@ class Unfold(inkex.EffectExtension):
|
||||
for i in range(3):
|
||||
halfEdgeConnections[originalHalfEdges[i].idx()] = unfoldedHalfEdges[i].idx()
|
||||
|
||||
return [unfoldedMesh, isFoldingEdge, connections, glueNumber, foldingDirection]
|
||||
return [unfoldedMesh, isFoldingEdge, connections, glueNumber, dihedralAngles]
|
||||
except Exception as e:
|
||||
inkex.utils.debug(str(e))
|
||||
inkex.utils.debug("Error: model could not be unfolded. Check for:")
|
||||
inkex.utils.debug(" - watertight model / intact hull")
|
||||
inkex.utils.debug(" - duplicated edges or faces")
|
||||
inkex.utils.debug(" - detached faces or holes")
|
||||
inkex.utils.debug(" - missing units")
|
||||
inkex.utils.debug(" - missing coordinate system")
|
||||
inkex.utils.debug(" - multiple bodies in one file")
|
||||
inkex.utils.debug("error was: " + str(e))
|
||||
exit(1)
|
||||
|
||||
|
||||
@ -271,7 +287,7 @@ class Unfold(inkex.EffectExtension):
|
||||
numFaces = mesh.n_faces()
|
||||
|
||||
if numFaces > self.options.maxNumFaces:
|
||||
inkex.utils.debug("Aborted. Target STL file has " + str(numFaces) + " faces, but only " + str(maxNumFaces) + " are allowed.")
|
||||
inkex.utils.debug("Aborted. Target STL file has " + str(numFaces) + " faces, but only " + str( self.options.maxNumFaces) + " are allowed.")
|
||||
exit(1)
|
||||
|
||||
if self.options.printStats is True:
|
||||
@ -325,7 +341,7 @@ class Unfold(inkex.EffectExtension):
|
||||
|
||||
# Unfold the tree
|
||||
fullUnfolding = self.unfoldSpanningTree(mesh, spanningTree)
|
||||
[unfoldedMesh, isFoldingEdge, connections, glueNumber, foldingDirection] = fullUnfolding
|
||||
[unfoldedMesh, isFoldingEdge, connections, glueNumber, dihedralAngles] = fullUnfolding
|
||||
|
||||
|
||||
# Resolve the intersections
|
||||
@ -443,12 +459,11 @@ class Unfold(inkex.EffectExtension):
|
||||
mesh = unfolding[0]
|
||||
isFoldingEdge = unfolding[1]
|
||||
glueNumber = unfolding[3]
|
||||
foldingDirection = unfolding[4]
|
||||
dihedralAngles = unfolding[4]
|
||||
|
||||
#statistic values
|
||||
gluePairs = 0
|
||||
mountainCuts = 0
|
||||
valleyCuts = 0
|
||||
cuts = 0
|
||||
coplanarEdges = 0
|
||||
mountainPerforations = 0
|
||||
valleyPerforations = 0
|
||||
@ -463,16 +478,9 @@ class Unfold(inkex.EffectExtension):
|
||||
dashLength = boxSize * self.options.fontSize / 2000
|
||||
spaceLength = boxSize * self.options.fontSize / 800
|
||||
textDistance = boxSize * self.options.fontSize / 800
|
||||
textStrokewidth = boxSize * self.options.fontSize / 3000
|
||||
textStrokeWidth = boxSize * self.options.fontSize / 3000
|
||||
fontsize = boxSize * self.options.fontSize / 1000
|
||||
|
||||
minAngle = min(foldingDirection)
|
||||
maxAngle = max(foldingDirection)
|
||||
angleRange = maxAngle - minAngle
|
||||
#self.msg(minAngle)
|
||||
#self.msg(maxAngle)
|
||||
#self.msg(angleRange)
|
||||
|
||||
# Grouping
|
||||
uniqueMainId = self.svg.get_unique_id("")
|
||||
|
||||
@ -497,30 +505,34 @@ class Unfold(inkex.EffectExtension):
|
||||
om.write_mesh(os.path.join(self.options.TwoDSTLdir, uniqueMainId + "-paperfold-page.stl"), mesh)
|
||||
|
||||
|
||||
#########################################################
|
||||
# Nmbering triangle faces with circle around
|
||||
#########################################################
|
||||
if self.options.printTriangleNumbers is True:
|
||||
|
||||
for face in mesh.faces():
|
||||
centroid = mesh.calc_face_centroid(face)
|
||||
|
||||
textFaceGroup = inkex.Group(id=uniqueMainId + "-textFace-" + str(face.idx()))
|
||||
|
||||
circle = textFaceGroup.add(Circle(cx=str(centroid[0]), cy=str(centroid[1]), r=str(fontsize)))
|
||||
circle.set('id', uniqueMainId + "-textFaceCricle-" + str(face.idx()))
|
||||
circle.set("style", "stroke:#000000;stroke-width:" + str(strokewidth/2) + ";fill:none")
|
||||
circle.set("style", "stroke:#000000;stroke-width {:0.6f}".format(strokewidth/2) + ";fill:none")
|
||||
|
||||
text = textFaceGroup.add(TextElement(id=uniqueMainId + "-textFaceNumber-" + str(face.idx())))
|
||||
text.set("x", str(centroid[0]))
|
||||
text.set("y", str(centroid[1] + fontsize / 3))
|
||||
text.set("font-size", str(fontsize))
|
||||
text.set("style", "stroke-width:" + str(textStrokewidth) + ";text-anchor:middle;text-align:center")
|
||||
text.set("style", "stroke-width {:0.6f}".format(textStrokeWidth) + ";text-anchor:middle;text-align:center")
|
||||
|
||||
tspan = text.add(Tspan(id=uniqueMainId + "-textFaceNumberTspan-" + str(face.idx())))
|
||||
tspan.set("x", str(centroid[0]))
|
||||
tspan.set("y", str(centroid[1] + fontsize / 3))
|
||||
tspan.set("style", "stroke-width:" + str(textStrokewidth) + ";text-anchor:middle;text-align:center")
|
||||
tspan.set("style", "stroke-width {:0.6f}".format(textStrokeWidth) + ";text-anchor:middle;text-align:center")
|
||||
tspan.text = str(face.idx())
|
||||
textFacesGroup.append(textFaceGroup)
|
||||
|
||||
#########################################################
|
||||
# Nmbering triangle edges and style them according to their type
|
||||
#########################################################
|
||||
# Go over all edges of the grid
|
||||
for edge in mesh.edges():
|
||||
# The two endpoints
|
||||
@ -534,46 +546,34 @@ class Unfold(inkex.EffectExtension):
|
||||
# Colour depending on folding direction
|
||||
lineStyle = {"fill": "none"}
|
||||
|
||||
dihedralAngle = foldingDirection[edge.idx()]
|
||||
lineStyle.update({"stroke": self.options.colorCutEdges})
|
||||
line.set("id", uniqueMainId + "-cut-edge-" + str(edge.idx()))
|
||||
|
||||
if dihedralAngle > 0:
|
||||
lineStyle.update({"stroke": self.options.colorMountainCut})
|
||||
line.set("id", uniqueMainId + "-mountain-cut-" + str(edge.idx()))
|
||||
mountainCuts += 1
|
||||
elif dihedralAngle < 0:
|
||||
lineStyle.update({"stroke": self.options.colorValleyCut})
|
||||
line.set("id", uniqueMainId + "-valley-cut-" + str(edge.idx()))
|
||||
valleyCuts += 1
|
||||
elif dihedralAngle == 0:
|
||||
lineStyle.update({"stroke": self.options.colorCoplanarEdges})
|
||||
line.set("id", uniqueMainId + "-coplanar-edge-" + str(edge.idx()))
|
||||
#if self.options.importCoplanarEdges is False:
|
||||
# line.delete()
|
||||
coplanarEdges += 1
|
||||
|
||||
lineStyle.update({"stroke-width":str(strokewidth)})
|
||||
lineStyle.update({"stroke-width": "{:0.6f}".format(strokewidth)})
|
||||
lineStyle.update({"stroke-linecap":"butt"})
|
||||
lineStyle.update({"stroke-linejoin":"miter"})
|
||||
lineStyle.update({"stroke-miterlimit":"4"})
|
||||
|
||||
dihedralAngle = dihedralAngles[edge.idx()]
|
||||
|
||||
# Dotted lines for folding edges
|
||||
if isFoldingEdge[edge.idx()]:
|
||||
if self.options.dashes is True:
|
||||
lineStyle.update({"stroke-dasharray":(str(dashLength) + ", " + str(spaceLength))})
|
||||
if dihedralAngle > 0:
|
||||
lineStyle.update({"stroke": self.options.colorMountainPerforates})
|
||||
line.set("id", uniqueMainId + "-mountain-perforate-" + str(edge.idx()))
|
||||
lineStyle.update({"stroke": self.options.colorMountainFolds})
|
||||
line.set("id", uniqueMainId + "-mountain-fold-" + str(edge.idx()))
|
||||
mountainPerforations += 1
|
||||
if dihedralAngle < 0:
|
||||
lineStyle.update({"stroke": self.options.colorValleyPerforates})
|
||||
line.set("id", uniqueMainId + "-valley-perforate-" + str(edge.idx()))
|
||||
lineStyle.update({"stroke": self.options.colorValleyFolds})
|
||||
line.set("id", uniqueMainId + "-valley-fold-" + str(edge.idx()))
|
||||
valleyPerforations += 1
|
||||
if dihedralAngle == 0:
|
||||
lineStyle.update({"stroke": self.options.colorCoplanarEdges})
|
||||
line.set("id", uniqueMainId + "-coplanar-edge-" + str(edge.idx()))
|
||||
if self.options.importCoplanarEdges is False:
|
||||
line.delete()
|
||||
valleyPerforations += 1
|
||||
coplanarEdges += 1
|
||||
else:
|
||||
lineStyle.update({"stroke-dasharray":"none"})
|
||||
|
||||
@ -583,21 +583,26 @@ class Unfold(inkex.EffectExtension):
|
||||
lineStyle.update({"stroke": randomColorSet[glueNumber[edge.idx()]]})
|
||||
gluePairs += 1
|
||||
|
||||
lineStyle.update({"stroke-dashoffset":"0"})
|
||||
lineStyle.update({"stroke-opacity":"1"})
|
||||
lineStyle.update({"stroke-dashoffset":"0.0"})
|
||||
lineStyle.update({"stroke-opacity":"1.0"})
|
||||
|
||||
if self.options.saturationsForAngles is True:
|
||||
if self.options.edgeStyle == "saturationsForAngles":
|
||||
if dihedralAngle != 0: #we dont want to apply HSL adjustments for zero angle lines because they would be invisible then
|
||||
hslColor = inkex.Color(lineStyle.get('stroke')).to_hsl()
|
||||
newSaturation = abs(dihedralAngle / angleRange) * 100 #percentage values
|
||||
newSaturation = abs(dihedralAngle / self.angleRange) * 100 #percentage values
|
||||
hslColor.saturation = newSaturation
|
||||
lineStyle.update({"stroke":hslColor.to_rgb()})
|
||||
|
||||
elif self.options.edgeStyle == "opacitiesForAngles":
|
||||
if dihedralAngle != 0: #we dont want to apply opacity adjustments for zero angle lines because they would be invisible then
|
||||
opacity = abs(dihedralAngle / 180)
|
||||
lineStyle.update({"stroke-opacity": "{:0.6f}".format(opacity)})
|
||||
|
||||
line.style = lineStyle
|
||||
|
||||
########################################################
|
||||
#########################################################
|
||||
# Textual things
|
||||
########################################################
|
||||
#########################################################
|
||||
halfEdge = mesh.halfedge_handle(edge, 0) # Find halfedge in the face
|
||||
if mesh.face_handle(halfEdge).idx() == -1:
|
||||
halfEdge = mesh.opposite_halfedge_handle(halfEdge)
|
||||
@ -618,13 +623,13 @@ class Unfold(inkex.EffectExtension):
|
||||
text.set("x", str(position[0]))
|
||||
text.set("y", str(position[1]))
|
||||
text.set("font-size", str(fontsize))
|
||||
text.set("style", "stroke-width:" + str(textStrokewidth) + ";text-anchor:middle;text-align:center")
|
||||
text.set("style", "stroke-width {:0.6f}".format(textStrokeWidth) + ";text-anchor:middle;text-align:center")
|
||||
text.set("transform", "rotate(" + str(rotation) + "," + str(position[0]) + "," + str(position[1]) + ")")
|
||||
|
||||
tspan = text.add(Tspan())
|
||||
tspan.set("x", str(position[0]))
|
||||
tspan.set("y", str(position[1]))
|
||||
tspan.set("style", "stroke-width:" + str(textStrokewidth) + ";text-anchor:middle;text-align:center")
|
||||
tspan.set("style", "stroke-width {:0.6f}".format(textStrokeWidth) + ";text-anchor:middle;text-align:center")
|
||||
tspanText = []
|
||||
if self.options.printGluePairNumbers is True and not isFoldingEdge[edge.idx()]:
|
||||
tspanText.append(str(glueNumber[edge.idx()]))
|
||||
@ -653,15 +658,14 @@ class Unfold(inkex.EffectExtension):
|
||||
textGroup.delete() #delete if empty set
|
||||
|
||||
if self.options.printStats is True:
|
||||
inkex.utils.debug(" * Number of mountain cuts: " + str(mountainCuts))
|
||||
inkex.utils.debug(" * Number of valley cuts: " + str(valleyCuts))
|
||||
inkex.utils.debug(" * Number of cuts: " + str(cuts))
|
||||
inkex.utils.debug(" * Number of coplanar edges: " + str(coplanarEdges))
|
||||
inkex.utils.debug(" * Number of mountain perforations: " + str(mountainPerforations))
|
||||
inkex.utils.debug(" * Number of valley perforations: " + str(valleyPerforations))
|
||||
inkex.utils.debug(" * Number of mountain folds: " + str(mountainPerforations))
|
||||
inkex.utils.debug(" * Number of valley folds: " + str(valleyPerforations))
|
||||
inkex.utils.debug(" * Number of glue pairs: {:0.0f}".format(gluePairs / 2))
|
||||
inkex.utils.debug(" * min angle: {:0.2f}".format(minAngle))
|
||||
inkex.utils.debug(" * max angle: {:0.2f}".format(maxAngle))
|
||||
inkex.utils.debug(" * Edge angle range: {:0.2f}".format(angleRange))
|
||||
inkex.utils.debug(" * min angle: {:0.2f}".format(self.minAngle))
|
||||
inkex.utils.debug(" * max angle: {:0.2f}".format(self.maxAngle))
|
||||
inkex.utils.debug(" * Edge angle range: {:0.2f}".format(self.angleRange))
|
||||
|
||||
return paperfoldPageGroup
|
||||
|
||||
@ -691,13 +695,12 @@ class Unfold(inkex.EffectExtension):
|
||||
pars.add_argument("--fontSize", type=int, default=15, help="Label font size (%)")
|
||||
pars.add_argument("--flipLabels", type=inkex.Boolean, default=False, help="Flip labels")
|
||||
pars.add_argument("--dashes", type=inkex.Boolean, default=True, help="Dashes for cut/coplanar edges")
|
||||
pars.add_argument("--saturationsForAngles", type=inkex.Boolean, help="Adjust color saturation for folding edges. The larger the angle the darker the color")
|
||||
pars.add_argument("--edgeStyle", help="Adjust color saturation or opacity for folding edges. The larger the angle the darker the color")
|
||||
pars.add_argument("--separateGluePairsByColor", type=inkex.Boolean, default=False, help="Separate glue pairs by color")
|
||||
pars.add_argument("--colorValleyCut", type=Color, default='255', help="Valley cut edges")
|
||||
pars.add_argument("--colorMountainCut", type=Color, default='1968208895', help="Mountain cut edges")
|
||||
pars.add_argument("--colorCutEdges", type=Color, default='255', help="Cut edges")
|
||||
pars.add_argument("--colorCoplanarEdges", type=Color, default='1943148287', help="Coplanar edges")
|
||||
pars.add_argument("--colorValleyPerforates", type=Color, default='3422552319', help="Valley perforation edges")
|
||||
pars.add_argument("--colorMountainPerforates", type=Color, default='879076607', help="Mountain perforation edges")
|
||||
pars.add_argument("--colorValleyFolds", type=Color, default='3422552319', help="Valley fold edges")
|
||||
pars.add_argument("--colorMountainFolds", type=Color, default='879076607', help="Mountain fold edges")
|
||||
|
||||
#Post Processing
|
||||
pars.add_argument("--joineryMode", type=inkex.Boolean, default=False, help="Enable joinery mode")
|
||||
@ -737,18 +740,41 @@ class Unfold(inkex.EffectExtension):
|
||||
if newColor not in randomColorSet:
|
||||
randomColorSet.append(newColor)
|
||||
|
||||
#some mode configs:
|
||||
#########################################################
|
||||
# mode config for joinery:
|
||||
#########################################################
|
||||
if self.options.joineryMode is True:
|
||||
self.options.separateGluePairsByColor = True #we need random colors in this mode
|
||||
|
||||
|
||||
#########################################################
|
||||
# mode config for origami simulator:
|
||||
#########################################################
|
||||
'''
|
||||
required style for Origami Simulator:
|
||||
colors:
|
||||
- #ff0000 (red) - mountain folds
|
||||
- #0000ff (blue) - valley folds
|
||||
- #000000 (black) - boundary cuts (for both the outline of the pattern and any internal holes)
|
||||
- #ffff00 (yellow) - coplonar triangle edges ("facet creases") (no support for polygons > 3 edges)
|
||||
- #00ff00 (green) - thin slits
|
||||
- #ff00ff (magenta) - undriven creases (swing freely)
|
||||
|
||||
opacity:
|
||||
- final fold angle of a mountain or valley fold is set by its opacity. Any fold angle between 0° and 180° may be used. For example:
|
||||
- 1.0 = 180° (fully folded)
|
||||
- 0.5 = 90°
|
||||
- 0 = 0° (flat)
|
||||
'''
|
||||
if self.options.origamiSimulatorMode is True:
|
||||
self.options.joineryMode = True #we set to true even if false because we need the same flat structure for origami simulator
|
||||
self.options.separateGluePairsByColor = False #we need to have no weird random colors in this mode
|
||||
self.options.colorMountainCut = "#000000" #black
|
||||
self.options.colorValleyCut = "#000000" #black
|
||||
self.options.colorCoplanarEdges = "#000000" #black
|
||||
self.options.colorMountainPerforates = "#ff0000" #red
|
||||
self.options.colorValleyPerforates = "#0000ff" #blue
|
||||
self.options.edgeStyle = "opacitiesForAngles" #highly important for simulation
|
||||
self.options.importCoplanarEdges = True
|
||||
self.options.colorCutEdges = "#000000" #black
|
||||
self.options.colorCoplanarEdges = "#ffff00" #yellow
|
||||
self.options.colorMountainFolds = "#ff0000" #red
|
||||
self.options.colorValleyFolds = "#0000ff" #blue
|
||||
|
||||
# Create a new container group to attach all paperfolds
|
||||
paperfoldMainGroup = self.document.getroot().add(inkex.Group(id=self.svg.get_unique_id("paperfold-"))) #make a new group at root level
|
||||
|
Reference in New Issue
Block a user