Skip to content

Commit 9649770

Browse files
committed
[orx-processing] Fix PShape conversion when multiple ShapeContours are present
Add a demo to show it works. I tested this in Processing and noticed it's necessary to avoid wrapping the first vertices in `s.beginContour()` / `s.endContour()`, otherwise it does not render properly there. I also noticed that `createShape()` in Processing creates a `PShape(PShape.GEOMETRY)` by default, but we create a `PShape.PATH`. I tried changing this but it failed to work without further tweaks, so I kept it as `PATH` for now.
1 parent 3ba0395 commit 9649770

File tree

4 files changed

+64
-9
lines changed

4 files changed

+64
-9
lines changed

orx-jvm/orx-processing/src/demo/kotlin/DemoPShape01.kt

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,13 +2,20 @@ import org.openrndr.application
22
import org.openrndr.extra.processing.PShape
33
import org.openrndr.extra.processing.toShape
44

5+
/**
6+
* Demonstrates how to construct a Processing `PShape` out of an OPENRNDR
7+
* `Shape` instance, and how to convert a `PShape` back into a `Shape.
8+
*
9+
* The program renders a rectangular `Shape` after converting to PShape and back.
10+
*
11+
*/
512
fun main() = application {
613
program {
7-
val c = drawer.bounds.offsetEdges(-100.0).shape
8-
val ps = PShape(c)
9-
val rc = ps.toShape()
14+
val s = drawer.bounds.offsetEdges(-100.0).shape
15+
val ps = PShape(s)
16+
val rs = ps.toShape()
1017
extend {
11-
drawer.shape(rc)
18+
drawer.shape(rs)
1219
}
1320
}
1421
}

orx-jvm/orx-processing/src/demo/kotlin/DemoPShape02.kt

Lines changed: 13 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,16 @@ import org.openrndr.extra.processing.PShape
44
import org.openrndr.extra.processing.toShape
55
import org.openrndr.extra.shapes.primitives.regularStarRounded
66

7+
/**
8+
* Demonstrates how to convert a `ShapeContour` into a Processing
9+
* `PShape`, then converts the `PShape` to a `Shape`.
10+
*
11+
* The program renders both the original `ShapeContour` and
12+
* the resulting `Shape` after being a `PShape`.
13+
*
14+
* Both elements are rendered with translucency and a slight offset
15+
* so they can be visually compared.
16+
*/
717
fun main() = application {
818
program {
919
val c = regularStarRounded(
@@ -15,10 +25,11 @@ fun main() = application {
1525
center = drawer.bounds.center
1626
)
1727
val ps = PShape(c)
18-
val rc = ps.toShape()
28+
val rs = ps.toShape()
1929
extend {
2030
drawer.fill = ColorRGBa.PINK.opacify(0.5)
21-
drawer.shape(rc)
31+
drawer.shape(rs)
32+
2233
drawer.translate(15.0, 15.0)
2334
drawer.contour(c)
2435
}
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
import org.openrndr.application
2+
import org.openrndr.color.ColorRGBa
3+
import org.openrndr.extra.processing.PShape
4+
import org.openrndr.extra.processing.toShape
5+
import org.openrndr.extra.shapes.operators.roundCorners
6+
import org.openrndr.shape.Shape
7+
8+
/**
9+
* Demonstrates how to convert a `Shape` with multiple `ShapeContour`s
10+
* (an outer contour and two holes) into a Processing `PShape`,
11+
* then converts it back to a `Shape`.
12+
*
13+
* The program renders both the original `Shape` and
14+
* the resulting `Shape` with translucency and a slight offset
15+
* so they can be visually compared.
16+
*/
17+
fun main() = application {
18+
program {
19+
val outlineRect = drawer.bounds.offsetEdges(-100.0)
20+
val s = Shape(
21+
listOf(
22+
outlineRect.contour.roundCorners(60.0),
23+
outlineRect.sub(0.25..0.45, 0.25..0.75).contour.reversed.roundCorners(30.0),
24+
outlineRect.sub(0.55..0.75, 0.25..0.75).contour.reversed.roundCorners(30.0),
25+
)
26+
)
27+
val ps = PShape(s)
28+
val rs = ps.toShape()
29+
extend {
30+
drawer.fill = ColorRGBa.PINK.opacify(0.5)
31+
drawer.shape(rs)
32+
33+
drawer.translate(15.0, 15.0)
34+
drawer.shape(s)
35+
}
36+
}
37+
}

orx-jvm/orx-processing/src/main/kotlin/PShapeExtensions.kt

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -92,8 +92,8 @@ fun PShape(shape: Shape): PShape {
9292
} else {
9393
val ps = PShape(PShape.PATH)
9494
ps.beginShape()
95-
for (contour in shape.contours) {
96-
ps.beginContour()
95+
shape.contours.forEachIndexed { i, contour ->
96+
if(i > 0) ps.beginContour()
9797
ps.vertex(contour.segments[0].start)
9898
for (segment in contour.segments) {
9999
when (segment.type) {
@@ -102,7 +102,7 @@ fun PShape(shape: Shape): PShape {
102102
SegmentType.CUBIC -> ps.bezierVertex(segment.control[0], segment.control[1], segment.end)
103103
}
104104
}
105-
ps.endContour()
105+
if(i > 0) ps.endContour()
106106
}
107107
ps.endShape(PShape.CLOSE)
108108
return ps

0 commit comments

Comments
 (0)