From 60a64806fcc9ff0a3b18546cb3a078961d5e7665 Mon Sep 17 00:00:00 2001 From: Edwin Jakobs Date: Wed, 22 Apr 2020 21:56:08 +0200 Subject: [PATCH] Add screenshot generation --- build.gradle | 38 ++++++- orx-easing/README.md | 6 +- orx-easing/build.gradle | 1 + orx-easing/src/demo/kotlin/DemoEasings01.kt | 16 +-- orx-fx/build.gradle | 16 +++ orx-fx/src/demo/kotlin/DemoFluidDistort01.kt | 30 +++++ orx-fx/src/main/kotlin/color/Colorspaces.kt | 8 ++ .../src/main/kotlin/distort/FluidDistort.kt | 68 ++++++++++++ orx-fx/src/main/kotlin/distort/Perturb.kt | 30 ++--- .../extra/fx/gl3/color/rgb-to-ycbcr.frag | 18 +++ .../extra/fx/gl3/color/ycbcr-to-rgb.frag | 26 +++++ .../extra/fx/gl3/distort/fluid-distort.frag | 73 +++++++++++++ .../extra/fx/gl3/distort/perturb.frag | 20 ++-- .../openrndr/extra/fx/gl3/distort/uvmap.frag | 11 ++ orx-gui/build.gradle | 1 + orx-gui/src/demo/kotlin/DemoOptions01.kt | 6 + orx-gui/src/demo/kotlin/DemoSimple01.kt | 8 +- orx-jumpflood/build.gradle | 4 + .../src/demo/kotlin/DemoShapeSDF01.kt | 42 +++++++ .../src/demo/kotlin/DemoShapeSDF02.kt | 70 ++++++++++++ .../src/demo/kotlin/DemoShapeSDF03.kt | 74 +++++++++++++ .../src/demo/kotlin/DemoShapeSDF04.kt | 80 ++++++++++++++ .../src/demo/kotlin/DemoShapeSDF05.kt | 98 +++++++++++++++++ .../src/demo/kotlin/DemoSkeleton01.kt | 8 +- .../src/demo/kotlin/DemoStraightSkeleton01.kt | 7 ++ orx-jumpflood/src/demo/resources/name.svg | 12 ++ orx-jumpflood/src/main/kotlin/ShapeSDF.kt | 78 +++++++++++++ orx-jumpflood/src/main/kotlin/draw/SDFDraw.kt | 41 +++++++ orx-jumpflood/src/main/kotlin/ops/SDFOps.kt | 86 +++++++++++++++ .../shaders/gl3/draw/sdf-stroke-fill.frag | 24 ++++ .../resources/shaders/gl3/ops/sdf-onion.frag | 12 ++ .../resources/shaders/gl3/ops/sdf-round.frag | 12 ++ .../gl3/ops/sdf-smooth-difference.frag | 19 ++++ .../gl3/ops/sdf-smooth-intersection.frag | 19 ++++ .../shaders/gl3/ops/sdf-smooth-union.frag | 19 ++++ .../main/resources/shaders/gl3/shape-sdf.frag | 103 ++++++++++++++++++ orx-keyframer/build.gradle | 2 + orx-keyframer/src/demo/kotlin/DemoFull01.kt | 7 +- orx-keyframer/src/demo/kotlin/DemoScrub01.kt | 7 +- orx-keyframer/src/demo/kotlin/DemoSimple01.kt | 7 +- orx-keyframer/src/demo/kotlin/DemoSimple02.kt | 6 + .../demo/kotlin/DemoSimpleExpressions01.kt | 7 +- .../demo/kotlin/DemoSimpleRepetitions01.kt | 7 +- orx-mesh-generators/build.gradle | 1 + .../src/demo/kotlin/DemoBox.kt | 12 +- .../src/demo/kotlin/DemoComplex01.kt | 13 ++- .../src/demo/kotlin/DemoComplex02.kt | 11 +- .../src/demo/kotlin/DemoComplex03.kt | 11 +- .../src/demo/kotlin/DemoComplex04.kt | 12 +- .../src/demo/kotlin/DemoComplex05.kt | 10 +- .../src/demo/kotlin/DemoComplex06.kt | 35 ------ orx-noise/build.gradle | 1 + .../src/demo/kotlin/DemoGradientPerturb2D.kt | 7 +- .../src/demo/kotlin/DemoGradientPerturb3D.kt | 6 + orx-rabbit-control/build.gradle | 1 + .../src/demo/kotlin/DemoRabbitControl.kt | 7 +- .../kotlin/DemoRabbitControlManualOverlay.kt | 6 + orx-shade-styles/build.gradle | 1 + .../src/demo/kotlin/DemoRadialGradient01.kt | 6 + orx-time-operators/build.gradle | 1 + .../src/demo/kotlin/DemoEnvelope.kt | 6 + orx-time-operators/src/demo/kotlin/DemoLFO.kt | 7 +- orx-timer/build.gradle | 1 + orx-timer/src/demo/kotlin/DemoRepeat01.kt | 6 + orx-timer/src/demo/kotlin/DemoRepeat02.kt | 6 + orx-timer/src/demo/kotlin/DemoTimeOut01.kt | 6 + 66 files changed, 1316 insertions(+), 84 deletions(-) create mode 100644 orx-fx/src/demo/kotlin/DemoFluidDistort01.kt create mode 100644 orx-fx/src/main/kotlin/color/Colorspaces.kt create mode 100644 orx-fx/src/main/kotlin/distort/FluidDistort.kt create mode 100644 orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/color/rgb-to-ycbcr.frag create mode 100644 orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/color/ycbcr-to-rgb.frag create mode 100644 orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/fluid-distort.frag create mode 100644 orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/uvmap.frag create mode 100644 orx-jumpflood/src/demo/kotlin/DemoShapeSDF01.kt create mode 100644 orx-jumpflood/src/demo/kotlin/DemoShapeSDF02.kt create mode 100644 orx-jumpflood/src/demo/kotlin/DemoShapeSDF03.kt create mode 100644 orx-jumpflood/src/demo/kotlin/DemoShapeSDF04.kt create mode 100644 orx-jumpflood/src/demo/kotlin/DemoShapeSDF05.kt create mode 100644 orx-jumpflood/src/demo/resources/name.svg create mode 100644 orx-jumpflood/src/main/kotlin/ShapeSDF.kt create mode 100644 orx-jumpflood/src/main/kotlin/draw/SDFDraw.kt create mode 100644 orx-jumpflood/src/main/kotlin/ops/SDFOps.kt create mode 100644 orx-jumpflood/src/main/resources/shaders/gl3/draw/sdf-stroke-fill.frag create mode 100644 orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-onion.frag create mode 100644 orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-round.frag create mode 100644 orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-difference.frag create mode 100644 orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-intersection.frag create mode 100644 orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-union.frag create mode 100644 orx-jumpflood/src/main/resources/shaders/gl3/shape-sdf.frag delete mode 100644 orx-mesh-generators/src/demo/kotlin/DemoComplex06.kt diff --git a/build.gradle b/build.gradle index 0e7d5f0c..59c631b0 100644 --- a/build.gradle +++ b/build.gradle @@ -16,7 +16,7 @@ buildscript { apply plugin: 'org.jetbrains.dokka' project.ext { - openrndrVersion = "0.3.41" + openrndrVersion = "0.4.0-SNAPSHOT" kotlinVersion = "1.3.72" spekVersion = "2.0.10" libfreenectVersion = "0.5.7-1.5.3" @@ -62,6 +62,7 @@ allprojects { group 'org.openrndr.extra' repositories { + mavenLocal() mavenCentral() jcenter() maven { @@ -124,4 +125,39 @@ allprojects { includeEngines 'spek2' } } + + +} + +task collectScreenshots(dependsOn: 'classes') { + doFirst { + for (sub in project.subprojects) { + if (sub.sourceSets.hasProperty("demo")) { + def set = sub.sourceSets.demo + def ucl = new URLClassLoader(set.runtimeClasspath.collect { it.toURI().toURL() } as URL[]) + for (x in set.output) { + if (x.exists()) { + for (y in x.listFiles()) { + def name = y.name + if (!name.contains('$') && name.contains(".class")) { + def klass = ucl.loadClass(y.name.replace(".class", "")) + try { + def mainMethod = klass.getMethod("main") + javaexec { + classpath set.runtimeClasspath + def className = y.name.replace(".class", "") + main = className + jvmArgs += "-DtakeScreenshot=true" + jvmArgs += "-DscreenshotPath=${sub.name}/images/${className}.png" + } + } catch (e) { + // skip? + } + } + } + } + } + } + } + } } diff --git a/orx-easing/README.md b/orx-easing/README.md index 029a3ccb..b6b9294f 100644 --- a/orx-easing/README.md +++ b/orx-easing/README.md @@ -28,4 +28,8 @@ Using the `Easing` enumeration ```kotlin val et = Easing.QuadIn.function(t, 0.0, 1.0, 1.0) -``` \ No newline at end of file +``` + +## Demos +[DemoEasings01Kt](src/demo/kotlin/DemoEasings01.kt) +![Screenshot](images/DemoEasings01Kt.png) \ No newline at end of file diff --git a/orx-easing/build.gradle b/orx-easing/build.gradle index d3bbc651..49d7c034 100644 --- a/orx-easing/build.gradle +++ b/orx-easing/build.gradle @@ -14,6 +14,7 @@ dependencies { demoImplementation(project(":orx-camera")) demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") demoImplementation(sourceSets.getByName("main").output) diff --git a/orx-easing/src/demo/kotlin/DemoEasings01.kt b/orx-easing/src/demo/kotlin/DemoEasings01.kt index ce0eb282..27a5aad3 100644 --- a/orx-easing/src/demo/kotlin/DemoEasings01.kt +++ b/orx-easing/src/demo/kotlin/DemoEasings01.kt @@ -1,11 +1,11 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extras.easing.* import org.openrndr.math.Vector2 fun main() { application { - configure { width = 1280 height = 1080 @@ -19,14 +19,17 @@ fun main() { points.add(Vector2(i*10.0, y)) } drawer.lineStrip(points) - drawer.stroke = ColorRGBa.GRAY drawer.lineSegment(0.0, 40.0, 400.0, 40.0) - - drawer.lineSegment(0.0, 20.0, 400.0, 20.0) - } + + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend { drawer.stroke = ColorRGBa.WHITE @@ -62,9 +65,7 @@ fun main() { ::easeBounceIn, ::easeBounceOut, ::easeBounceInOut - ) - var i = 0 for (f in functions) { drawEasing(f) @@ -78,5 +79,4 @@ fun main() { } } } - } \ No newline at end of file diff --git a/orx-fx/build.gradle b/orx-fx/build.gradle index 7afc9b60..d6a74909 100644 --- a/orx-fx/build.gradle +++ b/orx-fx/build.gradle @@ -1,3 +1,19 @@ +sourceSets { + demo { + java { + srcDirs = ["src/demo/kotlin"] + compileClasspath += main.getCompileClasspath() + runtimeClasspath += main.getRuntimeClasspath() + } + } +} + dependencies { api project(":orx-parameters") + + demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") + demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") + demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") + demoImplementation(sourceSets.getByName("main").output) } \ No newline at end of file diff --git a/orx-fx/src/demo/kotlin/DemoFluidDistort01.kt b/orx-fx/src/demo/kotlin/DemoFluidDistort01.kt new file mode 100644 index 00000000..bfb0b44d --- /dev/null +++ b/orx-fx/src/demo/kotlin/DemoFluidDistort01.kt @@ -0,0 +1,30 @@ +import org.openrndr.application +import org.openrndr.draw.colorBuffer +import org.openrndr.extensions.SingleScreenshot +import org.openrndr.extra.fx.distort.FluidDistort +import org.openrndr.extra.fx.patterns.Checkers + +fun main() { + application { + program { + val fd = FluidDistort() + val checkers = Checkers() + + val image = colorBuffer(width, height) + val distorted = image.createEquivalent() + checkers.size = 64.0 + checkers.apply(emptyArray(), image) + + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend { + fd.blend = mouse.position.x/width + fd.apply(image, distorted) + drawer.image(distorted) + } + } + } +} \ No newline at end of file diff --git a/orx-fx/src/main/kotlin/color/Colorspaces.kt b/orx-fx/src/main/kotlin/color/Colorspaces.kt new file mode 100644 index 00000000..63de2580 --- /dev/null +++ b/orx-fx/src/main/kotlin/color/Colorspaces.kt @@ -0,0 +1,8 @@ +package org.openrndr.extra.fx.color + +import org.openrndr.draw.Filter +import org.openrndr.draw.filterShaderFromUrl +import org.openrndr.extra.fx.filterFragmentUrl + +class RgbToYCbcr : Filter(filterShaderFromUrl(filterFragmentUrl("color/rgb-to-ycbcr.frag"))) +class YcbcrToRgb : Filter(filterShaderFromUrl(filterFragmentUrl("color/ycbcr-to-rgb.frag"))) \ No newline at end of file diff --git a/orx-fx/src/main/kotlin/distort/FluidDistort.kt b/orx-fx/src/main/kotlin/distort/FluidDistort.kt new file mode 100644 index 00000000..9f4f5295 --- /dev/null +++ b/orx-fx/src/main/kotlin/distort/FluidDistort.kt @@ -0,0 +1,68 @@ +package org.openrndr.extra.fx.distort + +import org.openrndr.draw.ColorBuffer +import org.openrndr.draw.Filter +import org.openrndr.draw.filterShaderFromUrl +import org.openrndr.extra.fx.filterFragmentUrl +import kotlin.math.cos + +private class UVMap: Filter(filterShaderFromUrl(filterFragmentUrl("distort/uvmap.frag"))) { + +} + +private class FluidDistortFilter : Filter(filterShaderFromUrl(filterFragmentUrl("distort/fluid-distort.frag"))) { + var blend : Double by parameters + var random: Double by parameters + init { + blend = 0.0 + random = 0.0 + } + +} + +class FluidDistort : Filter() { + var blend: Double = 1.0 + + var outputUV = false + + private val distort = FluidDistortFilter() + private val uvmap = UVMap() + + private var buffer0: ColorBuffer? = null + private var buffer1: ColorBuffer? = null + private var index = 0 + override fun apply(source: Array, target: Array) { + + distort.blend = blend + distort.random = cos(index*0.5)*0.5+0.5 + + buffer0?.let { + if (!it.isEquivalentTo(target[0])) { + it.destroy() + } + } + if (buffer0 == null) { + buffer0 = target[0].createEquivalent() + } + + buffer1?.let { + if (!it.isEquivalentTo(target[0])) { + it.destroy() + } + } + if (buffer1 == null) { + buffer1 = target[0].createEquivalent() + } + val buffers = arrayOf(buffer0!!, buffer1!!) + distort.apply(buffers[index%2], buffers[(index+1)%2]) + + if (!outputUV) { + uvmap.apply(arrayOf(buffers[(index + 1) % 2], source[0]), target[0]) + } else { + buffers[(index+1)%2].copyTo(target[0]) + } + index++ + blend = 0.0 + } + +} \ No newline at end of file diff --git a/orx-fx/src/main/kotlin/distort/Perturb.kt b/orx-fx/src/main/kotlin/distort/Perturb.kt index 22d920ca..1a670805 100644 --- a/orx-fx/src/main/kotlin/distort/Perturb.kt +++ b/orx-fx/src/main/kotlin/distort/Perturb.kt @@ -2,9 +2,8 @@ package org.openrndr.extra.fx.distort import org.openrndr.draw.* import org.openrndr.extra.fx.filterFragmentUrl -import org.openrndr.extra.parameters.Description -import org.openrndr.extra.parameters.DoubleParameter -import org.openrndr.extra.parameters.IntParameter +import org.openrndr.extra.parameters.* +import org.openrndr.math.Vector2 import org.openrndr.math.Vector3 import org.openrndr.math.Vector4 @@ -15,37 +14,41 @@ class Perturb : Filter(filterShaderFromUrl(filterFragmentUrl("distort/perturb.fr /** * base noise scale, default is Vector3(1.0, 1.0, 1.0) */ - @DoubleParameter("scale", 0.01, 8.0) + @DoubleParameter("scale", 0.01, 8.0, order = 0) var scale: Double by parameters - @DoubleParameter("phase", -2.0, 2.0) + @DoubleParameter("phase", -2.0, 2.0, order = 1) var phase: Double by parameters /** * lacunarity is the amount by which scale is modulated per octave, default is Vector3(2.0, 2.0, 2.0) */ - @DoubleParameter("lacunarity", 0.0, 1.0) + @DoubleParameter("lacunarity", 0.0, 1.0, order = 2) var lacunarity: Double by parameters - @DoubleParameter("gain", 0.0, 1.0) + @DoubleParameter("gain", 0.0, 1.0, order = 3) var gain: Double by parameters - @DoubleParameter("decay", 0.0, 1.0) + @DoubleParameter("decay", 0.0, 1.0, order = 4) var decay: Double by parameters /** * the number of octaves of noise to generate, default is 4 */ - @IntParameter("octaves", 1, 10) + @IntParameter("octaves", 1, 10, order = 5) var octaves: Int by parameters - - @IntParameter("x segments", 0, 256) + @IntParameter("x segments", 0, 256, order = 6) var xSegments: Int by parameters - @IntParameter("y segments", 0, 256) + @IntParameter("y segments", 0, 256, order = 7) var ySegments: Int by parameters + @BooleanParameter("output UV", order = 8) + var outputUV: Boolean by parameters + + @Vector2Parameter("offset", -1.0, 1.0, order = 9) + var offset: Vector2 by parameters init { @@ -58,6 +61,8 @@ class Perturb : Filter(filterShaderFromUrl(filterFragmentUrl("distort/perturb.fr phase = 0.0 xSegments = 0 ySegments = 0 + outputUV = false + offset = Vector2.ZERO } var bicubicFiltering = true @@ -68,5 +73,4 @@ class Perturb : Filter(filterShaderFromUrl(filterFragmentUrl("distort/perturb.fr } super.apply(source, target) } - } \ No newline at end of file diff --git a/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/color/rgb-to-ycbcr.frag b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/color/rgb-to-ycbcr.frag new file mode 100644 index 00000000..4dbbf715 --- /dev/null +++ b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/color/rgb-to-ycbcr.frag @@ -0,0 +1,18 @@ +#version 330 + +uniform vec4 tint; +in vec2 v_texCoord0; +uniform sampler2D tex0; + +out vec4 o_color; +void main() { + vec4 c = texture(tex0, v_texCoord0); + if (c.a != 0.0) { + c.rgb /= c.a; + } + c.rgb *= 255.0; + float y = 0.0 + 0.299 * c.r + 0.587 * c.g + 0.114 * c.b; + float cb = 128 - (0.168736 * c.r) - (0.331264 * c.g) + (0.5 * c.b); + float cr = 128 + (0.5 * c.r) - 0.418688 * c.g - 0.081312 * c.b; + o_color = vec4(y/255.0, cb/255.0, cr/255.0, 1.0) * c.a; +} \ No newline at end of file diff --git a/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/color/ycbcr-to-rgb.frag b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/color/ycbcr-to-rgb.frag new file mode 100644 index 00000000..e98391cf --- /dev/null +++ b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/color/ycbcr-to-rgb.frag @@ -0,0 +1,26 @@ +#version 330 + +uniform vec4 tint; +in vec2 v_texCoord0; +uniform sampler2D tex0; + +out vec4 o_color; +void main() { + vec2 ts = textureSize(tex0, 0); + vec4 c = texture(tex0, v_texCoord0); + + if (c.a != 0.0) { + c.rgb /= c.a; + } + c.rgb *= 255.0; + + float y = c.r; + float cb = c.g; + float cr = c.b; + + float r = y + 1.402 * (cr - 128.0); + float g = y - 0.344136 * (cb - 128.0) - 0.714136 * (cr - 128.0); + float b = y + 1.772 * (cb - 128.0); + + o_color = vec4(r/255.0, g/255.0, b/255.0, 1.0) * c.a; +} \ No newline at end of file diff --git a/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/fluid-distort.frag b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/fluid-distort.frag new file mode 100644 index 00000000..7d31b7c4 --- /dev/null +++ b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/fluid-distort.frag @@ -0,0 +1,73 @@ +#version 330 + +// created by florian berger (flockaroo) - 2016 +// License Creative Commons Attribution-NonCommercial-ShareAlike 3.0 Unported License. + +// single pass CFD +// --------------- +// this is some "computational flockarooid dynamics" ;) +// the self-advection is done purely rotational on all scales. +// therefore i dont need any divergence-free velocity field. +// with stochastic sampling i get the proper "mean values" of rotations +// over time for higher order scales. +// +// try changing "RotNum" for different accuracies of rotation calculation +// for even RotNum uncomment the line #define SUPPORT_EVEN_ROTNUM + +#define RotNum 5 +//#define SUPPORT_EVEN_ROTNUM + +//#define keyTex iChannel3 +//#define KEY_I texture(keyTex,vec2((105.5-32.0)/256.0,(0.5+0.0)/3.0)).x + +const float ang = 2.0*3.1415926535/float(RotNum); +mat2 m = mat2(cos(ang), sin(ang), -sin(ang), cos(ang)); +mat2 mh = mat2(cos(ang*0.5), sin(ang*0.5), -sin(ang*0.5), cos(ang*0.5)); + +uniform sampler2D tex0; +uniform float time; +uniform float random; + +in vec2 v_texCoord0; +uniform vec2 targetSize; + +uniform float blend; + +out vec4 o_color; + +float getRot(vec2 pos, vec2 b) { + vec2 Res = textureSize(tex0, 0); + vec2 p = b; + float rot = 0.0; + for (int i = 0; i < RotNum; i++) { + rot += dot(texture(tex0, fract((pos + p) / Res.xy)).xy -vec2(0.5), p.yx * vec2(1, -1)); + p = m * p; + } + return rot / float(RotNum)/dot(b, b); +} + +void main() { + vec2 pos = v_texCoord0 * targetSize; + vec2 Res = textureSize(tex0, 0); + + vec2 b = vec2(cos(ang * random), sin(ang * random)); + vec2 v = vec2(0); + float bbMax = 0.5 * Res.y; + bbMax *= bbMax; + for (int l = 0; l < 20; l++) { + if (dot(b, b) > bbMax) break; + vec2 p = b; + for (int i = 0; i < RotNum; i++) { + #ifdef SUPPORT_EVEN_ROTNUM + v += p.yx * getRot(pos + p, -mh * b); + #else + // this is faster but works only for odd RotNum + v += p.yx * getRot(pos + p, b); + #endif + p = m*p; + } + b *= 2.0; + } + o_color = vec4(0.0, 0.0, 0.0, 1.0); + o_color.xy = texture(tex0, fract((pos + v * vec2(-1, 1) * 2.0) / Res.xy)).xy * (1.0-blend) + v_texCoord0 * blend; +} \ No newline at end of file diff --git a/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/perturb.frag b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/perturb.frag index 49366bdc..87adcd7a 100644 --- a/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/perturb.frag +++ b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/perturb.frag @@ -15,6 +15,9 @@ uniform sampler2D tex0; uniform int xSegments; uniform int ySegments; +uniform bool outputUV; +uniform vec2 offset; + // varyings in vec2 v_texCoord0; @@ -143,7 +146,7 @@ void main() { vec3 xseed = vec3(seed.xy, seed.z+cos(phase*3.1415926535)); vec3 yseed = vec3(seed.yx, seed.z+sin(phase*3.1415926535)); - vec3 uv = vec3(v_texCoord0, 1.0) * 2.0 - 1.0; + vec3 uv = vec3(v_texCoord0 + offset, 1.0) * 2.0 - 1.0; vec3 px = ((segment(uv, xSegments, ySegments) + xseed) * scale); vec3 py = ((segment(uv, xSegments, ySegments) + yseed + vec3(100.37, 40.51, 9.43)) * scale); @@ -157,14 +160,17 @@ void main() { vec2 distCoord = v_texCoord0 + vec2(tx, ty); - if (distCoord.x >= 0.0 && distCoord.y >= 0.0 && distCoord.x < 1.0 && distCoord.y < 1.0) { - - if (xSegments == 0 && ySegments == 0) { - o_output = texture(tex0, distCoord); + if (!outputUV) { + if (distCoord.x >= 0.0 && distCoord.y >= 0.0 && distCoord.x < 1.0 && distCoord.y < 1.0) { + if (xSegments == 0 && ySegments == 0) { + o_output = texture(tex0, distCoord); + } else { + o_output = textureLod(tex0, distCoord, 0.0); + } } else { - o_output = textureLod(tex0, distCoord, 0.0); + o_output = vec4(0.0); } } else { - o_output = vec4(0.0); + o_output = vec4(distCoord, 0.0, 1.0); } } diff --git a/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/uvmap.frag b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/uvmap.frag new file mode 100644 index 00000000..422c4b79 --- /dev/null +++ b/orx-fx/src/main/resources/org/openrndr/extra/fx/gl3/distort/uvmap.frag @@ -0,0 +1,11 @@ +#version 330 core + +in vec2 v_texCoord0; +uniform sampler2D tex0;// uvmap +uniform sampler2D tex1;// input +out vec4 o_color; + +void main() { + vec2 uv = texture(tex0, v_texCoord0).xy; + o_color = texture(tex1, uv); +} diff --git a/orx-gui/build.gradle b/orx-gui/build.gradle index eab77f99..1c306462 100644 --- a/orx-gui/build.gradle +++ b/orx-gui/build.gradle @@ -15,6 +15,7 @@ dependencies { implementation "com.google.code.gson:gson:$gsonVersion" implementation "org.jetbrains.kotlin:kotlin-reflect:$kotlinVersion" demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") demoImplementation(sourceSets.getByName("main").output) diff --git a/orx-gui/src/demo/kotlin/DemoOptions01.kt b/orx-gui/src/demo/kotlin/DemoOptions01.kt index 4dfa594e..c72cfff4 100644 --- a/orx-gui/src/demo/kotlin/DemoOptions01.kt +++ b/orx-gui/src/demo/kotlin/DemoOptions01.kt @@ -1,5 +1,6 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.gui.GUI import org.openrndr.extra.parameters.* import org.openrndr.math.Vector2 @@ -23,6 +24,11 @@ fun main() = application { } gui.add(settings) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend(gui) extend { when(settings.option) { diff --git a/orx-gui/src/demo/kotlin/DemoSimple01.kt b/orx-gui/src/demo/kotlin/DemoSimple01.kt index 44636bce..c944059a 100644 --- a/orx-gui/src/demo/kotlin/DemoSimple01.kt +++ b/orx-gui/src/demo/kotlin/DemoSimple01.kt @@ -1,5 +1,6 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.gui.GUI import org.openrndr.extra.parameters.* import org.openrndr.math.Vector2 @@ -22,10 +23,13 @@ fun main() = application { @DoubleListParameter("a double list") var adl = MutableList(2) { 0.0 } - } - gui.add(settings) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend(gui) extend { drawer.fill = settings.color diff --git a/orx-jumpflood/build.gradle b/orx-jumpflood/build.gradle index be8b867e..51e89a48 100644 --- a/orx-jumpflood/build.gradle +++ b/orx-jumpflood/build.gradle @@ -11,7 +11,11 @@ sourceSets { dependencies { implementation project(":orx-fx") demoImplementation project(":orx-noise") + demoImplementation project(":orx-gui") demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-svg:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-ffmpeg:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") demoImplementation(sourceSets.getByName("main").output) diff --git a/orx-jumpflood/src/demo/kotlin/DemoShapeSDF01.kt b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF01.kt new file mode 100644 index 00000000..cb47435a --- /dev/null +++ b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF01.kt @@ -0,0 +1,42 @@ +import org.openrndr.application +import org.openrndr.draw.ColorFormat +import org.openrndr.draw.ColorType +import org.openrndr.draw.colorBuffer +import org.openrndr.extensions.SingleScreenshot +import org.openrndr.extra.jumpfill.ShapeSDF +import org.openrndr.math.Vector3 +import org.openrndr.math.transforms.transform +import org.openrndr.shape.Circle +import org.openrndr.svg.loadSVG + +fun main() { + application { + configure { + width = 1280 + height = 720 + } + program { + val sdf = ShapeSDF() + val df = colorBuffer(width, height, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + + val shapes = loadSVG("orx-jumpflood/src/demo/resources/name.svg").findShapes().map { it.shape } + + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend { + sdf.setShapes(shapes.mapIndexed { index, it -> + it.transform(transform { + translate(1280/2.0, 720.0/2) + + translate(-1280/2.0, -720.0/2.0) + }) + }) + sdf.apply(emptyArray(), df) + drawer.image(df) + } + } + } +} \ No newline at end of file diff --git a/orx-jumpflood/src/demo/kotlin/DemoShapeSDF02.kt b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF02.kt new file mode 100644 index 00000000..4aac9990 --- /dev/null +++ b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF02.kt @@ -0,0 +1,70 @@ +import org.openrndr.application +import org.openrndr.color.ColorRGBa +import org.openrndr.draw.ColorFormat +import org.openrndr.draw.ColorType +import org.openrndr.draw.colorBuffer +import org.openrndr.extensions.SingleScreenshot +import org.openrndr.extra.jumpfill.ShapeSDF +import org.openrndr.extra.jumpfill.draw.SDFStrokeFill +import org.openrndr.extra.jumpfill.ops.* +import org.openrndr.math.Vector3 +import org.openrndr.math.transforms.transform +import org.openrndr.svg.loadSVG + +fun main() { + application { + configure { + width = 1280 + height = 720 + } + program { + val sdf0 = ShapeSDF() + val df0 = colorBuffer(width, height, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + + val sdf1 = ShapeSDF() + val df1 = colorBuffer(width, height, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + + val shapes = loadSVG("orx-jumpflood/src/demo/resources/name.svg").findShapes().map { it.shape } + + val union = SDFSmoothIntersection() + val onion = SDFOnion() + + + val strokeFill = SDFStrokeFill() + + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend { + drawer.background(ColorRGBa.PINK) + + sdf0.setShapes(shapes.mapIndexed { index, it -> + it.transform(transform { + translate(1280 / 2.0, 720.0 / 2) + translate(-1280 / 2.0, -720.0 / 2.0) + }) + }) + + sdf1.setShapes(shapes.mapIndexed { index, it -> + it.transform(transform { + translate(1280 / 2.0, 720.0 / 2) + rotate(Vector3.Companion.UNIT_Z, seconds * 45.0) + translate(-1280 / 2.0, -720.0 / 2.0) + }) + }) + + sdf0.apply(emptyArray(), df0) + sdf1.apply(emptyArray(), df1) + union.radius = mouse.position.y + union.apply(arrayOf(df0, df1), df0) + onion.radius = 20.0 + onion.apply(df0, df0) + strokeFill.strokeWeight = 2.0 + strokeFill.apply(df0, df0); + drawer.image(df0) + } + } + } +} \ No newline at end of file diff --git a/orx-jumpflood/src/demo/kotlin/DemoShapeSDF03.kt b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF03.kt new file mode 100644 index 00000000..9c0ae17f --- /dev/null +++ b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF03.kt @@ -0,0 +1,74 @@ +import org.openrndr.application +import org.openrndr.color.ColorRGBa +import org.openrndr.draw.ColorFormat +import org.openrndr.draw.ColorType +import org.openrndr.draw.colorBuffer +import org.openrndr.extensions.SingleScreenshot +import org.openrndr.extra.fx.distort.FluidDistort +import org.openrndr.extra.jumpfill.ShapeSDF +import org.openrndr.extra.jumpfill.draw.SDFStrokeFill +import org.openrndr.extra.jumpfill.ops.* +import org.openrndr.ffmpeg.ScreenRecorder +import org.openrndr.math.Vector3 +import org.openrndr.math.transforms.transform +import org.openrndr.svg.loadSVG + +fun main() { + application { + configure { + width = 1280 + height = 720 + } + program { + val sdf0 = ShapeSDF() + val sdf1 = ShapeSDF() + val df0 = colorBuffer(width, height, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + val df1 = colorBuffer(width, height, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + + val fd = FluidDistort() + fd.outputUV = true + + val uvmap = colorBuffer(width, height, type = ColorType.FLOAT16) + + val shapes = loadSVG("orx-jumpflood/src/demo/resources/name.svg").findShapes().map { it.shape } + val union = SDFSmoothDifference() + + val strokeFill = SDFStrokeFill() + + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend { + + drawer.background(ColorRGBa.PINK) + + fd.apply(emptyArray(), uvmap) + + sdf0.setShapes(shapes.mapIndexed { index, it -> + it.transform(transform { + translate(1280 / 2.0, 720.0 / 2) + translate(-1280 / 2.0, -720.0 / 2.0) + }) + }) + sdf1.setShapes(shapes.mapIndexed { index, it -> + it.transform(transform { + translate(1280 / 2.0, 720.0 / 2) + translate(-1280 / 2.0, -720.0 / 2.0) + }) + }) + + sdf0.useUV = true + sdf0.apply(uvmap, df0) + sdf1.apply(uvmap, df1) + union.radius = 10.0 + union.apply(arrayOf(df0, df1), df0) + + strokeFill.strokeWeight = 10.0 + strokeFill.apply(df0, df0); + drawer.image(df0) + } + } + } +} \ No newline at end of file diff --git a/orx-jumpflood/src/demo/kotlin/DemoShapeSDF04.kt b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF04.kt new file mode 100644 index 00000000..5f106b00 --- /dev/null +++ b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF04.kt @@ -0,0 +1,80 @@ +package sketches + +import org.openrndr.application +import org.openrndr.color.ColorRGBa +import org.openrndr.draw.ColorFormat +import org.openrndr.draw.ColorType +import org.openrndr.draw.colorBuffer +import org.openrndr.extensions.SingleScreenshot +import org.openrndr.extra.fx.distort.Perturb +import org.openrndr.extra.gui.GUI +import org.openrndr.extra.jumpfill.ShapeSDF +import org.openrndr.extra.jumpfill.draw.SDFStrokeFill +import org.openrndr.extra.jumpfill.ops.* +import org.openrndr.math.transforms.transform +import org.openrndr.shape.Circle +import org.openrndr.svg.loadSVG + +fun main() { + application { + configure { + width = 1280 + height = 720 + } + program { + val gui = GUI() + val sdf0 = ShapeSDF() + val sdf1 = ShapeSDF() + val df0 = colorBuffer(width, height, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + val df1 = colorBuffer(width, height, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + + val perturb = Perturb() + perturb.outputUV = true + + val uvmap = colorBuffer(width, height, type = ColorType.FLOAT16) + + val circleShapes = List(1) { Circle(width/2.0, height/2.0, 200.0).shape} + + val shapes = loadSVG("orx-jumpflood/src/demo/resources/name.svg").findShapes().map { it.shape } + val difference = SDFSmoothDifference() + val strokeFill = SDFStrokeFill() + + gui.add(perturb) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend(gui) + extend { + drawer.background(ColorRGBa.PINK) + + perturb.phase = seconds * 0.1 + perturb.apply(uvmap, uvmap) + + sdf0.setShapes(circleShapes.mapIndexed { index, it -> + it.transform(transform { + translate(1280 / 2.0, 720.0 / 2) + translate(-1280 / 2.0, -720.0 / 2.0) + }) + }) + sdf1.setShapes(shapes.mapIndexed { index, it -> + it.transform(transform { + translate(1280 / 2.0, 720.0 / 2) + translate(-1280 / 2.0, -720.0 / 2.0) + }) + }) + + sdf0.useUV = true + sdf0.apply(uvmap, df0) + sdf1.apply(uvmap, df1) + difference.radius = 10.0 + difference.apply(arrayOf(df0, df1), df0) + + strokeFill.strokeWeight = 10.0 + strokeFill.apply(df0, df0); + drawer.image(df0) + } + } + } +} \ No newline at end of file diff --git a/orx-jumpflood/src/demo/kotlin/DemoShapeSDF05.kt b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF05.kt new file mode 100644 index 00000000..78d9f6cc --- /dev/null +++ b/orx-jumpflood/src/demo/kotlin/DemoShapeSDF05.kt @@ -0,0 +1,98 @@ +import org.openrndr.application +import org.openrndr.color.ColorRGBa +import org.openrndr.draw.ColorFormat +import org.openrndr.draw.ColorType +import org.openrndr.draw.colorBuffer +import org.openrndr.extensions.SingleScreenshot +import org.openrndr.extra.fx.distort.Perturb +import org.openrndr.extra.gui.GUI +import org.openrndr.extra.jumpfill.ShapeSDF +import org.openrndr.extra.jumpfill.draw.SDFStrokeFill +import org.openrndr.extra.jumpfill.ops.* +import org.openrndr.ffmpeg.ScreenRecorder +import org.openrndr.math.Vector2 +import org.openrndr.math.transforms.transform +import org.openrndr.shape.Circle +import org.openrndr.svg.loadSVG +import kotlin.math.cos +import kotlin.math.sin + +fun main() { + application { + configure { + width = 1280 + height = 720 + } + program { + val gui = GUI() + val sdf0 = ShapeSDF() + val sdf1 = ShapeSDF() + val df0 = colorBuffer(width, height, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + val df1 = colorBuffer(width, height, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + + val perturb = Perturb() + + perturb.outputUV = true + + val uvmap = colorBuffer(width, height, type = ColorType.FLOAT16) + val uvmap2 = colorBuffer(width, height, type = ColorType.FLOAT16) + + val circleShapes = List(1) { Circle(width/2.0, height/2.0, 200.0).shape} + + val shapes = loadSVG("orx-jumpflood/src/demo/resources/name.svg").findShapes().map { it.shape } + val difference = SDFSmoothDifference() + val strokeFill = SDFStrokeFill() + sdf0.useUV = true + gui.add(sdf0) + gui.add(perturb) + gui.add(strokeFill) + gui.add(difference) + + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + + extend(ScreenRecorder()) { + frameRate = 60 + } + extend(gui) + extend { + drawer.background(ColorRGBa.PINK) + + perturb.offset = Vector2(cos(seconds*0.2), sin(seconds*0.2)) + perturb.outputUV = true + perturb.phase = seconds * 0.1 + perturb.apply(uvmap, uvmap) + + perturb.offset = Vector2.ZERO + perturb.outputUV = false + perturb.phase = seconds * 0.05 + perturb.apply(uvmap, uvmap2) + + sdf0.setShapes(circleShapes.mapIndexed { index, it -> + it.transform(transform { + translate(1280 / 2.0, 720.0 / 2) + translate(-1280 / 2.0, -720.0 / 2.0) + }) + }) + sdf1.setShapes(shapes.mapIndexed { index, it -> + it.transform(transform { + translate(1280 / 2.0, 720.0 / 2) + translate(-1280 / 2.0, -720.0 / 2.0) + }) + }) + + + sdf0.apply(uvmap2, df0) + sdf1.apply(uvmap2, df1) + + difference.apply(arrayOf(df0, df1), df0) + + strokeFill.apply(df0, df0); + drawer.image(df0) + } + } + } +} \ No newline at end of file diff --git a/orx-jumpflood/src/demo/kotlin/DemoSkeleton01.kt b/orx-jumpflood/src/demo/kotlin/DemoSkeleton01.kt index 6fbd4394..09905840 100644 --- a/orx-jumpflood/src/demo/kotlin/DemoSkeleton01.kt +++ b/orx-jumpflood/src/demo/kotlin/DemoSkeleton01.kt @@ -1,11 +1,10 @@ -package sketches - import org.openrndr.application import org.openrndr.color.ColorRGBa import org.openrndr.draw.ColorType import org.openrndr.draw.isolatedWithTarget import org.openrndr.draw.renderTarget +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.jumpfill.fx.Skeleton import org.openrndr.extra.jumpfill.fx.StraightSkeleton import org.openrndr.extra.noise.simplex @@ -23,6 +22,11 @@ fun main() { colorBuffer() } val field = input.colorBuffer(0).createEquivalent(type = ColorType.FLOAT32) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { drawer.isolatedWithTarget(input) { // -- draw something interesting diff --git a/orx-jumpflood/src/demo/kotlin/DemoStraightSkeleton01.kt b/orx-jumpflood/src/demo/kotlin/DemoStraightSkeleton01.kt index e8b3dbef..522a7751 100644 --- a/orx-jumpflood/src/demo/kotlin/DemoStraightSkeleton01.kt +++ b/orx-jumpflood/src/demo/kotlin/DemoStraightSkeleton01.kt @@ -6,6 +6,7 @@ import org.openrndr.draw.ColorType import org.openrndr.draw.isolatedWithTarget import org.openrndr.draw.renderTarget +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.jumpfill.fx.StraightSkeleton import org.openrndr.extra.noise.simplex @@ -22,6 +23,12 @@ fun main() { colorBuffer() } val field = input.colorBuffer(0).createEquivalent(type = ColorType.FLOAT32) + + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { drawer.isolatedWithTarget(input) { // -- draw something interesting diff --git a/orx-jumpflood/src/demo/resources/name.svg b/orx-jumpflood/src/demo/resources/name.svg new file mode 100644 index 00000000..7d3f45b2 --- /dev/null +++ b/orx-jumpflood/src/demo/resources/name.svg @@ -0,0 +1,12 @@ + + + + + + + diff --git a/orx-jumpflood/src/main/kotlin/ShapeSDF.kt b/orx-jumpflood/src/main/kotlin/ShapeSDF.kt new file mode 100644 index 00000000..20d8feda --- /dev/null +++ b/orx-jumpflood/src/main/kotlin/ShapeSDF.kt @@ -0,0 +1,78 @@ +package org.openrndr.extra.jumpfill + +import org.openrndr.draw.* +import org.openrndr.extra.parameters.BooleanParameter +import org.openrndr.math.Vector4 +import org.openrndr.resourceUrl +import org.openrndr.shape.Shape +import org.openrndr.shape.ShapeContour + + +class ShapeSDF : Filter(filterShaderFromUrl(resourceUrl("/shaders/gl3/shape-sdf.frag"))) { + private val fromBuffer = bufferTexture(1024, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + private val toBuffer = bufferTexture(1024, format = ColorFormat.RGBa, type = ColorType.FLOAT32) + private var segmentCount = 0 + + @BooleanParameter("use UV map") + var useUV:Boolean by parameters + + @BooleanParameter("rectify distance") + var rectify:Boolean by parameters + + + init { + useUV = false + rectify = false + } + + fun setShapes(shapes: List) { + setContours(shapes.flatMap { it.contours }) + } + + fun setContours(contours: List) { + val from = mutableListOf() + val to = mutableListOf() + + for (contour in contours) { + val lin = contour.sampleLinear() + var contourLength = 0.0 + for (segment in lin.segments) { + contourLength += segment.length + } + var offset = 0.0 + for (segment in lin.segments) { + from.add(Vector4(segment.start.x, segment.start.y, offset, contourLength)) + offset += segment.length + to.add(Vector4(segment.end.x, segment.end.y, offset, contourLength)) + } + } + + val fromShadow = fromBuffer.shadow + val fromWriter = fromShadow.writer() + fromWriter.rewind() + for (v in from) { + fromWriter.write(v) + } + fromShadow.upload(0, from.size*4*4) + + val toShadow = toBuffer.shadow + val toWriter = toShadow.writer() + toWriter.rewind() + for (v in to) { + toWriter.write(v) + } + toShadow.upload(0, to.size*4*4) + + segmentCount = from.size + } + + override fun apply(source: Array, target: Array) { + require(target[0].type == ColorType.FLOAT16 || target[0].type == ColorType.FLOAT32) { + "needs a floating point target" + } + parameters["fromBuffer"] = fromBuffer + parameters["toBuffer"] = toBuffer + parameters["segmentCount"] = segmentCount + super.apply(source, target) + } +} \ No newline at end of file diff --git a/orx-jumpflood/src/main/kotlin/draw/SDFDraw.kt b/orx-jumpflood/src/main/kotlin/draw/SDFDraw.kt new file mode 100644 index 00000000..55ba9f6d --- /dev/null +++ b/orx-jumpflood/src/main/kotlin/draw/SDFDraw.kt @@ -0,0 +1,41 @@ +package org.openrndr.extra.jumpfill.draw + +import org.openrndr.color.ColorRGBa +import org.openrndr.draw.ColorBuffer +import org.openrndr.draw.Filter +import org.openrndr.draw.filterShaderFromUrl +import org.openrndr.extra.parameters.ColorParameter +import org.openrndr.extra.parameters.Description +import org.openrndr.extra.parameters.DoubleParameter +import org.openrndr.resourceUrl + +@Description("SDF stroke and fill") +class SDFStrokeFill : Filter(filterShaderFromUrl(resourceUrl("/shaders/gl3/draw/sdf-stroke-fill.frag"))) { + @DoubleParameter("stroke weight", 0.0, 20.0, order = 0) + var strokeWeight: Double by parameters + + @DoubleParameter("stroke feather", 0.0, 20.0, order = 0) + var strokeFeather: Double by parameters + + @ColorParameter("stroke color", order = 1) + var strokeColor: ColorRGBa by parameters + + @DoubleParameter("fill feather", 0.0, 20.0, order = 0) + var fillFeather: Double by parameters + + + @ColorParameter("fill color", order = 2) + var fillColor: ColorRGBa by parameters + init { + fillFeather = 1.0 + strokeFeather = 1.0 + strokeWeight = 1.0 + strokeColor = ColorRGBa.BLACK + fillColor = ColorRGBa.WHITE + + } + + override fun apply(source: Array, target: Array) { + super.apply(source, target) + } +} diff --git a/orx-jumpflood/src/main/kotlin/ops/SDFOps.kt b/orx-jumpflood/src/main/kotlin/ops/SDFOps.kt new file mode 100644 index 00000000..6878a6d8 --- /dev/null +++ b/orx-jumpflood/src/main/kotlin/ops/SDFOps.kt @@ -0,0 +1,86 @@ +package org.openrndr.extra.jumpfill.ops + +import org.openrndr.draw.ColorBuffer +import org.openrndr.draw.ColorType +import org.openrndr.draw.Filter +import org.openrndr.draw.filterShaderFromUrl +import org.openrndr.extra.parameters.Description +import org.openrndr.extra.parameters.DoubleParameter +import org.openrndr.resourceUrl + +class SDFSmoothUnion : Filter(filterShaderFromUrl(resourceUrl("/shaders/gl3/ops/sdf-smooth-union.frag"))) { + var radius: Double by parameters + + init { + radius = 0.0 + } + + override fun apply(source: Array, target: Array) { + require(target[0].type == ColorType.FLOAT16 || target[0].type == ColorType.FLOAT32) { + "needs a floating point target" + } + super.apply(source, target) + } +} + +class SDFSmoothIntersection : Filter(filterShaderFromUrl(resourceUrl("/shaders/gl3/ops/sdf-smooth-intersection.frag"))) { + var radius: Double by parameters + + init { + radius = 0.0 + } + + override fun apply(source: Array, target: Array) { + require(target[0].type == ColorType.FLOAT16 || target[0].type == ColorType.FLOAT32) { + "needs a floating point target" + } + super.apply(source, target) + } +} +@Description("SDF smooth difference") +class SDFSmoothDifference : Filter(filterShaderFromUrl(resourceUrl("/shaders/gl3/ops/sdf-smooth-difference.frag"))) { + @DoubleParameter("smooth radius", 0.0, 200.0, order = 0) + var radius: Double by parameters + + init { + radius = 0.0 + } + + override fun apply(source: Array, target: Array) { + require(target[0].type == ColorType.FLOAT16 || target[0].type == ColorType.FLOAT32) { + "needs a floating point target" + } + super.apply(source, target) + } +} + +class SDFRound : Filter(filterShaderFromUrl(resourceUrl("/shaders/gl3/ops/sdf-round.frag"))) { + @DoubleParameter("rounding radius", 0.0, 200.0, order = 0) + var radius: Double by parameters + + init { + radius = 0.0 + } + + override fun apply(source: Array, target: Array) { + require(target[0].type == ColorType.FLOAT16 || target[0].type == ColorType.FLOAT32) { + "needs a floating point target" + } + super.apply(source, target) + } +} + +class SDFOnion : Filter(filterShaderFromUrl(resourceUrl("/shaders/gl3/ops/sdf-onion.frag"))) { + var radius: Double by parameters + + init { + radius = 0.0 + } + + override fun apply(source: Array, target: Array) { + require(target[0].type == ColorType.FLOAT16 || target[0].type == ColorType.FLOAT32) { + "needs a floating point target" + } + super.apply(source, target) + } +} diff --git a/orx-jumpflood/src/main/resources/shaders/gl3/draw/sdf-stroke-fill.frag b/orx-jumpflood/src/main/resources/shaders/gl3/draw/sdf-stroke-fill.frag new file mode 100644 index 00000000..ac50164e --- /dev/null +++ b/orx-jumpflood/src/main/resources/shaders/gl3/draw/sdf-stroke-fill.frag @@ -0,0 +1,24 @@ +#version 330 core + +uniform sampler2D tex0;// signed distance +uniform float radius; + +uniform vec4 strokeColor; +uniform float strokeWeight; +uniform float strokeFeather; + +uniform float fillFeather; +uniform vec4 fillColor; + +in vec2 v_texCoord0; +out vec4 o_color; + +void main() { + float d = texture(tex0, v_texCoord0).r; + float strokeFactor = smoothstep(strokeWeight + strokeFeather, strokeWeight, abs(d)); + float fillFactor = smoothstep(0.0, fillFeather, -d); + + vec4 fc = (fillColor * fillColor.a) * fillFactor; + fc = fc * (1.0 - strokeFactor) + strokeFactor * (strokeColor * strokeColor.a); + o_color = fc; +} \ No newline at end of file diff --git a/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-onion.frag b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-onion.frag new file mode 100644 index 00000000..9bd8f0f5 --- /dev/null +++ b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-onion.frag @@ -0,0 +1,12 @@ +#version 330 core + +uniform sampler2D tex0;// signed distance +uniform float radius; + +in vec2 v_texCoord0; +out vec4 o_color; + +void main() { + float d0 = texture(tex0, v_texCoord0).r; + o_color = vec4(abs(d0)- radius, 0.0, 0.0, 1.0); +} \ No newline at end of file diff --git a/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-round.frag b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-round.frag new file mode 100644 index 00000000..7fd5ae75 --- /dev/null +++ b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-round.frag @@ -0,0 +1,12 @@ +#version 330 core + +uniform sampler2D tex0; // signed distance +uniform float radius; + +in vec2 v_texCoord0; +out vec4 o_color; + +void main() { + float d0 = texture(tex0, v_texCoord0).r - radius; + o_color = vec4(d0, 0.0, 0.0, 1.0); +} \ No newline at end of file diff --git a/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-difference.frag b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-difference.frag new file mode 100644 index 00000000..bf898021 --- /dev/null +++ b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-difference.frag @@ -0,0 +1,19 @@ +#version 330 core + +uniform sampler2D tex0;// signed distance +uniform sampler2D tex1;// signed distance +uniform float radius; + +in vec2 v_texCoord0; +out vec4 o_color; + +float opSmoothDifference( float d1, float d2, float k ) { + float h = clamp( 0.5 - 0.5*(d2+d1)/k, 0.0, 1.0 ); + return mix( d2, -d1, h ) + k*h*(1.0-h); } + + +void main() { + float d0 = texture(tex0, v_texCoord0).r; + float d1 = texture(tex1, v_texCoord0).r; + o_color = vec4(opSmoothDifference(d0, d1, radius), 0.0, 0.0, 1.0); +} \ No newline at end of file diff --git a/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-intersection.frag b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-intersection.frag new file mode 100644 index 00000000..bc402b93 --- /dev/null +++ b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-intersection.frag @@ -0,0 +1,19 @@ +#version 330 core + +uniform sampler2D tex0;// signed distance +uniform sampler2D tex1;// signed distance +uniform float radius; + +in vec2 v_texCoord0; +out vec4 o_color; + +float opSmoothIntersection(float d1, float d2, float k) { + float h = clamp(0.5 - 0.5*(d2-d1)/k, 0.0, 1.0); + return mix(d2, d1, h) + k*h*(1.0-h); } + + +void main() { + float d0 = texture(tex0, v_texCoord0).r; + float d1 = texture(tex1, v_texCoord0).r; + o_color = vec4(opSmoothIntersection(d0, d1, radius), 0.0, 0.0, 1.0); +} \ No newline at end of file diff --git a/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-union.frag b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-union.frag new file mode 100644 index 00000000..00dae6b3 --- /dev/null +++ b/orx-jumpflood/src/main/resources/shaders/gl3/ops/sdf-smooth-union.frag @@ -0,0 +1,19 @@ +#version 330 core + +uniform sampler2D tex0; // signed distance +uniform sampler2D tex1; // signed distance +uniform float radius; + +in vec2 v_texCoord0; +out vec4 o_color; + +float opSmoothUnion(float d1, float d2, float k) { + float h = clamp(0.5 + 0.5*(d2-d1)/k, 0.0, 1.0); + return mix(d2, d1, h) - k*h*(1.0-h); +} + +void main() { + float d0 = texture(tex0, v_texCoord0).r; + float d1 = texture(tex1, v_texCoord0).r; + o_color = vec4(opSmoothUnion(d0, d1, radius), 0.0, 0.0, 1.0); +} \ No newline at end of file diff --git a/orx-jumpflood/src/main/resources/shaders/gl3/shape-sdf.frag b/orx-jumpflood/src/main/resources/shaders/gl3/shape-sdf.frag new file mode 100644 index 00000000..572099a2 --- /dev/null +++ b/orx-jumpflood/src/main/resources/shaders/gl3/shape-sdf.frag @@ -0,0 +1,103 @@ +#version 330 +#extension GL_ARB_derivative_control : enable +in vec2 v_texCoord0; +uniform float iTime; +out vec4 o_color; + +uniform bool useUV; +uniform bool rectify; + +uniform samplerBuffer toBuffer; +uniform samplerBuffer fromBuffer; +uniform int segmentCount; +uniform vec2 targetSize; + +uniform sampler2D tex0; // uv-map + +float isLeft( vec2 P0, vec2 P1, vec2 P2 ) { + return ( (P1.x - P0.x) * (P2.y - P0.y) + - (P2.x - P0.x) * (P1.y - P0.y) ); +} + +float length_squared( vec2 v, vec2 w ) { + return dot(w-v, w-v); +} + +int winding_number( vec2 v, vec2 w, vec2 p ) { + if (v.y <= p.y) { // start y <= P.y + if (w.y > p.y) // an upward crossing + if (isLeft( v, w, p) > 0.0) // P left of edge + return 1; // ++wn; // have a valid up intersect + } + else { // start y > P.y (no test needed) + if (w.y <= p.y) // a downward crossing + if (isLeft( v,w,p) < 0.0) // P right of edge + return -1; //--wn; // have a valid down intersect + } + return 0; +} + +float minimum_distance(vec2 v, vec2 w, vec2 p) { + // Return minimum distance between line segment vw and point p + float l2 = length_squared(v, w); // i.e. |w-v|^2 - avoid a sqrt + if (l2 == 0.0) return distance(p, v); // v == w case + // Consider the line extending the segment, parameterized as v + t (w - v). + // We find projection of point p onto the line. + // It falls where t = [(p-v) . (w-v)] / |w-v|^2 + // We clamp t from [0,1] to handle points outside the segment vw. + float t = max(0.0, min(1.0, dot(p - v, w - v) / l2)); + vec2 projection = v + t * (w - v); // Projection falls on the segment + return distance(p, projection); +} + +vec3 minimum_distance_and_perpendicular(vec4 v, vec4 w, vec2 p) { + // Return minimum distance between line segment vw and point p + float l2 = length_squared(v.xy, w.xy); // i.e. |w-v|^2 - avoid a sqrt + if (l2 == 0.0) return vec3(distance(p, v.xy), v.z, v.w); // v == w case + // Consider the line extending the segment, parameterized as v + t (w - v). + // We find projection of point p onto the line. + // It falls where t = [(p-v) . (w-v)] / |w-v|^2 + // We clamp t from [0,1] to handle points outside the segment vw. + float t = max(0.0, min(1.0, dot(p - v.xy, w.xy - v.xy) / l2)); + vec3 projection = v.xyz + t * (w.xyz - v.xyz); // Projection falls on the segment + return vec3(distance(p.xy, projection.xy), projection.z, v.w); +} + + +void main() { + vec2 uv = v_texCoord0; + + vec2 fixDistance = vec2(1.0); + + if (useUV) { + vec2 o = 0.5 / textureSize(tex0, 0); + uv = texture(tex0, v_texCoord0 + o).xy; + if (rectify) { + fixDistance = (fwidthFine(uv))*vec2(1280.0, 720.0); + } + } + + uv.y = 1.0 - uv.y; + uv *= targetSize; + + float mindist = 10E10; + float perpdist = 0.0; + float contourLength = 0.0; + int windingNr = 0; + for (int i = 0; i < segmentCount; i++) { + vec4 from = texelFetch(fromBuffer, i); + vec4 to = texelFetch(toBuffer, i); + vec3 distline_and_perp = minimum_distance_and_perpendicular(from, to, uv.xy); + windingNr += winding_number( from.xy, to.xy, uv.xy ); + float distline = distline_and_perp.x; + if (abs(distline) <= mindist) { + mindist = distline; + perpdist = distline_and_perp.y; + contourLength = distline_and_perp.z; + } + } + float signedDistance = mindist * (windingNr==0 ? 1.0 : -1.0); + + + o_color = vec4(signedDistance / length(fixDistance), perpdist/contourLength, contourLength, 1.0); +} \ No newline at end of file diff --git a/orx-keyframer/build.gradle b/orx-keyframer/build.gradle index 961e7bff..8559e014 100644 --- a/orx-keyframer/build.gradle +++ b/orx-keyframer/build.gradle @@ -39,8 +39,10 @@ dependencies { implementation("org.jetbrains.kotlin:kotlin-reflect:$kotlinVersion") demoImplementation(project(":orx-camera")) + demoImplementation(project(":orx-panel")) demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") demoImplementation(sourceSets.getByName("main").output) diff --git a/orx-keyframer/src/demo/kotlin/DemoFull01.kt b/orx-keyframer/src/demo/kotlin/DemoFull01.kt index c358dd8d..e7a1b1b1 100644 --- a/orx-keyframer/src/demo/kotlin/DemoFull01.kt +++ b/orx-keyframer/src/demo/kotlin/DemoFull01.kt @@ -1,4 +1,5 @@ import org.openrndr.application +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.keyframer.Keyframer import org.openrndr.extra.keyframer.KeyframerFormat import org.openrndr.resourceUrl @@ -13,7 +14,11 @@ fun main() = application { } val animation = Animation() animation.loadFromJson(URL(resourceUrl("/demo-full-01.json")), format = KeyframerFormat.FULL) - + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { animation(seconds) drawer.fill = animation.color diff --git a/orx-keyframer/src/demo/kotlin/DemoScrub01.kt b/orx-keyframer/src/demo/kotlin/DemoScrub01.kt index 9f2c5204..6c96a088 100644 --- a/orx-keyframer/src/demo/kotlin/DemoScrub01.kt +++ b/orx-keyframer/src/demo/kotlin/DemoScrub01.kt @@ -1,4 +1,5 @@ import org.openrndr.application +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.keyframer.Keyframer import org.openrndr.panel.controlManager import org.openrndr.panel.elements.Range @@ -29,8 +30,12 @@ fun main() = application { } } } + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend(cm) - class Animation: Keyframer() { val position by Vector2Channel(arrayOf("x", "y")) } diff --git a/orx-keyframer/src/demo/kotlin/DemoSimple01.kt b/orx-keyframer/src/demo/kotlin/DemoSimple01.kt index 42674697..79a78205 100644 --- a/orx-keyframer/src/demo/kotlin/DemoSimple01.kt +++ b/orx-keyframer/src/demo/kotlin/DemoSimple01.kt @@ -1,4 +1,5 @@ import org.openrndr.application +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.keyframer.Keyframer import org.openrndr.resourceUrl import java.net.URL @@ -10,7 +11,11 @@ fun main() = application { } val animation = Animation() animation.loadFromJson(URL(resourceUrl("/demo-simple-01.json"))) - + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { animation(seconds) drawer.circle(animation.position, 100.0) diff --git a/orx-keyframer/src/demo/kotlin/DemoSimple02.kt b/orx-keyframer/src/demo/kotlin/DemoSimple02.kt index 65048b4a..6032fd61 100644 --- a/orx-keyframer/src/demo/kotlin/DemoSimple02.kt +++ b/orx-keyframer/src/demo/kotlin/DemoSimple02.kt @@ -1,4 +1,5 @@ import org.openrndr.application +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.keyframer.Keyframer import org.openrndr.resourceUrl import java.net.URL @@ -12,6 +13,11 @@ fun main() = application { } val animation = Animation() animation.loadFromJson(URL(resourceUrl("/demo-simple-02.json"))) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { animation(seconds) drawer.fill = animation.color diff --git a/orx-keyframer/src/demo/kotlin/DemoSimpleExpressions01.kt b/orx-keyframer/src/demo/kotlin/DemoSimpleExpressions01.kt index b936eafd..605b2dd9 100644 --- a/orx-keyframer/src/demo/kotlin/DemoSimpleExpressions01.kt +++ b/orx-keyframer/src/demo/kotlin/DemoSimpleExpressions01.kt @@ -1,4 +1,5 @@ import org.openrndr.application +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.keyframer.Keyframer import org.openrndr.resourceUrl import java.net.URL @@ -13,7 +14,11 @@ fun main() = application { val animation = Animation() animation.loadFromJson(URL(resourceUrl("/demo-simple-expressions-01.json")), parameters = mapOf("cycleDuration" to 2.0)) - + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { animation(seconds) drawer.circle(animation.position, animation.radius) diff --git a/orx-keyframer/src/demo/kotlin/DemoSimpleRepetitions01.kt b/orx-keyframer/src/demo/kotlin/DemoSimpleRepetitions01.kt index e1295cf3..df6319dc 100644 --- a/orx-keyframer/src/demo/kotlin/DemoSimpleRepetitions01.kt +++ b/orx-keyframer/src/demo/kotlin/DemoSimpleRepetitions01.kt @@ -1,4 +1,5 @@ import org.openrndr.application +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.keyframer.Keyframer import org.openrndr.resourceUrl import java.net.URL @@ -11,7 +12,11 @@ fun main() = application { } val animation = Animation() animation.loadFromJson(URL(resourceUrl("/demo-simple-repetitions-01.json"))) - + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { animation(seconds) drawer.circle(animation.position, animation.radius) diff --git a/orx-mesh-generators/build.gradle b/orx-mesh-generators/build.gradle index 6e7d4be1..91e63483 100644 --- a/orx-mesh-generators/build.gradle +++ b/orx-mesh-generators/build.gradle @@ -11,6 +11,7 @@ sourceSets { dependencies { demoImplementation(project(":orx-camera")) demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") diff --git a/orx-mesh-generators/src/demo/kotlin/DemoBox.kt b/orx-mesh-generators/src/demo/kotlin/DemoBox.kt index 63689924..853a57ae 100644 --- a/orx-mesh-generators/src/demo/kotlin/DemoBox.kt +++ b/orx-mesh-generators/src/demo/kotlin/DemoBox.kt @@ -3,8 +3,10 @@ import org.openrndr.color.ColorRGBa import org.openrndr.draw.DrawPrimitive import org.openrndr.draw.colorBuffer import org.openrndr.draw.shadeStyle +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extras.camera.Orbital import org.openrndr.extras.meshgenerators.boxMesh +import org.openrndr.math.Vector3 fun main() { application { @@ -18,8 +20,14 @@ fun main() { } } s.upload() - - extend(Orbital()) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend(Orbital()) { + eye = Vector3(1.0, 1.0, 1.0) + } extend { drawer.background(ColorRGBa.PINK) drawer.shadeStyle = shadeStyle { diff --git a/orx-mesh-generators/src/demo/kotlin/DemoComplex01.kt b/orx-mesh-generators/src/demo/kotlin/DemoComplex01.kt index 72f671ec..522dd2ac 100644 --- a/orx-mesh-generators/src/demo/kotlin/DemoComplex01.kt +++ b/orx-mesh-generators/src/demo/kotlin/DemoComplex01.kt @@ -1,17 +1,18 @@ import org.openrndr.application import org.openrndr.draw.DrawPrimitive import org.openrndr.draw.shadeStyle +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extras.camera.Orbital import org.openrndr.extras.meshgenerators.box import org.openrndr.extras.meshgenerators.group import org.openrndr.extras.meshgenerators.meshGenerator import org.openrndr.extras.meshgenerators.sphere +import org.openrndr.math.Vector3 import org.openrndr.math.transforms.transform fun main() { application { program { - extend(Orbital()) val m = meshGenerator { sphere(32, 32, 1.0) group { @@ -21,6 +22,16 @@ fun main() { }) } } + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend(Orbital()) { + this.eye = Vector3(0.0, 3.0, 7.0) + this.lookAt = Vector3(0.0, 2.0, 0.0) + } + extend { drawer.shadeStyle = shadeStyle { fragmentTransform = """ diff --git a/orx-mesh-generators/src/demo/kotlin/DemoComplex02.kt b/orx-mesh-generators/src/demo/kotlin/DemoComplex02.kt index 8de50432..286a3aed 100644 --- a/orx-mesh-generators/src/demo/kotlin/DemoComplex02.kt +++ b/orx-mesh-generators/src/demo/kotlin/DemoComplex02.kt @@ -1,6 +1,7 @@ import org.openrndr.application import org.openrndr.draw.DrawPrimitive import org.openrndr.draw.shadeStyle +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extras.camera.Orbital import org.openrndr.extras.meshgenerators.* import org.openrndr.math.Vector3 @@ -9,7 +10,15 @@ import org.openrndr.math.transforms.transform fun main() { application { program { - extend(Orbital()) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend(Orbital()) { + this.eye = Vector3(0.0, 10.0, 20.0) + this.lookAt = Vector3(0.0, 5.0, 0.0) + } val m = meshGenerator { group { hemisphere(32, 16, 5.0) diff --git a/orx-mesh-generators/src/demo/kotlin/DemoComplex03.kt b/orx-mesh-generators/src/demo/kotlin/DemoComplex03.kt index ba97369c..3cb5190a 100644 --- a/orx-mesh-generators/src/demo/kotlin/DemoComplex03.kt +++ b/orx-mesh-generators/src/demo/kotlin/DemoComplex03.kt @@ -1,6 +1,7 @@ import org.openrndr.application import org.openrndr.draw.DrawPrimitive import org.openrndr.draw.shadeStyle +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extras.camera.Orbital import org.openrndr.extras.meshgenerators.* import org.openrndr.math.Vector3 @@ -9,7 +10,15 @@ import org.openrndr.math.transforms.transform fun main() { application { program { - extend(Orbital()) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend(Orbital()) { + this.eye = Vector3(0.0, 10.0, 20.0) + this.lookAt = Vector3(0.0, 5.0, 0.0) + } val m = meshGenerator { group { hemisphere(32, 16, 5.0) diff --git a/orx-mesh-generators/src/demo/kotlin/DemoComplex04.kt b/orx-mesh-generators/src/demo/kotlin/DemoComplex04.kt index ed0f344c..1fd58968 100644 --- a/orx-mesh-generators/src/demo/kotlin/DemoComplex04.kt +++ b/orx-mesh-generators/src/demo/kotlin/DemoComplex04.kt @@ -1,6 +1,7 @@ import org.openrndr.application import org.openrndr.draw.DrawPrimitive import org.openrndr.draw.shadeStyle +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extras.camera.Orbital import org.openrndr.extras.meshgenerators.* import org.openrndr.math.Vector2 @@ -10,7 +11,16 @@ import org.openrndr.math.transforms.transform fun main() { application { program { - extend(Orbital()) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + + extend(Orbital()) { + this.eye = Vector3(0.0, 15.0, 15.0) + } + val m = meshGenerator { val sides = 12 group { diff --git a/orx-mesh-generators/src/demo/kotlin/DemoComplex05.kt b/orx-mesh-generators/src/demo/kotlin/DemoComplex05.kt index 4603043c..12ac9336 100644 --- a/orx-mesh-generators/src/demo/kotlin/DemoComplex05.kt +++ b/orx-mesh-generators/src/demo/kotlin/DemoComplex05.kt @@ -1,6 +1,7 @@ import org.openrndr.application import org.openrndr.draw.DrawPrimitive import org.openrndr.draw.shadeStyle +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extras.camera.Orbital import org.openrndr.extras.meshgenerators.* import org.openrndr.math.Vector2 @@ -11,7 +12,14 @@ import org.openrndr.shape.Circle fun main() { application { program { - extend(Orbital()) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } + extend(Orbital()) { + this.eye = Vector3(0.0, 30.0, 50.0) + } val m = meshGenerator { grid(5,5, 5) { u, v, w -> diff --git a/orx-mesh-generators/src/demo/kotlin/DemoComplex06.kt b/orx-mesh-generators/src/demo/kotlin/DemoComplex06.kt deleted file mode 100644 index d20fc55d..00000000 --- a/orx-mesh-generators/src/demo/kotlin/DemoComplex06.kt +++ /dev/null @@ -1,35 +0,0 @@ -import org.openrndr.application -import org.openrndr.draw.DrawPrimitive -import org.openrndr.draw.shadeStyle -import org.openrndr.extras.camera.Orbital -import org.openrndr.extras.meshgenerators.* -import org.openrndr.math.Vector2 -import org.openrndr.math.Vector3 -import org.openrndr.math.transforms.transform -import org.openrndr.shape.Circle - -fun main() { - application { - program { - extend(Orbital()) - val m = meshGenerator { - - grid(5,5, 5) { u, v, w -> - extrudeShape(Circle(0.0, 0.0, 50.0).shape, 4.0, scale = 0.1) - transform(transform{ translate(u*20.0, v*20.0, w * 20.0)} ) - } - twist(360.0/200.0, 0.0) - twist(360.0/200.0, 0.0, Vector3.UNIT_X) - twist(360.0/200.0, 0.0, Vector3.UNIT_Z) - } - extend { - drawer.shadeStyle = shadeStyle { - fragmentTransform = """ - x_fill.rgb *= v_viewNormal.z; - """.trimIndent() - } - drawer.vertexBuffer(m, DrawPrimitive.TRIANGLES) - } - } - } -} \ No newline at end of file diff --git a/orx-noise/build.gradle b/orx-noise/build.gradle index d3bbc651..49d7c034 100644 --- a/orx-noise/build.gradle +++ b/orx-noise/build.gradle @@ -14,6 +14,7 @@ dependencies { demoImplementation(project(":orx-camera")) demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") demoImplementation(sourceSets.getByName("main").output) diff --git a/orx-noise/src/demo/kotlin/DemoGradientPerturb2D.kt b/orx-noise/src/demo/kotlin/DemoGradientPerturb2D.kt index 85e5fe44..6a2e8848 100644 --- a/orx-noise/src/demo/kotlin/DemoGradientPerturb2D.kt +++ b/orx-noise/src/demo/kotlin/DemoGradientPerturb2D.kt @@ -1,10 +1,10 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa import org.openrndr.draw.colorBuffer +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.noise.gradientPerturbFractal import org.openrndr.extra.noise.simplex import org.openrndr.math.Vector2 -import org.openrndr.math.Vector3 import kotlin.math.absoluteValue fun main() { @@ -12,6 +12,11 @@ fun main() { program { val cb = colorBuffer(width, height) val shad = cb.shadow + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { for (y in 0 until height) { for (x in 0 until width) { diff --git a/orx-noise/src/demo/kotlin/DemoGradientPerturb3D.kt b/orx-noise/src/demo/kotlin/DemoGradientPerturb3D.kt index c707b063..a1acc55d 100644 --- a/orx-noise/src/demo/kotlin/DemoGradientPerturb3D.kt +++ b/orx-noise/src/demo/kotlin/DemoGradientPerturb3D.kt @@ -1,6 +1,7 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa import org.openrndr.draw.colorBuffer +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.noise.gradientPerturbFractal import org.openrndr.extra.noise.simplex import org.openrndr.math.Vector3 @@ -11,6 +12,11 @@ fun main() { program { val cb = colorBuffer(width, height) val shad = cb.shadow + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { for (y in 0 until height) { for (x in 0 until width) { diff --git a/orx-rabbit-control/build.gradle b/orx-rabbit-control/build.gradle index 9b865c72..f36cb09f 100644 --- a/orx-rabbit-control/build.gradle +++ b/orx-rabbit-control/build.gradle @@ -21,6 +21,7 @@ dependencies { implementation "com.google.zxing:core:3.4.0" implementation "com.google.zxing:javase:3.4.0" + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") demoImplementation(sourceSets.getByName("main").output) diff --git a/orx-rabbit-control/src/demo/kotlin/DemoRabbitControl.kt b/orx-rabbit-control/src/demo/kotlin/DemoRabbitControl.kt index db808803..78a79079 100644 --- a/orx-rabbit-control/src/demo/kotlin/DemoRabbitControl.kt +++ b/orx-rabbit-control/src/demo/kotlin/DemoRabbitControl.kt @@ -1,6 +1,7 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa import org.openrndr.draw.loadFont +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.parameters.* import org.openrndr.math.Vector2 import org.openrndr.math.Vector3 @@ -48,7 +49,11 @@ fun main() = application { } rabbit.add(settings) - + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend(rabbit) extend { drawer.background(if (settings.b) ColorRGBa.BLUE else ColorRGBa.BLACK) diff --git a/orx-rabbit-control/src/demo/kotlin/DemoRabbitControlManualOverlay.kt b/orx-rabbit-control/src/demo/kotlin/DemoRabbitControlManualOverlay.kt index 784d6940..4de1f7c4 100644 --- a/orx-rabbit-control/src/demo/kotlin/DemoRabbitControlManualOverlay.kt +++ b/orx-rabbit-control/src/demo/kotlin/DemoRabbitControlManualOverlay.kt @@ -1,6 +1,7 @@ import org.openrndr.KEY_HOME import org.openrndr.application import org.openrndr.color.ColorRGBa +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.parameters.* @@ -19,6 +20,11 @@ fun main() = application { } rabbit.add(settings) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend(rabbit) /** diff --git a/orx-shade-styles/build.gradle b/orx-shade-styles/build.gradle index 37ffbeab..8220384d 100644 --- a/orx-shade-styles/build.gradle +++ b/orx-shade-styles/build.gradle @@ -11,6 +11,7 @@ dependencies { api project(":orx-parameters") demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") demoImplementation(sourceSets.getByName("main").output) diff --git a/orx-shade-styles/src/demo/kotlin/DemoRadialGradient01.kt b/orx-shade-styles/src/demo/kotlin/DemoRadialGradient01.kt index 1beb3c01..93378268 100644 --- a/orx-shade-styles/src/demo/kotlin/DemoRadialGradient01.kt +++ b/orx-shade-styles/src/demo/kotlin/DemoRadialGradient01.kt @@ -1,5 +1,6 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.shadestyles.radialGradient import kotlin.math.cos @@ -7,6 +8,11 @@ import kotlin.math.cos fun main() { application { program { + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { drawer.shadeStyle = radialGradient( ColorRGBa.PINK, diff --git a/orx-time-operators/build.gradle b/orx-time-operators/build.gradle index d1479bb6..bfdfb261 100644 --- a/orx-time-operators/build.gradle +++ b/orx-time-operators/build.gradle @@ -13,6 +13,7 @@ dependencies { demoImplementation(project(":orx-camera")) demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") demoImplementation(sourceSets.getByName("main").output) diff --git a/orx-time-operators/src/demo/kotlin/DemoEnvelope.kt b/orx-time-operators/src/demo/kotlin/DemoEnvelope.kt index fd11abe2..37b16187 100644 --- a/orx-time-operators/src/demo/kotlin/DemoEnvelope.kt +++ b/orx-time-operators/src/demo/kotlin/DemoEnvelope.kt @@ -1,6 +1,7 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa import org.openrndr.draw.isolated +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.timeoperators.Envelope import org.openrndr.extra.timeoperators.TimeOperators @@ -10,6 +11,11 @@ fun main() { val size = Envelope(50.0, 400.0, 0.5, 0.5) val rotation = Envelope(easingFactor = 0.4) + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend(TimeOperators()) { track(size, rotation) } diff --git a/orx-time-operators/src/demo/kotlin/DemoLFO.kt b/orx-time-operators/src/demo/kotlin/DemoLFO.kt index b6146fad..ce06202b 100644 --- a/orx-time-operators/src/demo/kotlin/DemoLFO.kt +++ b/orx-time-operators/src/demo/kotlin/DemoLFO.kt @@ -1,6 +1,7 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa import org.openrndr.draw.isolated +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.timeoperators.Envelope import org.openrndr.extra.timeoperators.LFO import org.openrndr.extra.timeoperators.LFOWave @@ -11,7 +12,11 @@ fun main() { program { val size = LFO() val rotation = LFO(LFOWave.SINE) - + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend(TimeOperators()) { track(size, rotation) } diff --git a/orx-timer/build.gradle b/orx-timer/build.gradle index 49bda9c8..dec3965b 100644 --- a/orx-timer/build.gradle +++ b/orx-timer/build.gradle @@ -10,6 +10,7 @@ sourceSets { dependencies { demoImplementation("org.openrndr:openrndr-core:$openrndrVersion") + demoImplementation("org.openrndr:openrndr-extensions:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3:$openrndrVersion") demoRuntimeOnly("org.openrndr:openrndr-gl3-natives-$openrndrOS:$openrndrVersion") demoImplementation(sourceSets.getByName("main").output) diff --git a/orx-timer/src/demo/kotlin/DemoRepeat01.kt b/orx-timer/src/demo/kotlin/DemoRepeat01.kt index f3ed5106..286a4d4d 100644 --- a/orx-timer/src/demo/kotlin/DemoRepeat01.kt +++ b/orx-timer/src/demo/kotlin/DemoRepeat01.kt @@ -1,4 +1,5 @@ import org.openrndr.application +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.timer.repeat fun main() = application { @@ -6,6 +7,11 @@ fun main() = application { repeat(2.0) { println("hello there $seconds" ) } + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { } diff --git a/orx-timer/src/demo/kotlin/DemoRepeat02.kt b/orx-timer/src/demo/kotlin/DemoRepeat02.kt index e5e310c1..9fa784a3 100644 --- a/orx-timer/src/demo/kotlin/DemoRepeat02.kt +++ b/orx-timer/src/demo/kotlin/DemoRepeat02.kt @@ -1,6 +1,7 @@ import org.openrndr.application import org.openrndr.color.ColorRGBa import org.openrndr.events.Event +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.timer.repeat /** @@ -17,6 +18,11 @@ fun main() = application { // -- we can not draw here, so we relay the repeat signal to the event event.trigger(null) } + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } extend { drawer.background(ColorRGBa.PINK) // -- by explicitly calling deliver we know that the drawing code in the listener will be diff --git a/orx-timer/src/demo/kotlin/DemoTimeOut01.kt b/orx-timer/src/demo/kotlin/DemoTimeOut01.kt index 3fd0296d..cb641a7c 100644 --- a/orx-timer/src/demo/kotlin/DemoTimeOut01.kt +++ b/orx-timer/src/demo/kotlin/DemoTimeOut01.kt @@ -1,8 +1,14 @@ import org.openrndr.application +import org.openrndr.extensions.SingleScreenshot import org.openrndr.extra.timer.timeOut fun main() = application { program { + if (System.getProperty("takeScreenshot") == "true") { + extend(SingleScreenshot()) { + this.outputFile = System.getProperty("screenshotPath") + } + } timeOut(2.0) { println("hello there $seconds" ) }