From 8cbe93d74da8e0c07fa197dddef63629b3a7a8cb Mon Sep 17 00:00:00 2001
From: Noelle Calliope <1581674+mekanoe@users.noreply.github.com>
Date: Sun, 1 Oct 2023 17:56:34 -0400
Subject: [PATCH] add 002
---
README.md | 3 ++
generators/README.md.txt | 2 +
generators/generate.ts | 8 +++-
html/002-rainbow-trinity.html | 31 +++++++++++++++
html/002-rainbow-trinity.js | 74 +++++++++++++++++++++++++++++++++++
html/index.html | 1 +
html/lib/shader.js | 34 ++++++++++++++++
package.json | 2 +-
8 files changed, 152 insertions(+), 3 deletions(-)
create mode 100644 html/002-rainbow-trinity.html
create mode 100644 html/002-rainbow-trinity.js
diff --git a/README.md b/README.md
index b3623dc..882a947 100644
--- a/README.md
+++ b/README.md
@@ -9,6 +9,7 @@ https://art.mekanoe.com
## Artworks
- [./001-platform-provenance](https://art.mekanoe.com/001-platform-provenance)
+- [./002-rainbow-trinity](https://art.mekanoe.com/002-rainbow-trinity)
## Development
@@ -18,6 +19,8 @@ https://art.mekanoe.com
`bun serve` to serve them locally
+`bun dev` if you're developing the templates for auto-generation.
+
### Infrastructure
- The "generator" does
diff --git a/generators/README.md.txt b/generators/README.md.txt
index 9a969b2..86964da 100644
--- a/generators/README.md.txt
+++ b/generators/README.md.txt
@@ -18,6 +18,8 @@ https://art.mekanoe.com
`bun serve` to serve them locally
+`bun dev` if you're developing the templates for auto-generation.
+
### Infrastructure
- The "generator" does
diff --git a/generators/generate.ts b/generators/generate.ts
index b5022ef..f5aee09 100644
--- a/generators/generate.ts
+++ b/generators/generate.ts
@@ -13,7 +13,8 @@ for (const htmlFile of allHtmls) {
const allWorks = globSync("html/*.js")
.map((file) => file.replace("html/", "").replace(".js", ""))
- .filter((work) => work !== "platform");
+ .sort()
+ .reverse();
console.log({ allWorks });
@@ -25,13 +26,16 @@ for (const work of allWorks) {
const index = indexTemplate.replace(
"",
- allWorks.map((work) => `
./${work}`).join("\n")
+ allWorks
+ .map((work) => `./${work}`)
+ .join("\n ")
);
await Bun.write("html/index.html", index);
const readme = readmeTemplate.replace(
"",
allWorks
+ .reverse()
.map((work) => `- [./${work}](https://art.mekanoe.com/${work})`)
.join("\n")
);
diff --git a/html/002-rainbow-trinity.html b/html/002-rainbow-trinity.html
new file mode 100644
index 0000000..e43e463
--- /dev/null
+++ b/html/002-rainbow-trinity.html
@@ -0,0 +1,31 @@
+
+
+com.mekanoe.art // 002-rainbow-trinity
+
+
+
+
+ XX.X FPS (XX.X ms)
+
+
+
diff --git a/html/002-rainbow-trinity.js b/html/002-rainbow-trinity.js
new file mode 100644
index 0000000..1402215
--- /dev/null
+++ b/html/002-rainbow-trinity.js
@@ -0,0 +1,74 @@
+import { Shader, colorUtils, commonFrag, commonVert } from "./lib/shader.js";
+import { BasicPlane } from "./lib/basic-plane.js";
+import { App } from "./lib/app.js";
+
+const app = new App({ fov: 20 });
+const gl = app.gl;
+
+const shader = new Shader(app)
+ .attach(
+ gl.VERTEX_SHADER,
+ `
+ ${commonVert}
+
+ varying highp vec2 vTextureCoord;
+
+ void main() {
+ gl_Position = uProjectionMatrix * uModelViewMatrix * aVertexPosition;
+ vTextureCoord = aTextureCoord;
+ }
+ `
+ )
+ .attach(
+ gl.FRAGMENT_SHADER,
+ `
+ ${commonFrag}
+ ${colorUtils}
+
+ varying highp vec2 vTextureCoord;
+
+ vec3 circle(vec2 pos, vec3 color) {
+ float radius = 0.75;
+ float dist = length(pos);
+ float circle = smoothstep(radius + 0.001, radius, dist);
+ return color * vec3(1.0 - circle);
+ }
+
+ vec3 colorRotator(vec3 color, float phase, vec2 uv) {
+ color.x += uSinTime * 0.0001 + uv.y;
+ vec3 hsv = rgb2hsv(color);
+ hsv.x += uSinTime * 0.001 * uv.y - phase;
+ hsv.y = 1.0;
+ hsv.z = 0.5;
+ vec3 rgb = hsv2rgb(hsv);
+ return rgb;
+ }
+
+ void main() {
+ float value = sin(uTime * 0.00025) * 0.5 + 0.5;
+ vec2 sv = vec2(1.0, 1.0);
+ vec3 triUpper = hsv2rgb(vec3(value, sv));
+ vec3 triLeft = hsv2rgb(vec3(value + 0.33, sv));
+ vec3 triRight = hsv2rgb(vec3(value + 0.66, sv));
+
+ vec2 uv = vTextureCoord * 2.0 - 1.0;
+ vec3 color = vec3(0.0);
+
+ // place 3 circles in a triangle
+ color += circle(vec2(uv.x, uv.y + 0.5), colorRotator(triUpper, 1.0, uv));
+ color += circle(vec2(uv.x - 0.5, uv.y - 0.33), colorRotator(triLeft, 0.667, uv));
+ color += circle(vec2(uv.x + 0.5, uv.y - 0.33), colorRotator(triRight, 0.333, uv));
+
+ // color = 1.0 - color;
+
+ gl_FragColor = vec4(color, 1.0);
+ gl_FragColor = clamp(gl_FragColor, 0.0, 1.0);
+ }
+ `
+ )
+ .link();
+
+const plane = new BasicPlane(app);
+plane.attachShader(shader);
+
+app.loop();
diff --git a/html/index.html b/html/index.html
index 6c689b6..f78e35d 100644
--- a/html/index.html
+++ b/html/index.html
@@ -30,6 +30,7 @@
diff --git a/html/lib/shader.js b/html/lib/shader.js
index 701890e..c977ce2 100644
--- a/html/lib/shader.js
+++ b/html/lib/shader.js
@@ -71,3 +71,37 @@ export class Shader {
this.updateTime();
}
}
+
+export const colorUtils = `
+ vec3 rgb2hsv(vec3 c) {
+ vec4 K = vec4(0.0, -1.0 / 3.0, 2.0 / 3.0, -1.0);
+ vec4 p = mix(vec4(c.bg, K.wz), vec4(c.gb, K.xy), step(c.b, c.g));
+ vec4 q = mix(vec4(p.xyw, c.r), vec4(c.r, p.yzx), step(p.x, c.r));
+
+ float d = q.x - min(q.w, q.y);
+ float e = 1.0e-10;
+ return vec3(abs(q.z + (q.w - q.y) / (6.0 * d + e)), d / (q.x + e), q.x);
+ }
+
+ vec3 hsv2rgb(vec3 c) {
+ vec4 K = vec4(1.0, 2.0 / 3.0, 1.0 / 3.0, 3.0);
+ vec3 p = abs(fract(c.xxx + K.xyz) * 6.0 - K.www);
+ return c.z * mix(K.xxx, clamp(p - K.xxx, 0.0, 1.0), c.y);
+ }
+`;
+
+export const commonFrag = `
+ precision highp float;
+
+ uniform float uTime;
+ uniform float uSinTime;
+ uniform float uCosTime;
+`;
+
+export const commonVert = `
+ attribute vec4 aVertexPosition;
+ attribute vec2 aTextureCoord;
+
+ uniform mat4 uModelViewMatrix;
+ uniform mat4 uProjectionMatrix;
+`;
diff --git a/package.json b/package.json
index c14195a..80d6bc1 100644
--- a/package.json
+++ b/package.json
@@ -1,7 +1,7 @@
{
"name": "noeidelon",
"type": "module",
- "main": "./generators/generate.ts",
+ "main": "./generators/generate.js",
"scripts": {
"build": "bun $BUNFLAGS ./generators/generate.ts",
"build:watch": "BUNFLAGS=--watch bun run build",