[orx-shapes] Add splitIn

This commit is contained in:
Edwin Jakobs
2023-10-28 14:01:39 +02:00
parent cce913d269
commit 2293d5d74e
2 changed files with 36 additions and 13 deletions

View File

@@ -11,17 +11,15 @@ data class ContourAdjusterEdge(val contourAdjuster: ContourAdjuster, val segment
val endPosition val endPosition
get() = contourAdjuster.contour.segments[segmentIndex()].end get() = contourAdjuster.contour.segments[segmentIndex()].end
fun position(t: Double) : Vector2 { fun position(t: Double): Vector2 {
return contourAdjuster.contour.segments[segmentIndex()].position(t) return contourAdjuster.contour.segments[segmentIndex()].position(t)
} }
fun normal(t: Double) : Vector2 { fun normal(t: Double): Vector2 {
return contourAdjuster.contour.segments[segmentIndex()].normal(t) return contourAdjuster.contour.segments[segmentIndex()].normal(t)
} }
/** /**
* A [ContourAdjusterVertex] interface for the start-vertex of the edge * A [ContourAdjusterVertex] interface for the start-vertex of the edge
*/ */
@@ -32,7 +30,9 @@ data class ContourAdjusterEdge(val contourAdjuster: ContourAdjuster, val segment
* A [ContourAdjusterVertex] interface for the end-vertex of the edge * A [ContourAdjusterVertex] interface for the end-vertex of the edge
*/ */
val end val end
get() = ContourAdjusterVertex(contourAdjuster, { (segmentIndex() + 1).mod(contourAdjuster.contour.segments.size) } ) get() = ContourAdjusterVertex(
contourAdjuster,
{ (segmentIndex() + 1).mod(contourAdjuster.contour.segments.size) })
/** /**
* A link to the edge before this edge * A link to the edge before this edge
@@ -56,7 +56,7 @@ data class ContourAdjusterEdge(val contourAdjuster: ContourAdjuster, val segment
this.copy(segmentIndex = { (segmentIndex() + 1).mod(contourAdjuster.contour.segments.size) }) this.copy(segmentIndex = { (segmentIndex() + 1).mod(contourAdjuster.contour.segments.size) })
} else { } else {
if (segmentIndex() < contourAdjuster.contour.segments.size - 1) { if (segmentIndex() < contourAdjuster.contour.segments.size - 1) {
this.copy(segmentIndex = { segmentIndex() + 1 } ) this.copy(segmentIndex = { segmentIndex() + 1 })
} else { } else {
null null
} }
@@ -65,27 +65,36 @@ data class ContourAdjusterEdge(val contourAdjuster: ContourAdjuster, val segment
fun select() { fun select() {
contourAdjuster.selectEdge(segmentIndex()) contourAdjuster.selectEdge(segmentIndex())
} }
private fun wrap(block: ContourEdge.() -> ContourEdge) { private fun wrap(block: ContourEdge.() -> ContourEdge) {
val newEdge = ContourEdge(contourAdjuster.contour, segmentIndex()).block() val newEdge = ContourEdge(contourAdjuster.contour, segmentIndex()).block()
contourAdjuster.contour = newEdge.contour contourAdjuster.contour = newEdge.contour
contourAdjuster.updateSelection(newEdge.adjustments) contourAdjuster.updateSelection(newEdge.adjustments)
} }
fun toLinear() = wrap { toLinear() } fun toLinear() = wrap { toLinear() }
fun toCubic() = wrap { toCubic() } fun toCubic() = wrap { toCubic() }
fun splitAt(t: Double) = wrap { splitAt(t) } fun splitAt(t: Double) = wrap { splitAt(t) }
/**
* split edge in [numberOfParts] parts of equal length
*/
fun splitIn(numberOfParts: Int) = wrap { splitIn(numberOfParts) }
fun moveBy(translation: Vector2, updateTangents: Boolean = true) = wrap { movedBy(translation, updateTangents) } fun moveBy(translation: Vector2, updateTangents: Boolean = true) = wrap { movedBy(translation, updateTangents) }
fun rotate(rotationInDegrees: Double, anchorT: Double = 0.5, updateTangents: Boolean = true) = fun rotate(rotationInDegrees: Double, anchorT: Double = 0.5, updateTangents: Boolean = true) =
wrap { rotatedBy(rotationInDegrees, anchorT, updateTangents) } wrap { rotatedBy(rotationInDegrees, anchorT, updateTangents) }
fun scale(scaleFactor: Double, anchorT: Double = 0.5, updateTangents: Boolean = true) = fun scale(scaleFactor: Double, anchorT: Double = 0.5, updateTangents: Boolean = true) =
wrap { scaledBy(scaleFactor, anchorT, updateTangents = true) } wrap { scaledBy(scaleFactor, anchorT, updateTangents = true) }
fun replaceWith(t:Double, updateTangents: Boolean = true) = wrap { replacedWith(t, updateTangents) } fun replaceWith(t: Double, updateTangents: Boolean = true) = wrap { replacedWith(t, updateTangents) }
fun replaceWith(openContour: ShapeContour) = wrap { replacedWith(openContour) } fun replaceWith(openContour: ShapeContour) = wrap { replacedWith(openContour) }
fun sub(t0:Double, t1: Double, updateTangents: Boolean = true) { fun sub(t0: Double, t1: Double, updateTangents: Boolean = true) {
contourAdjuster.contour = contourAdjuster.contour =
ContourEdge(contourAdjuster.contour, segmentIndex()) ContourEdge(contourAdjuster.contour, segmentIndex())
.subbed(t0, t1) .subbed(t0, t1)

View File

@@ -1,5 +1,7 @@
package org.openrndr.extra.shapes.adjust package org.openrndr.extra.shapes.adjust
import org.openrndr.extra.shapes.rectify.rectified
import org.openrndr.extra.shapes.utilities.fromContours
import org.openrndr.extra.shapes.utilities.insertPointAt import org.openrndr.extra.shapes.utilities.insertPointAt
import org.openrndr.math.Matrix44 import org.openrndr.math.Matrix44
import org.openrndr.math.Vector2 import org.openrndr.math.Vector2
@@ -111,11 +113,25 @@ data class ContourEdge(
return ContourEdge(ShapeContour.fromSegments(newSegments, contour.closed), segmentIndex, adjustments) return ContourEdge(ShapeContour.fromSegments(newSegments, contour.closed), segmentIndex, adjustments)
} }
fun replacedWith(openContour: ShapeContour) : ContourEdge { fun splitIn(parts: Int): ContourEdge {
if (contour.empty || parts < 2) {
return withoutAdjustments()
}
val segment = contour.segments[segmentIndex]
val r = segment.contour.rectified()
val newSegments = (0..parts).map {
it.toDouble() / parts
}.windowed(2, 1).map {
r.sub(it[0], it[1])
}
return replacedWith(ShapeContour.fromContours(newSegments, false))
}
fun replacedWith(openContour: ShapeContour): ContourEdge {
if (contour.empty) { if (contour.empty) {
return withoutAdjustments() return withoutAdjustments()
} }
require(!openContour.closed) { "openContour should be open"} require(!openContour.closed) { "openContour should be open" }
val segment = contour.segments[segmentIndex] val segment = contour.segments[segmentIndex]
var newSegments = contour.segments.toMutableList() var newSegments = contour.segments.toMutableList()
@@ -255,7 +271,5 @@ data class ContourEdge(
translate(-anchor) translate(-anchor)
}, updateTangents) }, updateTangents)
} }
} }