├── public
├── textures
│ ├── text_map.png
│ ├── unsplash_1.webp
│ ├── uv_checker_1.png
│ ├── uv_checker_2.png
│ └── lancellotti_chapel
│ │ ├── nx.webp
│ │ ├── ny.webp
│ │ ├── nz.webp
│ │ ├── px.webp
│ │ ├── py.webp
│ │ └── pz.webp
└── vite.svg
├── src
├── 20240202
│ ├── sketch.fs
│ └── index.html
├── 20240203
│ ├── index.html
│ └── sketch.fs
├── 20240204
│ ├── sketch.fs
│ └── index.html
├── 20240205
│ ├── index.html
│ └── sketch.fs
├── 20240206
│ ├── index.html
│ └── sketch.fs
├── 20240207
│ ├── index.html
│ └── sketch.fs
├── 20240208
│ ├── index.html
│ └── sketch.fs
├── 20240210
│ ├── index.html
│ └── sketch.fs
├── 20240211
│ ├── index.html
│ └── sketch.fs
├── 20240213
│ ├── index.html
│ └── sketch.fs
├── 20240214
│ ├── index.html
│ └── sketch.fs
├── 20240217
│ ├── index.html
│ └── sketch.fs
├── 20240218
│ ├── index.html
│ └── sketch.fs
├── 20240219
│ ├── index.html
│ └── sketch.fs
├── 20240221
│ ├── index.html
│ └── sketch.fs
├── 20240225
│ ├── index.html
│ └── sketch.fs
├── 20240303
│ ├── sketch.fs
│ ├── index.html
│ └── output.fs
├── 20240304
│ ├── index.html
│ └── sketch.fs
├── 20240306
│ ├── index.html
│ └── sketch.fs
├── 20240308
│ ├── index.html
│ └── sketch.fs
├── 20240311
│ ├── index.html
│ └── sketch.fs
├── 20240312
│ ├── index.html
│ └── sketch.fs
├── 20240401
│ ├── index.html
│ └── sketch.fs
├── 20240418
│ ├── index.html
│ └── sketch.fs
├── 20240419
│ ├── index.html
│ └── sketch.fs
├── 20240422
│ ├── index.html
│ └── sketch.fs
├── 20240425
│ ├── index.html
│ └── sketch.fs
├── vite-env.d.ts
├── scripts
│ ├── shader
│ │ ├── quad.vs
│ │ └── output.fs
│ ├── core
│ │ ├── ExtendedMaterials.ts
│ │ ├── BackBuffer.ts
│ │ ├── FrameBuffer.ts
│ │ └── Three.ts
│ ├── entry.ts
│ ├── Params.ts
│ ├── Mouse2D.ts
│ ├── MainScene.ts
│ └── Canvas.ts
├── template
│ ├── sketch.fs
│ └── index.html
├── template_postprocessing
│ ├── sketch.fs
│ ├── output.fs
│ └── index.html
├── 20240203_2
│ ├── index.html
│ └── sketch.fs
├── 20240206_2
│ ├── index.html
│ └── sketch.fs
├── 20240204_2
│ ├── index.html
│ └── sketch.fs
├── 20240306_2
│ ├── index.html
│ └── sketch.fs
├── 20240207_2
│ ├── index.html
│ └── sketch.fs
├── 20240213_2
│ ├── index.html
│ └── sketch.fs
├── style.css
└── index.html
├── README.md
├── .prettierrc.cjs
├── .gitignore
├── package.json
├── tsconfig.json
├── vite.config.ts
└── .github
└── workflows
└── deploy.yml
/public/textures/text_map.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/text_map.png
--------------------------------------------------------------------------------
/src/vite-env.d.ts:
--------------------------------------------------------------------------------
1 | ///
2 | ///
3 |
--------------------------------------------------------------------------------
/public/textures/unsplash_1.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/unsplash_1.webp
--------------------------------------------------------------------------------
/public/textures/uv_checker_1.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/uv_checker_1.png
--------------------------------------------------------------------------------
/public/textures/uv_checker_2.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/uv_checker_2.png
--------------------------------------------------------------------------------
/public/textures/lancellotti_chapel/nx.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/lancellotti_chapel/nx.webp
--------------------------------------------------------------------------------
/public/textures/lancellotti_chapel/ny.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/lancellotti_chapel/ny.webp
--------------------------------------------------------------------------------
/public/textures/lancellotti_chapel/nz.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/lancellotti_chapel/nz.webp
--------------------------------------------------------------------------------
/public/textures/lancellotti_chapel/px.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/lancellotti_chapel/px.webp
--------------------------------------------------------------------------------
/public/textures/lancellotti_chapel/py.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/lancellotti_chapel/py.webp
--------------------------------------------------------------------------------
/public/textures/lancellotti_chapel/pz.webp:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/nemutas/webgl-sketch/HEAD/public/textures/lancellotti_chapel/pz.webp
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | move to https://github.com/nemutas/fs-sketch
2 |
3 | # About
4 | fragmentShaderの復習やちょっとした試し書き用のリポジトリ。twiglみたいな感じ。
5 |
6 | https://nemutas.github.io/webgl-sketch/
7 |
--------------------------------------------------------------------------------
/src/scripts/shader/quad.vs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 |
3 | in vec3 position;
4 | in vec2 uv;
5 |
6 | out vec2 vUv;
7 |
8 | void main() {
9 | vUv = uv;
10 | gl_Position = vec4(position, 1.0);
11 | }
--------------------------------------------------------------------------------
/.prettierrc.cjs:
--------------------------------------------------------------------------------
1 | /** @type {import("prettier").Config} */
2 | module.exports = {
3 | tabWidth: 2,
4 | useTabs: false,
5 | semi: false,
6 | trailingComma: 'all',
7 | singleQuote: true,
8 | printWidth: 160,
9 | }
10 |
--------------------------------------------------------------------------------
/src/scripts/shader/output.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D source;
5 |
6 | in vec2 vUv;
7 | out vec4 outColor;
8 |
9 | void main() {
10 | outColor = vec4(texture(source, vUv).rgb, 1.0);
11 | }
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | # Logs
2 | logs
3 | *.log
4 | npm-debug.log*
5 | yarn-debug.log*
6 | yarn-error.log*
7 | pnpm-debug.log*
8 | lerna-debug.log*
9 |
10 | node_modules
11 | dist
12 | dist-ssr
13 | *.local
14 |
15 | # Editor directories and files
16 | .vscode/*
17 | !.vscode/extensions.json
18 | .idea
19 | .DS_Store
20 | *.suo
21 | *.ntvs*
22 | *.njsproj
23 | *.sln
24 | *.sw?
25 |
--------------------------------------------------------------------------------
/src/scripts/core/ExtendedMaterials.ts:
--------------------------------------------------------------------------------
1 | import * as THREE from 'three'
2 |
3 | export class RawShaderMaterial extends THREE.RawShaderMaterial {
4 | constructor(parameters: THREE.ShaderMaterialParameters) {
5 | super(parameters)
6 | this.preprocess()
7 | }
8 |
9 | private preprocess() {
10 | if (this.glslVersion === '300 es') {
11 | this.vertexShader = this.vertexShader.replace('#version 300 es', '')
12 | this.fragmentShader = this.fragmentShader.replace('#version 300 es', '')
13 | }
14 | }
15 | }
16 |
--------------------------------------------------------------------------------
/src/template/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | const float SEED = SEED_VALUE;
15 |
16 | void main() {
17 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
18 | outColor = vec4(uv, 0.0, 1.0);
19 | }
20 |
21 | //----------------------------
22 | // Reference
23 | //----------------------------
--------------------------------------------------------------------------------
/src/scripts/entry.ts:
--------------------------------------------------------------------------------
1 | import { Canvas } from './Canvas'
2 |
3 | export function entry(fragmentShader: string, outputFs?: string) {
4 | setSourceLink()
5 | new Canvas(document.querySelector('canvas')!, fragmentShader, outputFs)
6 | }
7 |
8 | function setSourceLink() {
9 | const source = document.querySelector('.links .source')
10 | if (source) {
11 | const page = location.href.split('/').at(-2)
12 | source.href = `https://github.com/nemutas/webgl-sketch/blob/main/src/${page}/sketch.fs`
13 | }
14 | }
15 |
--------------------------------------------------------------------------------
/src/template_postprocessing/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | const float SEED = SEED_VALUE;
15 |
16 | void main() {
17 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
18 | outColor = vec4(uv, 0.0, 1.0);
19 | }
20 |
21 | //----------------------------
22 | // Reference
23 | //----------------------------
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "webgl-sketch",
3 | "private": true,
4 | "version": "0.0.0",
5 | "type": "module",
6 | "scripts": {
7 | "dev": "vite",
8 | "start": "vite",
9 | "build": "tsc && vite build",
10 | "preview": "vite preview"
11 | },
12 | "devDependencies": {
13 | "@types/node": "^20.11.16",
14 | "@types/three": "^0.160.0",
15 | "prettier": "^3.0.3",
16 | "typescript": "^5.0.2",
17 | "vite": "^4.4.5",
18 | "vite-plugin-glsl": "^1.1.2"
19 | },
20 | "dependencies": {
21 | "three": "^0.160.0"
22 | }
23 | }
24 |
--------------------------------------------------------------------------------
/src/template_postprocessing/output.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D source;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform int frame;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | void main() {
14 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
15 |
16 | float n = 20.0;
17 | uv = floor(uv * asp * n) / asp / n;
18 | vec3 source = texture(source, uv).rgb;
19 | float gray = dot(source, vec3(0.333333));
20 |
21 | outColor = vec4(vec3(gray), 1.0);
22 | }
--------------------------------------------------------------------------------
/tsconfig.json:
--------------------------------------------------------------------------------
1 | {
2 | "compilerOptions": {
3 | "target": "ES2020",
4 | "useDefineForClassFields": true,
5 | "module": "ESNext",
6 | "lib": ["ES2023", "DOM", "DOM.Iterable"],
7 | "skipLibCheck": true,
8 |
9 | /* Bundler mode */
10 | "moduleResolution": "bundler",
11 | "allowImportingTsExtensions": true,
12 | "resolveJsonModule": true,
13 | "isolatedModules": true,
14 | "noEmit": true,
15 |
16 | /* Linting */
17 | "strict": true,
18 | "noUnusedLocals": true,
19 | "noUnusedParameters": true,
20 | "noFallthroughCasesInSwitch": true
21 | },
22 | "include": ["src"]
23 | }
24 |
--------------------------------------------------------------------------------
/src/20240204/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | const float PI = acos(-1.0);
13 |
14 | void main() {
15 | vec2 uv = vUv, asp = vec2(resolution.x / resolution.y, 1.0), suv = (uv * 2.0 - 1.0) * asp;
16 |
17 | vec2 puv = vec2(atan(suv.y, suv.x), length(suv));
18 | float c = step(fract(puv.x / PI * 5.0 + sin(puv.y * 10.0 - time)), 0.5);
19 |
20 | vec4 b = texture(backBuffer, vUv);
21 | vec3 col = mix(vec3(c), b.rgb, 0.5);
22 |
23 | outColor = vec4(col, 1.0);
24 | }
--------------------------------------------------------------------------------
/src/20240202/sketch.fs:
--------------------------------------------------------------------------------
1 | // https://scrapbox.io/0b5vr/Cyclic_Noise
2 |
3 | #version 300 es
4 | precision highp float;
5 |
6 | uniform sampler2D backBuffer;
7 | uniform vec2 resolution;
8 | uniform vec2 mouse;
9 | uniform float time;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | #define loop(i, n) for(int i; i < n; i++)
15 |
16 | vec3 cyc(vec3 p) {
17 | vec4 n;
18 | loop(i, 8) {
19 | p += sin(p.yzx);
20 | n = 2.0 * n + vec4(cross(cos(p), sin(p.zxy)), 1.0);
21 | p *= 2.0;
22 | }
23 | return n.xyz / n.w;
24 | }
25 |
26 | void main() {
27 | vec2 uv = vUv, suv = uv * 2.0 - 1.0;
28 | vec3 color = cyc(vec3(suv * 3.0, time)) * 0.5 + 0.5;
29 |
30 | outColor = vec4(color, 1.0);
31 | }
--------------------------------------------------------------------------------
/src/20240203_2/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | 120bpm
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240205/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | 0x👾👾u
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240206_2/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | IFS
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240419/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | old view
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/template/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | template
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240202/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | Cyclic Noise
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240204/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | polar coords
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240207/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | (👾<<16)+👾
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240306/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | fake fluid
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240204_2/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | learning bit calc
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240208/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | 👾
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240211/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | 山岳
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240214/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | cross
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240306_2/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | Lissajous curve
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240207_2/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | polar👾
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240213/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | voronoi
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240217/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | hash shape
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240218/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | Conway's Game of Life
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240308/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | 75fps torusknot star
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240206/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | phantom mode
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240210/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | quadtree + pmod
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240213_2/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | menger sponge
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240221/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | mandelbrot set
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240304/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | pattern shading
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240311/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | unshift pattern☐
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240312/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | unshift pattern○
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240422/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | quad tree detail
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240425/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | annual tree ring
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240203/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | hemisphere
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240219/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | アルキメデス立体
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240401/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | spread
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240225/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | raymarching study
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240303/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform int frame;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | #define loop(n) for(int i=0;i
2 |
3 |
4 |
5 |
6 |
7 | quad tree text
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
23 |
24 |
--------------------------------------------------------------------------------
/src/20240303/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | dither
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
24 |
25 |
--------------------------------------------------------------------------------
/src/template_postprocessing/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | template
8 |
9 |
10 |
11 |
12 |
16 |
17 |
18 |
24 |
25 |
--------------------------------------------------------------------------------
/src/20240205/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 | precision highp int;
4 |
5 | uniform sampler2D backBuffer;
6 | uniform vec2 resolution;
7 | uniform vec2 mouse;
8 | uniform float time;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | void main() {
14 | vec2 uv = vUv, asp = vec2(resolution.x / resolution.y, 1.0);
15 | vec2 iuv = floor(uv * vec2(32.0, 32.0 / asp.x));
16 | float x = floor(iuv.y / 8.0) * 8.0;
17 | iuv.y = fract(iuv.y / 8.0) * 8.0;
18 |
19 | uint[8] rows = uint[](
20 | 0x00d800d8u,
21 | 0x05050505u,
22 | 0x05fd05fdu,
23 | 0x07ff07ffu,
24 | 0x03760376u,
25 | 0x01fc01fcu,
26 | 0x00880088u,
27 | 0x01040104u
28 | );
29 |
30 | float t = time * 100.0 / 60.0 + x;
31 |
32 | float c;
33 | uint b = rows[int(iuv.y)];
34 | b = (b << uint(iuv.x + t)) >> 31;
35 | c = float(b);
36 |
37 | outColor = vec4(vec3(c), 1.0);
38 | }
--------------------------------------------------------------------------------
/src/style.css:
--------------------------------------------------------------------------------
1 | * {
2 | padding: 0;
3 | margin: 0;
4 | box-sizing: border-box;
5 | }
6 |
7 | html {
8 | font-size: 62.5%;
9 | background: #0e0e0e;
10 | }
11 |
12 | a {
13 | position: relative;
14 | display: inline-block;
15 | padding: 5px 3px;
16 | font-size: 15px;
17 | line-height: 1;
18 | text-underline-offset: 2px;
19 | color: #f0f0f0;
20 | }
21 |
22 | canvas {
23 | position: fixed;
24 | top: 0;
25 | width: 100%;
26 | height: 100lvh;
27 | background: #0e0e0e;
28 | }
29 |
30 | .links {
31 | position: absolute;
32 | bottom: 5px;
33 | right: 10px;
34 | }
35 |
36 | .tmp {
37 | color: #fff4;
38 | }
39 |
40 | .sketches {
41 | padding: 5px;
42 | }
43 |
44 | .sketches a::before {
45 | position: absolute;
46 | content: '';
47 | width: 1px;
48 | height: 50vh;
49 | /* height: 90vh; */
50 | background: linear-gradient(to bottom, #fff1 80%, transparent 100%);
51 | right: 2px;
52 | top: calc(100% - 7px);
53 | pointer-events: none;
54 | }
55 |
--------------------------------------------------------------------------------
/src/20240306_2/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | #define sat(v) clamp(v, 0.0, 1.0)
15 |
16 | void main() {
17 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
18 |
19 | float dt = time - prevTime;
20 | float d, n = 15.0;
21 | for (float i = 0.0; i < n; i++) {
22 | float t = prevTime + dt * (i / n);
23 | vec2 coord = sin(vec2(4, 5) * t * 1.);
24 | d += smoothstep(0.02, 0.01, distance(suv * 1.5, coord));
25 | }
26 |
27 | vec3 b = texture(backBuffer, uv).rgb;
28 | b *= step(0.08, b);
29 | vec3 col = vec3(d, b.rg);
30 | col = sat(mix(b, col * 2.0, 0.1));
31 |
32 | outColor = vec4(col, 1.0);
33 | }
34 |
35 | //----------------------------
36 | // Reference
37 | //----------------------------
38 | // https://zenn.dev/k_kuroguro/articles/b73e4e6e3d2c13
--------------------------------------------------------------------------------
/src/scripts/core/BackBuffer.ts:
--------------------------------------------------------------------------------
1 | import { FrameBuffer, Options } from './FrameBuffer'
2 |
3 | export abstract class BackBuffer extends FrameBuffer {
4 | private readonly rt2: THREE.WebGLRenderTarget
5 | private prev: THREE.WebGLRenderTarget
6 | private current: THREE.WebGLRenderTarget
7 |
8 | constructor(renderer: THREE.WebGLRenderer, material: THREE.RawShaderMaterial, options?: Options) {
9 | super(renderer, material, options)
10 |
11 | this.rt2 = this.createRenderTarget()
12 | this.prev = this.renderTarget
13 | this.current = this.rt2
14 | }
15 |
16 | resize() {
17 | super.resize()
18 | this.rt2.setSize(this.size.width, this.size.height)
19 | }
20 |
21 | get backBuffer() {
22 | return this.prev.texture
23 | }
24 |
25 | private swap() {
26 | this.current = this.current === this.renderTarget ? this.rt2 : this.renderTarget
27 | this.prev = this.current === this.renderTarget ? this.rt2 : this.renderTarget
28 | }
29 |
30 | render(..._args: any[]) {
31 | this.renderer.setRenderTarget(this.current)
32 | this.renderer.render(this.scene, this.camera)
33 |
34 | this.swap()
35 | }
36 | }
37 |
--------------------------------------------------------------------------------
/src/20240203/sketch.fs:
--------------------------------------------------------------------------------
1 | // https://twitter.com/cmzw_/status/1616708959506948096
2 |
3 | #version 300 es
4 | precision highp float;
5 |
6 | uniform sampler2D backBuffer;
7 | uniform vec2 resolution;
8 | uniform vec2 mouse;
9 | uniform float time;
10 | uniform sampler2D textureUnit;
11 |
12 | in vec2 vUv;
13 | out vec4 outColor;
14 |
15 | vec2 coveredUv() {
16 | ivec2 imgSize = textureSize(textureUnit, 0);
17 | float imgAsp = float(imgSize.x) / float(imgSize.y);
18 | float screenAsp = resolution.x / resolution.y;
19 | vec2 covered = imgAsp < screenAsp ? vec2(1.0, imgAsp / screenAsp) : vec2(screenAsp / imgAsp, 1.0);
20 | return (vUv - 0.5) * covered + 0.5;
21 | }
22 |
23 | void main() {
24 | vec2 asp = vec2(resolution.x / resolution.y, 1.0);
25 | vec2 suv = vUv * 2.0 - 1.0;
26 | suv *= asp * 1.5;
27 | vec3 hemiSphereNormal = normalize(vec3(suv, (sqrt(1.0 - dot(suv, suv)) + 0.5) / 0.5));
28 | vec2 distortion = hemiSphereNormal.xy * (1.0 - hemiSphereNormal.z);
29 |
30 | vec2 uv = coveredUv();
31 | uv.x += time * 0.1;
32 | vec4 col = mix(texture(textureUnit, uv), texture(textureUnit, uv + distortion), smoothstep(1.0, 0.99, length(suv)));
33 |
34 | outColor = col;
35 | }
--------------------------------------------------------------------------------
/vite.config.ts:
--------------------------------------------------------------------------------
1 | import path from 'path'
2 | import { defineConfig } from 'vite'
3 | import glsl from 'vite-plugin-glsl'
4 |
5 | function resolvedPath(root: string) {
6 | const r = root !== '' ? `/${root}` : ''
7 | return path.resolve(__dirname, `./src${r}/index.html`)
8 | }
9 |
10 | export default defineConfig(() => {
11 | return {
12 | root: './src',
13 | publicDir: '../public',
14 | base: '/webgl-sketch/',
15 | build: {
16 | outDir: '../dist',
17 | rollupOptions: {
18 | // prettier-ignore
19 | input: [
20 | '',
21 | 'template', 'template_postprocessing',
22 | '20240202', '20240203', '20240203_2', '20240204', '20240204_2', '20240205', '20240206', '20240206_2', '20240207', '20240207_2', '20240208', '20240210', '20240211', '20240213', '20240213_2', '20240214', '20240217', '20240218', '20240219', '20240221', '20240225',
23 | '20240303', '20240304', '20240306', '20240306_2', '20240308', '20240311', '20240312',
24 | '20240401', '20240418', '20240419', '20240422', '20240425',
25 | ].map((str) => resolvedPath(str)),
26 | },
27 | },
28 | plugins: [glsl()],
29 | server: {
30 | host: true,
31 | },
32 | }
33 | })
34 |
--------------------------------------------------------------------------------
/src/20240419/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | const float SEED = SEED_VALUE;
15 |
16 | #define h21(f2, f1) hash(vec3(f2, f1))
17 |
18 | vec3 hash(vec3 v) {
19 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
20 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
21 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
22 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
23 | return vec3(x) / vec3(-1u);
24 | }
25 |
26 | void main() {
27 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
28 |
29 | float lt = time * 180.0 / 60.0;
30 | float bt = floor(lt);
31 | float tt = tanh(fract(lt) * 5.0);
32 | lt = bt + tt;
33 |
34 | vec3 h1 = h21(floor(uv * asp * vec2(1000, 0)), floor(time * 30.0));
35 | vec3 h2 = h21(floor(floor(uv * asp * 400.0)), floor(time * 30.0));
36 | float c = step(h1.x, 0.995);
37 | c *= step(h2.x, 0.9999);
38 | c = 1.0 - clamp(c, 0.0, 1.0);
39 | c *= 0.2;
40 |
41 | outColor = vec4(vec3(c), 1.0);
42 | }
43 |
44 | //----------------------------
45 | // Reference
46 | //----------------------------
--------------------------------------------------------------------------------
/src/20240203_2/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | #define sat(v) clamp(v, 0.0, 1.0)
13 |
14 | const float PI = acos(-1.0);
15 |
16 | mat2 rot(float a) {
17 | float s = sin(a), c = cos(a);
18 | return mat2(c, s, -s, c);
19 | }
20 |
21 | void main() {
22 | vec2 uv = vUv, asp = vec2(resolution.x / resolution.y, 1.0), suv = (uv * 2.0 - 1.0) * asp;
23 |
24 | vec4 b = texture(backBuffer, uv);
25 |
26 | float lt = time * 120.0 / 60.0; // 120bpm
27 | float bt = floor(lt);
28 | float tt = tanh(fract(lt) * 5.0);
29 | lt = bt + tt;
30 |
31 | suv *= rot(PI * 0.25 * lt);
32 |
33 | vec2 auv = abs(suv), ruv = abs(rot(PI * 0.25) * suv);
34 | float c = step(auv.x + auv.y * 0.18, 0.12) + step(auv.y + auv.x * 0.18, 0.12);
35 | c += step(ruv.x + ruv.y * 0.18, 0.08) + step(ruv.y + ruv.x * 0.18, 0.08);
36 | auv = abs(rot(PI * 1.0 / 6.2) * suv), ruv = abs(rot(PI * 1.0 / 2.95) * suv);
37 | c *= step(0.008, auv.x) * step(0.008, auv.y) * step(0.008, ruv.x) * step(0.008, ruv.y);
38 |
39 | vec3 col = vec3(sat(c), b.rg);
40 | col = mix(col, b.rgb, 0.5);
41 |
42 | outColor = vec4(col, 1.0);
43 | }
--------------------------------------------------------------------------------
/src/scripts/Params.ts:
--------------------------------------------------------------------------------
1 | import * as THREE from 'three'
2 |
3 | class Params {
4 | private data_texture?: string
5 | private data_dpr?: string
6 | private data_stats?: string
7 | private data_cubemap?: string
8 | private data_filter?: string
9 |
10 | constructor() {
11 | const canvas = document.querySelector('canvas')!
12 | this.data_texture = canvas.dataset.texture
13 | this.data_dpr = canvas.dataset.dpr
14 | this.data_stats = canvas.dataset.stats
15 | this.data_cubemap = canvas.dataset.cubemap
16 | this.data_filter = canvas.dataset.filter
17 | }
18 |
19 | get texturePath() {
20 | if (this.data_texture) {
21 | return import.meta.env.BASE_URL + `textures/${this.data_texture}`
22 | } else {
23 | return null
24 | }
25 | }
26 |
27 | get cubeMapPath() {
28 | if (this.data_cubemap) {
29 | return import.meta.env.BASE_URL + `textures/${this.data_cubemap}/`
30 | } else {
31 | return null
32 | }
33 | }
34 |
35 | get dpr() {
36 | const d = Number(this.data_dpr ?? window.devicePixelRatio)
37 | return Math.min(d, 2)
38 | }
39 |
40 | get enableStats() {
41 | return Boolean(this.data_stats)
42 | }
43 |
44 | get filterType() {
45 | return this.data_filter === 'linear' ? THREE.LinearFilter : THREE.NearestFilter
46 | }
47 | }
48 |
49 | export const params = new Params()
50 |
--------------------------------------------------------------------------------
/.github/workflows/deploy.yml:
--------------------------------------------------------------------------------
1 | # 静的コンテンツを GitHub Pages にデプロイするためのシンプルなワークフロー
2 | name: Deploy static content to Pages
3 |
4 | on:
5 | # デフォルトブランチを対象としたプッシュ時にで実行されます
6 | push:
7 | branches: ['main']
8 | paths-ignore: ['**/README.md']
9 |
10 | # Actions タブから手動でワークフローを実行できるようにします
11 | workflow_dispatch:
12 |
13 | # GITHUB_TOKEN のパーミッションを設定し、GitHub Pages へのデプロイを許可します
14 | permissions:
15 | contents: read
16 | pages: write
17 | id-token: write
18 |
19 | # 1 つの同時デプロイメントを可能にする
20 | concurrency:
21 | group: 'pages'
22 | cancel-in-progress: true
23 |
24 | jobs:
25 | # デプロイするだけなので、単一のデプロイジョブ
26 | deploy:
27 | environment:
28 | name: github-pages
29 | url: ${{ steps.deployment.outputs.page_url }}
30 | runs-on: ubuntu-latest
31 | steps:
32 | - name: Checkout
33 | uses: actions/checkout@v3
34 | - name: Set up Node
35 | uses: actions/setup-node@v3
36 | with:
37 | node-version: 18
38 | cache: 'npm'
39 | - name: Install dependencies
40 | run: npm install
41 | - name: Build
42 | run: npm run build
43 | - name: Setup Pages
44 | uses: actions/configure-pages@v3
45 | - name: Upload artifact
46 | uses: actions/upload-pages-artifact@v1
47 | with:
48 | # dist リポジトリのアップロード
49 | path: './dist'
50 | - name: Deploy to GitHub Pages
51 | id: deployment
52 | uses: actions/deploy-pages@v1
53 |
--------------------------------------------------------------------------------
/public/vite.svg:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/src/scripts/Mouse2D.ts:
--------------------------------------------------------------------------------
1 | class Mouse2D {
2 | readonly position: [number, number] = [99999, 99999]
3 | readonly prevPosition: [number, number] = [99999, 99999]
4 |
5 | constructor() {
6 | window.addEventListener('mousemove', this.handleMouseMove)
7 | window.addEventListener('touchmove', this.handleTouchMove)
8 | }
9 |
10 | private handleMouseMove = (e: MouseEvent) => {
11 | this.prevPosition[0] = this.position[0]
12 | this.prevPosition[1] = this.position[1]
13 | this.position[0] = (e.clientX / window.innerWidth) * 2 - 1
14 | this.position[1] = -1 * ((e.clientY / window.innerHeight) * 2 - 1)
15 | }
16 |
17 | private handleTouchMove = (e: TouchEvent) => {
18 | const { pageX, pageY } = e.touches[0]
19 | this.prevPosition[0] = this.position[0]
20 | this.prevPosition[1] = this.position[1]
21 | this.position[0] = (pageX / window.innerWidth) * 2 - 1
22 | this.position[1] = -1 * ((pageY / window.innerHeight) * 2 - 1)
23 | }
24 |
25 | lerp(t: number) {
26 | this.prevPosition[0] = this.prevPosition[0] * (1 - t) + this.position[0] * t
27 | this.prevPosition[1] = this.prevPosition[1] * (1 - t) + this.position[1] * t
28 | return [this.position[0] - this.prevPosition[0], this.position[1] - this.prevPosition[1]]
29 | }
30 |
31 | dispose() {
32 | window.removeEventListener('mousemove', this.handleMouseMove)
33 | window.removeEventListener('touchmove', this.handleTouchMove)
34 | }
35 | }
36 |
37 | export const mouse2d = new Mouse2D()
38 |
--------------------------------------------------------------------------------
/src/scripts/MainScene.ts:
--------------------------------------------------------------------------------
1 | import { mouse2d } from './Mouse2D'
2 | import { BackBuffer } from './core/BackBuffer'
3 | import { RawShaderMaterial } from './core/ExtendedMaterials'
4 | import vertexShader from './shader/quad.vs'
5 |
6 | export class MainScene extends BackBuffer {
7 | constructor(renderer: THREE.WebGLRenderer, fragmentShader: string) {
8 | fragmentShader = fragmentShader.replace('SEED_VALUE', Math.random().toFixed(5))
9 |
10 | const material = new RawShaderMaterial({
11 | uniforms: {
12 | backBuffer: { value: null },
13 | resolution: { value: [renderer.domElement.width, renderer.domElement.height] },
14 | mouse: { value: mouse2d.position },
15 | time: { value: 0 },
16 | prevTime: { value: 0 },
17 | frame: { value: 0 },
18 | },
19 | vertexShader,
20 | fragmentShader,
21 | glslVersion: '300 es',
22 | })
23 |
24 | super(renderer, material)
25 | }
26 |
27 | resize() {
28 | super.resize()
29 | this.uniforms.resolution.value = [this.size.width, this.size.height]
30 | this.uniforms.time.value = 0
31 | this.uniforms.prevTime.value = 0
32 | this.uniforms.frame.value = 0
33 | }
34 |
35 | render(dt: number) {
36 | this.uniforms.backBuffer.value = this.backBuffer
37 | this.uniforms.mouse.value = mouse2d.position
38 | this.uniforms.prevTime.value = this.uniforms.time.value
39 | this.uniforms.time.value += dt
40 | this.uniforms.frame.value += 1
41 | super.render()
42 | }
43 | }
44 |
--------------------------------------------------------------------------------
/src/20240213/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | vec2 hash(vec2 v) {
13 | uvec2 x = floatBitsToUint(v + vec2(0.1, 0.2));
14 | x = (x >> 8 ^ x.yx) * 0x456789ABu;
15 | x = (x >> 8 ^ x.yx) * 0x6789AB45u;
16 | x = (x >> 8 ^ x.yx) * 0x89AB4567u;
17 | return vec2(x) / vec2(-1u);
18 | }
19 |
20 | mat2 rot(float a) {
21 | float s = sin(a), c = cos(a);
22 | return mat2(c, s, -s, c);
23 | }
24 |
25 | vec3 voronoi(vec2 p) {
26 | vec2 n = floor(p + 0.5);
27 | float dist = sqrt(2.0);
28 | vec2 id;
29 | for (float j = -1.0; j <= 1.0; j++) {
30 | for (float i = -1.0; i <= 1.0; i++) {
31 | vec2 grid = n + vec2(i, j);
32 | vec2 h = hash(grid) - 0.5;
33 | vec2 jitter = rot(time * sign(h).x * h.y * 5.0) * h;
34 | if (distance(grid + jitter, p) <= dist) {
35 | dist = distance(grid + jitter, p);
36 | id = grid;
37 | }
38 | }
39 | }
40 | return vec3(id, dist);
41 | }
42 |
43 | void main() {
44 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
45 | vec3 v = voronoi(uv * asp * 10.0);
46 | vec2 vid = hash(v.xy);
47 | vec3 col = vec3(vid, 0.9) + pow(v.z, 5.0);
48 | outColor = vec4(col, 1.0);
49 | }
50 |
51 | //----------------------------
52 | // Reference
53 | //----------------------------
54 | // リアルタイムグラフィックスの数学 ― GLSLではじめるシェーダプログラミング
55 | // https://amzn.asia/d/9rQTjZC
--------------------------------------------------------------------------------
/src/20240211/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | #define loop(n) for(int i; i < n; i++)
13 |
14 | float lt, bt, tt;
15 |
16 | vec3 cyc(vec3 p) {
17 | vec4 n;
18 | loop(8) {
19 | p += sin(p.yzx);
20 | n = 2.0 * n + vec4(cross(cos(p), sin(p.zxy)), 1.0);
21 | p *= 2.0;
22 | }
23 | return n.xyz / n.w;
24 | }
25 |
26 | mat2 rot(float a) {
27 | float s = sin(a), c = cos(a);
28 | return mat2(c, s, -s, c);
29 | }
30 |
31 | float sdf(vec3 p) {
32 | p.y += 13.0;
33 | p.yz *= rot(-time * 0.01);
34 | p += cyc(p * 2.0 + lt) * 0.25;
35 | float final = length(p) - 13.0;
36 | return final * 0.6;
37 | }
38 |
39 | void main() {
40 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
41 | vec3 rd = normalize(vec3(suv, -5.0)), ro = vec3(0.0, 0.0, 7.0);
42 |
43 | lt = time * 30.0 / 60.0;
44 | bt = floor(lt);
45 | tt = tanh(fract(lt) * 5.0);
46 | lt = bt + tt;
47 |
48 | float t, acc;
49 | loop(80) {
50 | vec3 p = rd * t + ro;
51 | float d = sdf(p);
52 | if (d < 1e-4 || 1e4 < t) break;
53 | t += d;
54 | acc += exp(abs(d) * -5.0);
55 | }
56 |
57 | float c = acc / 80.0;
58 |
59 | vec4 b = texture(backBuffer, vUv);
60 | vec3 col = mix(vec3(c), b.rgb, 0.7);
61 |
62 | outColor = vec4(col, 1.0);
63 | }
64 |
65 | //----------------------------
66 | // Reference
67 | //----------------------------
--------------------------------------------------------------------------------
/src/20240206/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | #define loop(n) for(int i; i < n; i++)
13 |
14 | mat2 rot(float a) {
15 | float s = sin(a), c = cos(a);
16 | return mat2(c, s, -s, c);
17 | }
18 |
19 | float box(vec3 p, vec3 b) {
20 | p = abs(p) - b;
21 | return max(p.x, max(p.y, p.z));
22 | }
23 |
24 | float sdf(vec3 p) {
25 | float final = 1e9;
26 |
27 | p.xz *= rot(time);
28 | p.zy *= rot(time);
29 |
30 | p = abs(p);
31 | vec3 edge = 0.5 - max(vec3(0.5), p) * 0.2;
32 | float b1 = box(p, vec3(2.5, edge.x, edge.x));
33 | float b2 = box(p, vec3(edge.y, 2.5, edge.y));
34 | float b3 = box(p, vec3(edge.z, edge.z, 2.5));
35 | final = min(b1, min(b2, b3));
36 | return final;
37 | }
38 |
39 | void main() {
40 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv - 0.5) * asp * 2.0;
41 | vec3 rd = normalize(vec3(suv, -4.0 + length(suv) * 5.0)), ro = vec3(0.0, 0.0, 8.0);
42 |
43 | float t, acc;
44 | loop(64) {
45 | vec3 p = rd * t + ro;
46 | float d = sdf(p);
47 | d = max(abs(d), 0.01);
48 | acc += exp(-d * 3.0);
49 | t += d;
50 | }
51 |
52 | acc *= 0.03;
53 | vec3 col = vec3(0.00, 0.56, 1.00) * acc;
54 | outColor = vec4(col, 1.0);
55 | }
56 |
57 | //----------------------------
58 | // Reference
59 | //----------------------------
60 | // 魔法使いになりたい人のためのシェーダーライブコーディング入門
61 | // https://qiita.com/kaneta1992/items/21149c78159bd27e0860
--------------------------------------------------------------------------------
/src/20240312/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | const float PI = acos(-1.0);
15 |
16 | vec3 hash(vec3 v) {
17 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
18 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
19 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
20 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
21 | return vec3(x) / vec3(-1u);
22 | }
23 |
24 | float pattern(vec2 uv, float n) {
25 | vec2 suv = uv * 2.0 - 1.0;
26 | float len = length(suv);
27 | float p = step(sin(len * PI * n), 0.0);
28 | if (mod(n, 2.0) == 1.0) p = 1.0 - p;
29 | p *= step(len, 1.0) * step(0.1, n);
30 | return p;
31 | }
32 |
33 | void main() {
34 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
35 |
36 | float bt = floor(time * 30.0 / 60.0);
37 |
38 | vec2 quv = uv * asp * 1.1, fuv, iuv;
39 | vec3 h;
40 | for (int i = 0; i < 5; i++) {
41 | fuv = fract(quv);
42 | iuv = floor(quv);
43 | if (0 < i && (h = hash(vec3(iuv, bt))).x < (0.3 + float(i) * 0.1)) break;
44 | quv *= 2.0;
45 | }
46 |
47 | float n = floor(h.y * 6.0);
48 | float c = pattern(fuv, n);
49 |
50 | if (h.z < 0.5) c = 1.0 - c;
51 |
52 | vec3 col = mix(vec3(1) * 0.93, vec3(1), c);
53 |
54 | vec3 b = texture(backBuffer, uv).rgb;
55 | col = mix(b, col, 0.5);
56 |
57 | outColor = vec4(col, 1.0);
58 | }
59 |
60 | //----------------------------
61 | // Reference
62 | //----------------------------
--------------------------------------------------------------------------------
/src/20240221/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform int frame;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | #define loop(n) for(int i; i < n; i++)
14 |
15 | const float PI = acos(-1.0);
16 |
17 | mat2 rot(float a) {
18 | float s = sin(a), c = cos(a);
19 | return mat2(c, s, -s, c);
20 | }
21 |
22 | void main() {
23 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
24 |
25 | float lt = time * 30.0 / 60.0;
26 | float bt = floor(lt);
27 | float tt = tanh(fract(lt) * 5.0);
28 |
29 | suv *= 1.0 - length(suv) * (1.0 - tt);
30 |
31 | vec2 z, c;
32 | if (mod(bt, 3.0) == 0.0) {
33 | z = vec2(0) + ((1.0 - tt * tt) * 0.5);
34 | c = suv + vec2(-0.5, 0.0);
35 | } else if (mod(bt, 3.0) == 1.0) {
36 | z = suv * rot(PI * 0.5) * 0.5;
37 | c = vec2(0.25, 0.58) * (tt * tt * 0.05 + 0.95);
38 | } else {
39 | z = suv * rot(PI * 0.5) * 0.5;
40 | c = vec2(0.25, 0.6) * (tt * tt * 0.05 + 0.95) + (suv + 0.3) * 0.07;
41 | }
42 |
43 | float j;
44 | loop(70) {
45 | z = vec2(z.x * z.x - z.y * z.y, 2.0 * z.x * z.y) + c;
46 | if (4.0 < dot(z, z)) break;
47 | j++;
48 | }
49 |
50 | float lum = j / 60.0;
51 | lum = smoothstep(0.35, 1.0, lum);
52 |
53 | outColor = vec4(vec3(lum), 1.0);
54 | }
55 |
56 | //----------------------------
57 | // Reference
58 | //----------------------------
59 | // z(n+1) = z(n)^2 + c. z, c: complex number
60 | // https://wgld.org/d/glsl/g005.html
61 | // https://wgld.org/d/glsl/g006.html
--------------------------------------------------------------------------------
/src/20240207/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 | precision highp int;
4 |
5 | uniform sampler2D backBuffer;
6 | uniform vec2 resolution;
7 | uniform vec2 mouse;
8 | uniform float time;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | #define loop(i, n) for(int i; i < n; i++)
14 |
15 | vec3 hash(vec3 v) {
16 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
17 | x = (x >> 8 ^ x.zxy) * 0x456789ABu;
18 | x = (x >> 8 ^ x.zxy) * 0x6789AB45u;
19 | x = (x >> 8 ^ x.zxy) * 0x89AB4567u;
20 | return vec3(x) / vec3(-1u);
21 | }
22 |
23 | void main() {
24 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
25 |
26 | float lt = time * 30.0 / 60.0;
27 | float bt = floor(lt);
28 |
29 | float sp = 32.0;
30 | loop(i, 3) {
31 | if(hash(vec3(vec2(0.1, 0.2) * float(i), bt)).x < 0.5) break;
32 | sp *= 1.5;
33 | }
34 |
35 | vec2 iuv = floor(uv * asp * sp);
36 | float x = mod(floor(iuv.y / 9.0), 2.0) * 8.0;
37 | iuv = mod(iuv, vec2(32.0, 9.0));
38 |
39 | uint[8] rows = uint[](
40 | (0x0d8u << 16) + 0x0d8u,
41 | (0x505u << 16) + 0x505u,
42 | (0x5fdu << 16) + 0x5fdu,
43 | (0x7ffu << 16) + 0x7ffu,
44 | (0x376u << 16) + 0x376u,
45 | (0x1fcu << 16) + 0x1fcu,
46 | (0x088u << 16) + 0x088u,
47 | (0x104u << 16) + 0x104u
48 | );
49 |
50 | float c;
51 | if (int(iuv.y) < rows.length()) {
52 | uint b = rows[int(iuv.y)];
53 | float shift = 0.0 < sign(x) ? iuv.x : 32.0 - iuv.x;
54 | b = (b << uint(shift + x + lt * 4.0)) >> 31;
55 | c = float(b);
56 | }
57 |
58 | vec4 b = texture(backBuffer, uv);
59 | vec3 col = vec3(c, b.rg);
60 |
61 | outColor = vec4(col, 1.0);
62 | }
--------------------------------------------------------------------------------
/src/20240214/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | #define loop(n) for(int i; i < n; i++)
13 | #define sat(v) clamp(v, 0.0, 1.0)
14 |
15 | const float PI = acos(-1.0);
16 |
17 | mat2 rot(float a) {
18 | float s = sin(a), c = cos(a);
19 | return mat2(c, s, -s, c);
20 | }
21 |
22 | float box(vec3 p, vec3 b) {
23 | p = abs(p) - b;
24 | return max(p.x, max(p.y, p.z));
25 | // return length(max(p, 0.0)) + min(max(p.x, max(p.y, p.z)), 0.0);
26 | }
27 |
28 | float sdf(vec3 p) {
29 | p.xy *= rot(-p.z * PI * 0.03);
30 | p.z += fract(-time) * 3.0;
31 |
32 | p = mod(p, 3.0) - 1.5;
33 |
34 | float d = 1e4;
35 | d = min(d, length(p.xz) - 0.05);
36 | d = min(d, length(p.yz) - 0.05);
37 | d = min(d, length(p.xy) - 0.05);
38 | d = max(d, box(p, vec3(0.5)));
39 | return d;
40 | }
41 |
42 | void main() {
43 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
44 | vec3 rd = normalize(vec3(suv, -2.0 - length(suv) * 0.5)), ro = vec3(0.0, 0.0, 10.0);
45 |
46 | float t, acc;
47 | loop(64) {
48 | vec3 p = rd * t + ro;
49 | float d = sdf(p) * 0.7;
50 | if (d < 1e-4 || 1e4 < t) break;
51 | t += d;
52 | acc += exp(abs(d) * -20.0);
53 | }
54 |
55 | float c = acc / 64.0;
56 |
57 | vec4 b = texture(backBuffer, uv);
58 | vec3 col = vec3(sat(c), b.rg);
59 | col = mix(col, b.rgb, 0.3) * 1.1;
60 |
61 | outColor = vec4(col, 1.0);
62 | }
63 |
64 | //----------------------------
65 | // Reference
66 | //----------------------------
--------------------------------------------------------------------------------
/src/20240308/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | #define sat(v) clamp(v, 0.0, 1.0)
15 |
16 | const float PI = acos(-1.0);
17 | const float p = 3.0, q = 10.0;
18 |
19 | float sdSegment(in vec2 p, in vec2 a, in vec2 b) {
20 | vec2 pa = p - a, ba = b - a;
21 | float h = clamp(dot(pa, ba) / dot(ba, ba), 0.0, 1.0);
22 | return length(pa - ba * h);
23 | }
24 |
25 | vec3 torusknot(float t) {
26 | float r = 1.0 + 0.5 * cos(2.0 * PI * p * t);
27 | float theta = 2.0 * PI * q * t;
28 | float z = 0.5 * sin(2.0 * PI * p * t);
29 | return vec3(r * cos(theta), r * sin(theta), z);
30 | }
31 |
32 | void main() {
33 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
34 | vec4 b = texture(backBuffer, uv);
35 |
36 | float fps = round(1.0 / (time - prevTime));
37 | // float speed = 0.1;
38 | float speed = 3.0; // star
39 | // float speed = 2.0; // rectangle
40 | vec2 p1 = torusknot(fract(prevTime * speed)).xy;
41 | vec2 p2 = torusknot(fract(time * speed)).xy;
42 | float l = smoothstep(0.01, 0.00, sdSegment(suv * 2.0, p1, p2));
43 |
44 | b.rgb *= step(0.1, b.rgb);
45 | vec3 col = vec3(sat(l), b.rg);
46 | col = mix(b.rgb, col * 5.0, 0.2);
47 |
48 | outColor = vec4(col, 1.0);
49 | }
50 |
51 | //----------------------------
52 | // Reference
53 | //----------------------------
54 | // https://ja.wikipedia.org/wiki/%E3%83%88%E3%83%BC%E3%83%A9%E3%82%B9%E7%B5%90%E3%81%B3%E7%9B%AE
55 | // https://iquilezles.org/articles/distfunctions2d/
--------------------------------------------------------------------------------
/src/20240217/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | #define loop(n) for(int i; i < n; i++)
13 |
14 | mat2 rot(float a) {
15 | float s = sin(a), c = cos(a);
16 | return mat2(c, s, -s, c);
17 | }
18 |
19 | vec3 hash(vec3 v) {
20 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
21 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
22 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
23 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
24 | return vec3(x) / vec3(-1u);
25 | }
26 |
27 | float box(vec3 p, vec3 b) {
28 | p = abs(p) - b;
29 | return max(p.x, max(p.y, p.z));
30 | }
31 |
32 | float sdf(vec3 p) {
33 | float d = 1e9;
34 |
35 | p.xy *= rot(time * 0.5);
36 | p.yz *= rot(time * 0.4);
37 | p.zx *= rot(time * 0.3);
38 |
39 | vec2 cb = vec2(0.48, 1.0);
40 | d = min(d, box(p, cb.xxy));
41 | d = min(d, box(p, cb.xyx));
42 | d = min(d, box(p, cb.yxx));
43 | d = max(-d, box(p, vec3(0.5)));
44 | return d;
45 | }
46 |
47 | void main() {
48 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
49 | suv = floor(suv * 50.0) / 50.0;
50 | vec3 rd = normalize(vec3(suv, -5.0)), ro = vec3(0.0, 0.0, 5.0);
51 |
52 | float t;
53 | loop(64) {
54 | vec3 p = rd * t + ro;
55 | float d = sdf(p);
56 | if (d < 1e-4 || 1e4 < t) break;
57 | t += d;
58 | }
59 |
60 | vec3 h = hash(vec3(suv, step(t, 1e4)));
61 | outColor = vec4(vec3(step(h.x, 0.5)), 1.0);
62 | }
63 |
64 | //----------------------------
65 | // Reference
66 | //----------------------------
67 | // https://x.com/matthen2/status/1758504190987423850?s=20
--------------------------------------------------------------------------------
/src/20240311/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | vec3 hash(vec3 v) {
15 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
16 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
17 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
18 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
19 | return vec3(x) / vec3(-1u);
20 | }
21 |
22 | float pattern(vec2 uv, float n) {
23 | float c = 0.0;
24 | vec2 auv = abs(uv * 2.0 - 1.0);
25 | float s = 1.0 / n;
26 | for (float i = 1.0; i < n; i++) {
27 | float a = step(auv.x, 1.0 - s * i) * step(auv.y, 1.0 - s * i);
28 | c = mix(c, mod(i, 2.0) == 0.0 ? 0.0 : 1.0, a);
29 | }
30 | return c;
31 | }
32 |
33 | void main() {
34 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
35 |
36 | float bt = floor(time * 30.0 / 60.0);
37 |
38 | vec2 quv = uv * asp * 1.1, fuv, iuv;
39 | vec3 h;
40 | for (int i = 0; i < 5; i++) {
41 | fuv = fract(quv);
42 | iuv = floor(quv);
43 | if (0 < i && (h = hash(vec3(iuv, bt))).x < (0.2 + float(i) * 0.1)) break;
44 | quv *= 2.0;
45 | }
46 |
47 | // 1, 3, 4, 5, 6
48 | float n = ceil(h.y * 6.0);
49 | if (n == 2.0) n = 1.0;
50 | float c = pattern(fuv, n);
51 |
52 | if (h.z < 0.5) c = 1.0 - c;
53 |
54 | vec3 col = mix(vec3(1) * 0.93, vec3(1), c);
55 |
56 | vec3 b = texture(backBuffer, uv).rgb;
57 | col = mix(b, col, 0.5);
58 |
59 | outColor = vec4(col, 1.0);
60 | }
61 |
62 | //----------------------------
63 | // Reference
64 | //----------------------------
65 | // https://unshift.jp/
--------------------------------------------------------------------------------
/src/20240303/output.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D source;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform int frame;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | // const float BAYER[16] = float[](
14 | // 0.0, 8.0, 2.0, 10.0,
15 | // 12.0, 4.0, 14.0, 6.0,
16 | // 3.0, 11.0, 1.0, 9.0,
17 | // 15.0, 7.0, 13.0, 5.0
18 | // );
19 |
20 | const float BAYER[64] = float[](
21 | 0.0, 32.0, 8.0, 40.0, 2.0, 34.0, 10.0, 42.0,
22 | 48.0, 16.0, 56.0, 24.0, 50.0, 18.0, 58.0, 26.0,
23 | 12.0, 44.0, 4.0, 36.0, 14.0, 46.0, 6.0, 38.0,
24 | 60.0, 28.0, 52.0, 20.0, 62.0, 30.0, 54.0, 22.0,
25 | 3.0, 35.0, 11.0, 43.0, 1.0, 33.0, 9.0, 41.0,
26 | 51.0, 19.0, 59.0, 27.0, 49.0, 17.0, 57.0, 25.0,
27 | 15.0, 47.0, 7.0, 39.0, 13.0, 45.0, 5.0, 37.0,
28 | 63.0, 31.0, 55.0, 23.0, 61.0, 29.0, 53.0, 21.0
29 | );
30 |
31 | void main() {
32 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
33 |
34 | vec3 col = texture(source, uv).rgb;
35 | float luma = dot(col, vec3(0.299, 0.587, 0.114));
36 |
37 | // ivec2 bayerCoord = ivec2(mod(gl_FragCoord.xy, 4.0));
38 | // float threshold = BAYER[bayerCoord.y * 4 + bayerCoord.x] / 16.0;
39 |
40 | ivec2 bayerCoord = ivec2(mod(gl_FragCoord.xy, 8.0));
41 | float threshold = BAYER[bayerCoord.y * 8 + bayerCoord.x] / 64.0;
42 |
43 | float g = step(threshold, luma);
44 | outColor = vec4(vec3(g), 1.0);
45 | }
46 |
47 | //----------------------------
48 | // Reference
49 | //----------------------------
50 | // https://scrapbox.io/0b5vr/Bayer_matrix
51 | // https://github.com/hughsk/glsl-dither/tree/master
52 | // https://ja.wikipedia.org/wiki/%E9%85%8D%E5%88%97%E3%83%87%E3%82%A3%E3%82%B6%E3%83%AA%E3%83%B3%E3%82%B0
--------------------------------------------------------------------------------
/src/20240210/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | #define loop(n) for(int i; i < n; i++)
13 |
14 | const float PI = acos(-1.0);
15 |
16 | mat2 rot(float a) {
17 | float s = sin(a), c = cos(a);
18 | return mat2(c, s, -s, c);
19 | }
20 |
21 | vec2 pmod(vec2 p, float r) {
22 | float n = PI * 2.0 / r;
23 | float a = atan(p.x, p.y) + n * 0.5;
24 | a = floor(a / n) * n;
25 | return rot(a) * p;
26 | }
27 |
28 | vec3 hash(vec3 v) {
29 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
30 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
31 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
32 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
33 | return vec3(x) / vec3(-1u);
34 | }
35 |
36 | void main() {
37 | vec2 uv = vUv;
38 | vec2 asp = resolution / min(resolution.x, resolution.y);
39 |
40 | float lt = time * 120.0 / 60.0;
41 | float bt = floor(lt);
42 | float tt = tanh(fract(lt) * 5.0);
43 | lt = bt + tt;
44 |
45 | vec2 quv = uv * asp, fuv, iuv;
46 | float n = 2.0;
47 | loop(4) {
48 | n += 1.0;
49 | fuv = fract(quv);
50 | iuv = floor(quv);
51 | if (hash(vec3(iuv, bt)).x < 0.5) break;
52 | quv *= 2.0;
53 | }
54 |
55 | vec2 suv = fuv * 2.0 - 1.0;
56 | suv *= rot(PI / n * lt);
57 |
58 | float scale = 1.5 + exp((-n + 3.0) * 3.0) * 0.5;
59 | vec2 puv = pmod(-suv * scale, n);
60 | float c = step(fract(puv.x * 10.0 + puv.y * 10.0 - time * 5.0), 0.3) * step(0.5, puv.y) * step(puv.y, 0.7);
61 |
62 | vec4 b = texture(backBuffer, vUv);
63 | vec3 col = vec3(c, b.rg);
64 |
65 | outColor = vec4(col, 1.0);
66 | }
67 |
68 | //----------------------------
69 | // Reference
70 | //----------------------------
--------------------------------------------------------------------------------
/src/20240219/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform int frame;
9 | uniform samplerCube cubeTextureUnit;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | #define loop(n) for(int i; i < n; i++)
15 |
16 | const float PI = acos(-1.0);
17 | float lt, bt, tt;
18 |
19 | mat2 rot(float a) {
20 | float s = sin(a), c = cos(a);
21 | return mat2(c, s, -s, c);
22 | }
23 |
24 | float sdf(vec3 p) {
25 | p.xy *= rot(lt * PI * 0.05);
26 | p.yz *= rot(lt * PI * 0.10);
27 | p.zx *= rot(lt * PI * 0.15);
28 |
29 | vec3 bp = abs(p) - 0.5 + sin(lt * PI * 0.25) * 0.25;
30 | float b = max(bp.x, max(bp.y, bp.z));
31 |
32 | return max(b, dot(normalize(vec3(1)), abs(p)) - 0.43);
33 | }
34 |
35 | void main() {
36 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
37 | vec3 rd = normalize(vec3(suv, -5.0)), ro = vec3(0.0, 0.0, 5.0);
38 |
39 | lt = time * 120.0 / 60.0;
40 | bt = floor(lt);
41 | tt = tanh(fract(lt) * 5.0);
42 | lt = bt + tt;
43 |
44 | float t;
45 | loop(64) {
46 | vec3 p = rd * t + ro;
47 | float d = sdf(p);
48 | if (d < 1e-4 || 1e4 < t) break;
49 | t += d;
50 | }
51 |
52 | vec3 col;
53 | if (t < 1e4) {
54 | vec3 p = rd * t + ro;
55 | vec2 e = vec2(1e-2, 0.0);
56 | vec3 n = normalize(vec3(
57 | sdf(p + e.xyy) - sdf(p - e.xyy),
58 | sdf(p + e.yxy) - sdf(p - e.yxy),
59 | sdf(p + e.yyx) - sdf(p - e.yyx)
60 | ));
61 | vec3 reflection = reflect(rd, n);
62 | col = texture(cubeTextureUnit, reflection).rgb;
63 | }
64 |
65 | outColor = vec4(col, 1.0);
66 | }
67 |
68 | //----------------------------
69 | // Reference
70 | //----------------------------
71 | // リアルタイムグラフィックスの数学 ― GLSLではじめるシェーダプログラミング
72 | // hash関数:https://www.shadertoy.com/view/XlXcW4
--------------------------------------------------------------------------------
/src/20240306/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform int frame;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | void main() {
14 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
15 | vec2 p = uv * asp * 6.0;
16 |
17 | for (float i = 0.0; i < 8.0; i++) {
18 | p.x += sin(p.y + i + time * 0.3);
19 | p *= mat2(6, -8, 8, 6) / 8.0;
20 | }
21 |
22 | vec3 col = sin(p.xyx * 0.3 + vec3(0, 1, 2)) * 0.5 + 0.5;
23 | outColor = vec4(col, 1.0);
24 | }
25 |
26 | //----------------------------
27 | // Reference
28 | //----------------------------
29 | // https://twitter.com/XorDev/status/1765032092721648044
30 | // https://www.shadertoy.com/view/lXXXzS
31 |
32 | //----------------------------
33 | // Commnets by @XorDev
34 | //----------------------------
35 | /**
36 | "Cheap Turbulence" by @XorDev
37 |
38 | Simulating proper fluid dynamics can be complicated and requires a back buffer or multi-pass setup.
39 |
40 | Sometimes, you just want to emulate some smoke or something simple, and you don't want to go through all that trouble.
41 |
42 | This method is very simple! Start with pixel coordinates and scale them down as desired, then with a for loop,
43 | you should do a sine wave offset. In my case I'm doing "p.x+=sin(p.y)".
44 | To animate it, you can add a time offset to the sine wave, and it also helps to shift each iteration with the
45 | iterator "i" to break up visible patterns.
46 |
47 | Next, you want to rotate the coordinates and scale down. It could be as simple as p=p.yx/0.8 or a rotation matrix like mat2(.8,-.6,.6,.8).
48 |
49 | Now the resulting p coordinates will appear turbulent, and you can use these coordinates in color function.
50 | My color equation looks like this:
51 |
52 | fragColor=sin(p.xyxy*.3+vec4(0,1,2,3))*.5+.5
53 |
54 | Smooth, continious equations look best
55 | */
56 |
--------------------------------------------------------------------------------
/src/20240204_2/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 | precision highp int;
4 |
5 | uniform sampler2D backBuffer;
6 | uniform vec2 resolution;
7 | uniform vec2 mouse;
8 | uniform float time;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | uvec3 uhash(vec3 p) {
14 | uvec3 x = floatBitsToUint(p + vec3(0.1, 0.2, 0.3));
15 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
16 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
17 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
18 | return x;
19 | }
20 |
21 | // vec3 hash(vec3 p) {
22 | // uvec3 x = floatBitsToUint(p + vec3(0.1, 0.2, 0.3));
23 | // x = (x >> 8 ^ x.yzx) * 0x456789ABu;
24 | // x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
25 | // x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
26 | // return vec3(x) / vec3(-1u);
27 | // }
28 |
29 | void main() {
30 | vec2 uv = vUv, asp = vec2(resolution.x / resolution.y, 1.0);
31 | uv *= vec2(32.0, 32.0 / asp);
32 |
33 | uint[16] a = uint[](
34 | uint(time),
35 | 0xbu,
36 | 9u,
37 | 0xbu ^ 9u,
38 | 0xffffffffu,
39 | 0xffffffffu + uint(time),
40 | floatBitsToUint(floor(time)),
41 | floatBitsToUint(-floor(time)),
42 | floatBitsToUint(11.5625),
43 | // ---
44 | floatBitsToUint(1.0),
45 | floatBitsToUint(2.0),
46 | floatBitsToUint(3.0),
47 | 3u,
48 | uint(3.0),
49 | -1u,
50 | uhash(vec3(floor(time * 10.0))).x
51 | );
52 |
53 | float c;
54 | if (a.length() - 1 < int(uv.y)) c = 0.0;
55 | else {
56 | uint b = a[int(uv.y)];
57 | b = (b << uint(uv.x)) >> 31;
58 | c = float(b);
59 | }
60 |
61 | if (fract(uv.x) < 0.05 || fract(uv.y) < 0.05) c = 0.1;
62 | if (int(uv.x) == 1 && fract(uv.x) < 0.05) c = 0.5;
63 | if (int(uv.x) == 9 && fract(uv.x) < 0.05) c = 0.5;
64 | if (int(uv.y) == 9 && fract(uv.y) < 0.05) c = 0.5;
65 |
66 | outColor = vec4(vec3(c), 1.0);
67 | }
68 |
69 | //----------------------------
70 | // Reference
71 | //----------------------------
72 | // リアルタイムグラフィックスの数学 ― GLSLではじめるシェーダプログラミング
73 | // hash関数:https://www.shadertoy.com/view/XlXcW4
--------------------------------------------------------------------------------
/src/20240218/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform int frame;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | #define sat(v) clamp(v, 0.0, 1.0)
14 |
15 | vec3 hash(vec3 v) {
16 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
17 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
18 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
19 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
20 | return vec3(x) / vec3(-1u);
21 | }
22 |
23 | void main() {
24 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
25 | float n = 100.0;
26 | vec2 fuv = (floor(uv * asp * n) + 0.5) / n / asp;
27 | vec2 px = 1.0 / n / asp;
28 |
29 | float cell;
30 | if (frame == 1) {
31 | cell = step(hash(vec3(fuv, 0.1)).x, 0.5);
32 | } else {
33 | if (frame % 5 == 0) {
34 | float r;
35 | for (float ix = -1.0; ix <= 1.0; ix++) {
36 | for (float iy = -1.0; iy <= 1.0; iy++) {
37 | if (ix == 0.0 && iy == 0.0) continue;
38 | r += texture(backBuffer, fuv + px * vec2(ix, iy)).a;
39 | }
40 | }
41 |
42 | if (0.5 < texture(backBuffer, fuv).a) {
43 | if (r == 2.0 || r == 3.0) cell = 1.0;
44 | else if (r <= 1.0) cell = 0.0;
45 | else if (4.0 <= r) cell = 0.0;
46 | } else {
47 | cell = float(r == 3.0);
48 | }
49 | } else {
50 | cell = texture(backBuffer, fuv).a;
51 | }
52 | }
53 |
54 | vec4 b = texture(backBuffer, uv);
55 | vec3 col = vec3(cell, b.rg);
56 | col = mix(col, b.rgb, 0.5);
57 |
58 | if (frame % 5 == 0) {
59 | vec2 m = (floor((mouse * 0.5 + 0.5) * asp * n) + 0.5) / n / asp;
60 | vec2 d = step(distance(m * asp, fuv * asp), px * 2.0);
61 | cell += float(hash(vec3(d, float(frame))).x < 0.5) * length(d);
62 | cell = sat(cell);
63 | }
64 |
65 | outColor = vec4(col, cell);
66 | }
67 |
68 | //----------------------------
69 | // Reference
70 | //----------------------------
--------------------------------------------------------------------------------
/src/20240422/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | const float SEED = SEED_VALUE;
15 | const float PI = acos(-1.0);
16 |
17 | #define h21(f2, f1) hash(vec3(f2, f1))
18 |
19 | vec3 hash(vec3 v) {
20 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
21 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
22 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
23 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
24 | return vec3(x) / vec3(-1u);
25 | }
26 |
27 | mat2 rot(float a) {
28 | float s = sin(a), c = cos(a);
29 | return mat2(c, s, -s, c);
30 | }
31 |
32 | void main() {
33 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = uv * 2.0 - 1.0;
34 |
35 | float lt = time * 100.0 / 60.0;
36 | float bt = floor(lt);
37 | float tt = tanh(fract(lt) * 3.0);
38 | lt = bt + tt;
39 |
40 | vec2 quv = suv * asp, fuv, iuv;
41 | // quv *= rot(PI * 0.1 + quv.y * 0.315);
42 | quv *= rot(PI * SEED + quv.y * 0.315);
43 | quv.x -= lt * 0.5;
44 |
45 | vec3 h;
46 | float i, n = 4.0;
47 | for (; i < n; i++) {
48 | fuv = fract(quv);
49 | iuv = floor(quv);
50 |
51 | if ((h = h21(iuv, 0.2)).x < 0.3) break;
52 |
53 | quv *= 2.0;
54 | }
55 |
56 | i = clamp(i, 0.0, n - 1.0);
57 | float qScale = pow(2.0, i);
58 |
59 | vec2 sfuv = fuv * 2.0 - 1.0, auv = abs(sfuv);
60 | float thin = 1.0 - 0.005 * qScale;
61 | float edge = smoothstep(thin, thin - 0.01 * qScale, auv.x) * smoothstep(thin, thin - 0.01 * qScale, auv.y);
62 | float disc = smoothstep(0.015 * qScale, (0.015 + 0.005) * qScale, length(sfuv));
63 | float marker = edge * disc;
64 | if (h.y < 0.1) marker = 0.0;
65 |
66 | vec3 c = mix(vec3(0.01, 0.04, 0.09), vec3(0.99, 0.97, 0.91), marker);
67 |
68 | vec4 b = texture(backBuffer, uv);
69 | vec3 col = mix(b.rgb, c, 0.5);
70 |
71 | outColor = vec4(vec3(marker), 1.0);
72 | outColor = vec4(col, 1.0);
73 | }
74 |
75 | //----------------------------
76 | // Reference
77 | //----------------------------
--------------------------------------------------------------------------------
/src/20240208/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 | precision highp int;
4 |
5 | uniform sampler2D backBuffer;
6 | uniform vec2 resolution;
7 | uniform vec2 mouse;
8 | uniform float time;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | const float PI = acos(-1.0);
14 |
15 | mat2 rot(float a) {
16 | float s = sin(a), c = cos(a);
17 | return mat2(c, s, -s, c);
18 | }
19 |
20 | void main() {
21 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
22 |
23 | vec2 suv = (uv * 2.0 - 1.0) * asp * 1.5;
24 | vec3 pos = vec3(suv, (sqrt(1.0 - dot(suv, suv)) + 0.5) / 0.5);
25 | vec3 normal = normalize(pos);
26 | if (0.0 < step(length(suv), 1.0)) uv += normal.xy * (1.0 - normal.z);
27 | else uv *= 1.5;
28 |
29 | vec2 iuv = floor(uv * 64.0 * asp);
30 | float r = floor(iuv.y / 9.0);
31 | iuv = mod(iuv, vec2(32.0, 9.0));
32 |
33 | uint[9] rows = uint[](
34 | (0x0d8u << 16) + 0x202u,
35 | (0x505u << 16) + 0x104u,
36 | (0x5fdu << 16) + 0x3feu,
37 | (0x7ffu << 16) + 0x7ffu,
38 | (0x376u << 16) + 0x777u,
39 | (0x1fcu << 16) + 0x5fdu,
40 | (0x088u << 16) + 0x489u,
41 | (0x104u << 16) + 0x104u,
42 | 0u
43 | );
44 |
45 | float t1 = time * 100.0 / 60.0;
46 | float t2 = t1 * 0.5;
47 | float bt = floor(t2);
48 | float tt = tanh(fract(t2) * 5.0);
49 |
50 | suv *= rot(-PI * 0.5 - PI / 12.0 * (bt + tt));
51 | float a = atan(suv.y, suv.x) / PI * 0.5 + 0.5;
52 |
53 | float c;
54 | if (int(iuv.y) < rows.length()) {
55 | uint b = rows[int(iuv.y)];
56 | if (a < 1.0 - tt) b = ~b;
57 | if (0.0 < mod(bt, 2.0)) b = ~b;
58 | float shift;
59 | if (0.0 < mod(floor(t1), 2.0)) shift += 16.0;
60 | if (0.0 < mod(r, 2.0)) shift += 8.0;
61 | b = (b << uint(iuv.x + shift + t1)) >> 31;
62 | c = float(b);
63 | }
64 |
65 | vec3 col = vec3(0.34, 1.00, 0.11) * c;
66 |
67 | vec3 l = vec3(1.0, 1.0, 4.0);
68 | float diffuse = max(dot(normal, normalize(l - pos)), 0.2);
69 | diffuse = diffuse * 0.7 + pow(diffuse, 30.0) * 0.3;
70 | col *= diffuse;
71 |
72 | outColor = vec4(col, 1.0);
73 | }
74 |
75 | //----------------------------
76 | // Reference
77 | //----------------------------
--------------------------------------------------------------------------------
/src/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 | Vite + TS
8 |
9 |
10 |
11 |
12 |
51 |
52 |
53 |
54 |
--------------------------------------------------------------------------------
/src/20240207_2/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 | precision highp int;
4 |
5 | uniform sampler2D backBuffer;
6 | uniform vec2 resolution;
7 | uniform vec2 mouse;
8 | uniform float time;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | #define sat(v) clamp(v, 0.0, 1.0)
14 |
15 | const float PI = acos(-1.0);
16 |
17 | vec3 hash(vec3 v) {
18 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
19 | x = (x >> 8 ^ x.zxy) * 0x456789ABu;
20 | x = (x >> 8 ^ x.zxy) * 0x6789AB45u;
21 | x = (x >> 8 ^ x.zxy) * 0x89AB4567u;
22 | return vec3(x) / vec3(-1u);
23 | }
24 |
25 | mat2 rot(float a) {
26 | float s = sin(a), c = cos(a);
27 | return mat2(c, s, -s, c);
28 | }
29 |
30 | void main() {
31 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y);
32 | float t = time * 60.0 / 60.0;
33 | float bt = floor(t);
34 | float tt = tanh(fract(t) * 5.0);
35 |
36 | uv = (uv - 0.5) * asp;
37 | uv = vec2(atan(uv.y, uv.x) / PI, 0.18 / length(uv));
38 | vec2 iuv = floor(uv * 64.0);
39 | float x = mod(floor(iuv.y / 9.0), 2.0);
40 | iuv = mod(iuv, vec2(32.0, 9.0));
41 |
42 | uint[8] rows = uint[](
43 | (0x0d8u << 16) + 0x0d8u,
44 | (0x505u << 16) + 0x505u,
45 | (0x5fdu << 16) + 0x5fdu,
46 | (0x7ffu << 16) + 0x7ffu,
47 | (0x376u << 16) + 0x376u,
48 | (0x1fcu << 16) + 0x1fcu,
49 | (0x088u << 16) + 0x088u,
50 | (0x104u << 16) + 0x104u
51 | );
52 |
53 | float c;
54 | if (int(iuv.y) < rows.length()) {
55 | float s = 0.0 < sign(x) ? iuv.x : 32.0 - iuv.x;
56 | uint b = rows[int(iuv.y)];
57 | b = (b << uint(s + t * 2.0)) >> 31;
58 | c = float(b);
59 | }
60 |
61 | float center = smoothstep(0.2, 0.03, distance((vUv - 0.5) * asp + 0.5, vec2(0.5)));
62 | c = sat(1.0 - c + center);
63 |
64 | uv = (vUv - 0.5) * asp;
65 | uv *= rot(-PI * 0.5 - PI * (bt + tt) * 1.0 / 12.0);
66 | uv = vec2(atan(uv.y, uv.x) / PI, length(uv));
67 | if (0.0 < mod(bt, 2.0)) c = mix(1.0 - c, c, step(uv.x * 0.5 + 0.5, fract(1.0 - tt)));
68 | else c = mix(c, 1.0 - c, step(uv.x * 0.5 + 0.5, fract(1.0 - tt)));
69 |
70 | outColor = vec4(vec3(c) * 0.9, 1.0);
71 | }
72 |
73 | //----------------------------
74 | // Reference
75 | //----------------------------
76 | // OpenGL Tunnel Effect Shader in GLSL
77 | // https://youtube.com/shorts/VF2R4tRdKMI?si=lvEY5fGEvz_d5TLy
--------------------------------------------------------------------------------
/src/20240418/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 | uniform sampler2D textureUnit;
11 |
12 | in vec2 vUv;
13 | out vec4 outColor;
14 |
15 | #define h21(v2, s) hash(vec3(v2, s))
16 | const float PI = acos(-1.0);
17 | const float SEED = SEED_VALUE;
18 |
19 | vec3 hash(vec3 v) {
20 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
21 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
22 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
23 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
24 | return vec3(x) / vec3(-1u);
25 | }
26 |
27 | mat2 rot(float a) {
28 | float s = sin(a), c = cos(a);
29 | return mat2(c, s, -s, c);
30 | }
31 |
32 | float easeInOutCubic(float x) {
33 | return x < 0.5 ? 4.0 * x * x * x : 1.0 - pow(-2.0 * x + 2.0, 3.0) / 2.0;
34 | }
35 |
36 | void main() {
37 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
38 | ivec2 tSize = textureSize(textureUnit, 0);
39 | float tAspect = float(tSize.x) / float(tSize.y);
40 | vec4 b = texture(backBuffer, uv);
41 |
42 | float lt = time * 15.0 / 60.0;
43 | float bt = floor(lt);
44 | float tt = easeInOutCubic(tanh(fract(lt) * 3.0));
45 | // float tt = tanh(fract(lt) * 5.0);
46 | lt = bt + tt;
47 |
48 | vec2 quv = suv, fuv, iuv;
49 | vec3 h;
50 | for (int i = 0; i < 4; i++) {
51 | fuv = fract(quv);
52 | iuv = floor(quv);
53 | if ((h = h21(iuv, float(i + 1) + bt + SEED)).x < 0.4) break;
54 | quv *= 2.0;
55 | }
56 |
57 | vec2 mapUv = fuv;
58 | mapUv += (h21(iuv, floor(time * 10.0)).xy * 2.0 - 1.0) * 0.02;
59 | mapUv = (mapUv - 0.5) * rot(floor(h21(iuv, bt + SEED).x * 4.0) / 4.0 * PI * 2.0) + 0.5;
60 | mapUv.x = floor(h.y * tAspect) / tAspect + mapUv.x / tAspect;
61 | vec4 text = texture(textureUnit, mapUv);
62 | vec3 txt = text.rgb * text.a;
63 |
64 | vec2 auv = abs(fuv * 2.0 - 1.0);
65 | txt *= step(auv.x, 0.9) * step(auv.y, 0.9);
66 |
67 | txt *= 1.0 - h21(uv, time).x * 0.3;
68 | txt *= 1.0 - step(h21(floor(uv * vec2(1000, 0)), time).x, 0.5) * 0.3;
69 |
70 | txt *= step(h.z, tt);
71 |
72 | outColor = vec4(mix(b.rgb, txt, 0.2), 1.0);
73 | }
74 |
75 | //----------------------------
76 | // Reference
77 | //----------------------------
--------------------------------------------------------------------------------
/src/20240206_2/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | #define loop(n) for(int i; i < n; i++)
13 | #define sat(v) clamp(v, 0.0, 1.0)
14 |
15 | const float PI = acos(-1.0);
16 |
17 | mat2 rot(float a) {
18 | float s = sin(a), c = cos(a);
19 | return mat2(c, s, -s, c);
20 | }
21 |
22 | float sdf(vec3 p) {
23 | float final = 1e9;
24 |
25 | vec3 bp = p;
26 |
27 | loop(5) {
28 | bp = abs(bp) - 0.5;
29 | bp.xy *= rot(1.0 * PI * 0.25);
30 | bp.xz *= rot(1.0 * PI * 0.25 - time * 0.5);
31 | }
32 |
33 | bp = abs(bp) - vec3(1.0, 0.3, 0.01);
34 | float b = max(bp.x, max(bp.y, bp.z));
35 | float c = p.z - 0.5;
36 | return max(b, c);
37 | }
38 |
39 | float raymarch(vec3 rd, vec3 ro) {
40 | float t;
41 | loop(128) {
42 | vec3 p = rd * t + ro;
43 | float d = sdf(p);
44 | if (d < 1e-5 || 1e9 < t) break;
45 | t += d;
46 | }
47 | return t;
48 | }
49 |
50 | vec3 calcNormal(vec3 p) {
51 | float h = 1e-4;
52 | vec2 k = vec2(1, -1);
53 | return normalize(vec3(
54 | k.xyy * sdf(p + k.xyy * h) +
55 | k.yxy * sdf(p + k.yxy * h) +
56 | k.yyx * sdf(p + k.yyx * h) +
57 | k.xxx * sdf(p + k.xxx * h)
58 | ));
59 | }
60 |
61 | void main() {
62 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv - 0.5) * asp * 2.0;
63 | vec3 rd = normalize(vec3(suv, -5.0)), ro = vec3(0.0, 0.0, 15.0);
64 |
65 | float t = raymarch(rd, ro);
66 |
67 | vec3 col;
68 | if (t < 1e9) {
69 | vec3 p = rd * t + ro;
70 | vec3 normal = calcNormal(p);
71 |
72 | vec3 l = vec3(5.0, 5.0, 10.0);
73 | float d = clamp(dot(normal, normalize(l - p)), 0.2, 1.0);
74 | col = vec3(d) * 0.5;
75 |
76 | vec3 reflection = reflect(rd, normal);
77 | ro = p + normal * 1e-4 * 2.0;
78 | t = raymarch(reflection, ro);
79 | if (t < 1e9) {
80 | vec3 rp = reflection * t + ro;
81 | normal = calcNormal(rp);
82 | d = clamp(dot(normal, normalize(l - rp)), 0.2, 1.0);
83 | col += vec3(d) * 0.5;
84 | }
85 | }
86 |
87 | outColor = vec4(col, 1.0);
88 | }
89 |
90 | //----------------------------
91 | // Reference
92 | //----------------------------
93 | // Iterated Function System(IFS)
94 | // https://qiita.com/kaneta1992/items/21149c78159bd27e0860
--------------------------------------------------------------------------------
/src/scripts/core/FrameBuffer.ts:
--------------------------------------------------------------------------------
1 | import * as THREE from 'three'
2 | import { params } from '../Params'
3 |
4 | export type Options = {
5 | dpr?: number
6 | matrixAutoUpdate?: boolean
7 | type?: THREE.TextureDataType
8 | }
9 |
10 | export abstract class FrameBuffer {
11 | protected readonly scene: THREE.Scene
12 | protected readonly camera: THREE.OrthographicCamera
13 | protected readonly renderTarget: THREE.WebGLRenderTarget
14 | private readonly screen: THREE.Mesh
15 |
16 | constructor(
17 | protected readonly renderer: THREE.WebGLRenderer,
18 | material: THREE.RawShaderMaterial,
19 | private options?: Options,
20 | ) {
21 | this.scene = new THREE.Scene()
22 | this.camera = new THREE.OrthographicCamera()
23 | this.renderTarget = this.createRenderTarget()
24 | this.screen = this.createScreen(material)
25 |
26 | this.setMatrixAutoUpdate(options?.matrixAutoUpdate ?? false)
27 | }
28 |
29 | private get devicePixelRatio() {
30 | return this.options?.dpr ?? params.dpr
31 | }
32 |
33 | private setMatrixAutoUpdate(v: boolean) {
34 | this.camera.matrixAutoUpdate = v
35 | this.scene.traverse((o) => (o.matrixAutoUpdate = v))
36 | }
37 |
38 | protected get size() {
39 | return { width: this.renderer.domElement.width * this.devicePixelRatio, height: this.renderer.domElement.height * this.devicePixelRatio }
40 | }
41 |
42 | protected createRenderTarget() {
43 | const rt = new THREE.WebGLRenderTarget(this.size.width, this.size.height, {
44 | type: this.options?.type ?? THREE.UnsignedByteType,
45 | generateMipmaps: false,
46 | minFilter: params.filterType,
47 | magFilter: params.filterType,
48 | wrapS: THREE.RepeatWrapping,
49 | wrapT: THREE.RepeatWrapping,
50 | })
51 | return rt
52 | }
53 |
54 | private createScreen(material: THREE.RawShaderMaterial) {
55 | const geometry = new THREE.PlaneGeometry(2, 2)
56 | const mesh = new THREE.Mesh(geometry, material)
57 | this.scene.add(mesh)
58 | return mesh
59 | }
60 |
61 | get uniforms() {
62 | return this.screen.material.uniforms
63 | }
64 |
65 | resize() {
66 | this.renderTarget.setSize(this.size.width, this.size.height)
67 | }
68 |
69 | get texture() {
70 | return this.renderTarget.texture
71 | }
72 |
73 | render(..._args: any[]) {
74 | this.renderer.setRenderTarget(this.renderTarget)
75 | this.renderer.render(this.scene, this.camera)
76 | }
77 | }
78 |
--------------------------------------------------------------------------------
/src/20240401/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform float prevTime;
9 | uniform int frame;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | float rand(vec2 n) {
15 | return fract(sin(dot(n, vec2(12.9898, 4.1414))) * 43758.5453);
16 | }
17 |
18 | float noise(vec2 p) {
19 | vec2 ip = floor(p);
20 | vec2 u = fract(p);
21 | u = u * u * (3.0 - 2.0 * u);
22 | float res = mix(mix(rand(ip), rand(ip + vec2(1.0, 0.0)), u.x), mix(rand(ip + vec2(0.0, 1.0)), rand(ip + vec2(1.0, 1.0)), u.x), u.y);
23 | return res * res;
24 | }
25 |
26 | float fbm(vec2 x, int octaves) {
27 | float v = 0.0;
28 | float a = 0.5;
29 | vec2 shift = vec2(100);
30 | // Rotate to reduce axial bias
31 | mat2 rot = mat2(cos(0.5), sin(0.5), -sin(0.5), cos(0.50));
32 | for (int i = 0; i < octaves; ++i) {
33 | v += a * noise(x);
34 | x = rot * x * 2.0 + shift;
35 | a *= 0.5;
36 | }
37 | return v;
38 | }
39 |
40 | float blendDarken(float base, float blend) {
41 | return min(blend, base);
42 | }
43 |
44 | vec3 blendDarken(vec3 base, vec3 blend) {
45 | return vec3(blendDarken(base.r, blend.r), blendDarken(base.g, blend.g), blendDarken(base.b, blend.b));
46 | }
47 |
48 | vec3 blendDarken(vec3 base, vec3 blend, float opacity) {
49 | return (blendDarken(base, blend) * opacity + base * (1.0 - opacity));
50 | }
51 |
52 | void main() {
53 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
54 |
55 | if (frame == 1) {
56 | vec2 auv = abs(suv);
57 | float c = step(length(suv), 0.1);
58 | vec3 col = mix(vec3(1), vec3(0), c);
59 | outColor = vec4(col, 1.0);
60 | return;
61 | }
62 |
63 | float disp = fbm(suv * 15.0, 4) * 0.005;
64 |
65 | vec3 t1 = texture(backBuffer, uv).rgb;
66 | vec3 t2 = texture(backBuffer, uv + vec2(disp, 0.0) / asp).rgb;
67 | vec3 t3 = texture(backBuffer, uv - vec2(disp, 0.0) / asp).rgb;
68 | vec3 t4 = texture(backBuffer, uv + vec2(0.0, disp) / asp).rgb;
69 | vec3 t5 = texture(backBuffer, uv - vec2(0.0, disp) / asp).rgb;
70 |
71 | vec3 col = t1;
72 | col = blendDarken(col, t2, 0.65);
73 | col = blendDarken(col, t3, 0.65);
74 | col = blendDarken(col, t4, 0.65);
75 | col = blendDarken(col, t5, 0.65);
76 |
77 | outColor = vec4(col, 1.0);
78 | }
79 |
80 | //----------------------------
81 | // Reference
82 | //----------------------------
83 | // https://www.youtube.com/live/ggruH0fHPOM?si=M8GiPSTCQOTP_JXs
84 | // https://gist.github.com/patriciogonzalezvivo/670c22f3966e662d2f83
85 | // https://github.com/jamieowen/glsl-blend/blob/master/darken.glsl
--------------------------------------------------------------------------------
/src/20240304/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform int frame;
9 |
10 | in vec2 vUv;
11 | out vec4 outColor;
12 |
13 | #define loop(n) for(int i;i> 8 ^ x.yzx) * 0x456789ABu;
21 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
22 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
23 | return vec3(x) / vec3(-1u);
24 | }
25 |
26 | // Classic Perlin 2D Noise
27 | // by Stefan Gustavson
28 | //
29 | vec2 fade(vec2 t) {
30 | return t * t * t * (t * (t * 6.0 - 15.0) + 10.0);
31 | }
32 | vec4 permute(vec4 x) {
33 | return mod(((x * 34.0) + 1.0) * x, 289.0);
34 | }
35 |
36 | float cnoise(vec2 P) {
37 | vec4 Pi = floor(P.xyxy) + vec4(0.0, 0.0, 1.0, 1.0);
38 | vec4 Pf = fract(P.xyxy) - vec4(0.0, 0.0, 1.0, 1.0);
39 | Pi = mod(Pi, 289.0); // To avoid truncation effects in permutation
40 | vec4 ix = Pi.xzxz;
41 | vec4 iy = Pi.yyww;
42 | vec4 fx = Pf.xzxz;
43 | vec4 fy = Pf.yyww;
44 | vec4 i = permute(permute(ix) + iy);
45 | vec4 gx = 2.0 * fract(i * 0.0243902439) - 1.0; // 1/41 = 0.024...
46 | vec4 gy = abs(gx) - 0.5;
47 | vec4 tx = floor(gx + 0.5);
48 | gx = gx - tx;
49 | vec2 g00 = vec2(gx.x, gy.x);
50 | vec2 g10 = vec2(gx.y, gy.y);
51 | vec2 g01 = vec2(gx.z, gy.z);
52 | vec2 g11 = vec2(gx.w, gy.w);
53 | vec4 norm = 1.79284291400159 - 0.85373472095314 * vec4(dot(g00, g00), dot(g01, g01), dot(g10, g10), dot(g11, g11));
54 | g00 *= norm.x;
55 | g01 *= norm.y;
56 | g10 *= norm.z;
57 | g11 *= norm.w;
58 | float n00 = dot(g00, vec2(fx.x, fy.x));
59 | float n10 = dot(g10, vec2(fx.y, fy.y));
60 | float n01 = dot(g01, vec2(fx.z, fy.z));
61 | float n11 = dot(g11, vec2(fx.w, fy.w));
62 | vec2 fade_xy = fade(Pf.xy);
63 | vec2 n_x = mix(vec2(n00, n01), vec2(n10, n11), fade_xy.x);
64 | float n_xy = mix(n_x.x, n_x.y, fade_xy.y);
65 | return 2.3 * n_xy;
66 | }
67 |
68 | void main() {
69 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
70 |
71 | suv *= 1.3;
72 |
73 | float r = 0.15, sm = 0.005, w = 0.0015, c;
74 | vec2 n = vec2(cnoise(suv * 7.0 + SEED), cnoise(suv.yx * 10.0 + SEED)) * 0.015;
75 |
76 | float rn = 50.0;
77 | for (float i = 0.0; i <= rn; i++) {
78 | vec3 h = h21(vec2(i), SEED);
79 | float s = 1.0 + step(h.x, 0.2) * h.y * 1.5;
80 | if (i == rn) s = 20.0;
81 | else if (mod(i, 15.0) == 0.0) s = 2.5;
82 | c += smoothstep(r, r + sm, length(suv + n)) * smoothstep(r + w * s + sm, r + w * s, length(suv + n));
83 | r += 0.012;
84 | }
85 |
86 | vec3 b = vec3(1.00, 0.98, 0.95);
87 | vec3 col = mix(b, b * 0.92, c);
88 |
89 | outColor = vec4(col, 1.0);
90 | }
91 |
92 | //----------------------------
93 | // Reference
94 | //----------------------------
95 | // https://gardeneight.medium.com/anai-764dd1fc1dd6
96 | // https://anaiwood.com/en/brands/fil - credits
--------------------------------------------------------------------------------
/src/20240213_2/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 |
9 | in vec2 vUv;
10 | out vec4 outColor;
11 |
12 | #define loop(n) for(int i; i < n; i++)
13 | #define sat(v) clamp(v, 0.0, 1.0)
14 |
15 | const float PI = acos(-1.0);
16 |
17 | float lt, bt, tt;
18 | vec3 h;
19 |
20 | mat2 rot(float a) {
21 | float s = sin(a), c = cos(a);
22 | return mat2(c, s, -s, c);
23 | }
24 |
25 | vec3 hash(vec3 v) {
26 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
27 | x = (x >> 8 ^ x.zxy) * 0x457890ABu;
28 | x = (x >> 8 ^ x.zxy) * 0x7890AB45u;
29 | x = (x >> 8 ^ x.zxy) * 0x90AB4578u;
30 | return vec3(x) / vec3(-1u);
31 | }
32 |
33 | vec2 pmod(vec2 p, float r) {
34 | float n = PI * 2.0 / r;
35 | float a = atan(p.x, p.y) + n * 0.5;
36 | a = floor(a / n) * n;
37 | return rot(a) * p;
38 | }
39 |
40 | float box(vec3 p, vec3 b) {
41 | p = abs(p) - b;
42 | return length(max(p, 0.0)) + min(max(p.x, max(p.y, p.z)), 0.0);
43 | }
44 |
45 | float sdCross(vec3 p) {
46 | float da = max(p.x, p.y);
47 | float db = max(p.y, p.z);
48 | float dc = max(p.z, p.x);
49 | return min(da, min(db, dc)) - 1.0;
50 | }
51 |
52 | float sdf(vec3 p) {
53 | p = mod(p, 2.0) - 1.0;
54 |
55 | float b = box(p, vec3(1.0));
56 | float s = 1.0;
57 | loop(3) {
58 | vec3 a = mod(p * s, 2.0) - 1.0;
59 | s *= 4.0;
60 | vec3 r = abs(1.0 - 4.0 * abs(a));
61 | float c = sdCross(r) / s;
62 | b = max(b, c);
63 | }
64 |
65 | return b;
66 | }
67 |
68 | void main() {
69 | lt = time * 120.0 / 60.0;
70 | bt = floor(lt);
71 | tt = tanh(fract(lt) * 4.0);
72 | lt = bt + tt;
73 | float ft = fract(time);
74 |
75 | h = hash(vec3(bt));
76 |
77 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
78 |
79 | suv.x += sin(suv.y * 1000.0 + ft * 100.0 ) * 0.005;
80 | vec2 fuv = floor(suv * vec2(1, 1.5) * 2.0);
81 | vec3 fh = hash(vec3(fuv + bt, floor(ft * 40.0)));
82 | if (fh.x < 0.1 && h.x < 0.9) suv.x += sign(fh.y) * 0.05;
83 | if (0.0 < mod(floor(suv.y * 0.7 - time * 0.5), 2.0)) suv.x += sign(fh.z) * 0.05;
84 |
85 | vec3 rd = normalize(vec3(suv, -5.0 + length(suv) * 2.0)), ro = vec3(0.0, 0.0, 7.0);
86 |
87 | float t, acc;
88 | loop(64) {
89 | vec3 p = rd * t + ro;
90 | if (h.x < 0.9) {
91 | p.y -= 0.1;
92 | p.z -= lt * 0.6;
93 | } else {
94 | p.xy *= rot(t * 0.5);
95 | p.z -= ft * 6.0;
96 | }
97 | float d = sdf(p);
98 | if (d < 1e-4 || 1e4 < t) break;
99 | t += d;
100 | acc += exp(abs(d) * -300.0);
101 | }
102 |
103 | float c;
104 | if (h.y < 0.8) c = acc / 64.0 * 0.5;
105 | else c = fwidth(acc) * 0.02;
106 |
107 | float sc = step(fract(suv.y * 40.0 - fract(time) * 10.0), 0.8);
108 | c += sc * 0.07;
109 |
110 | vec4 b = texture(backBuffer, vUv);
111 | vec3 col = vec3(sat(c), b.rg);
112 | col = mix(col, b.rgb, 0.5) * 1.08;
113 |
114 | outColor = vec4(col, 1.0);
115 | }
116 |
117 | //----------------------------
118 | // Reference
119 | //----------------------------
120 | // https://iquilezles.org/articles/menger/
--------------------------------------------------------------------------------
/src/scripts/Canvas.ts:
--------------------------------------------------------------------------------
1 | import * as THREE from 'three'
2 | import { Three } from './core/Three'
3 | import vertexShader from './shader/quad.vs'
4 | import fragmentShader from './shader/output.fs'
5 | import { RawShaderMaterial } from './core/ExtendedMaterials'
6 | import { MainScene } from './MainScene'
7 | import { params } from './Params'
8 | import { mouse2d } from './Mouse2D'
9 |
10 | export class Canvas extends Three {
11 | private mainScene: MainScene
12 | private output: THREE.Mesh
13 |
14 | constructor(canvas: HTMLCanvasElement, mainFs: string, outputFs?: string) {
15 | super(canvas)
16 | this.mainScene = new MainScene(this.renderer, mainFs)
17 | this.output = this.createOutput(outputFs ?? fragmentShader)
18 |
19 | this.disableMatrixAutoUpdate()
20 |
21 | this.bindAssets().then(() => {
22 | window.addEventListener('resize', this.resize.bind(this))
23 | this.renderer.setAnimationLoop(this.anime.bind(this))
24 | })
25 | }
26 |
27 | private async bindAssets() {
28 | const texturePath = params.texturePath
29 | if (texturePath) {
30 | const loader = new THREE.TextureLoader()
31 | const texture = await loader.loadAsync(texturePath)
32 | texture.wrapS = THREE.RepeatWrapping
33 | texture.wrapT = THREE.RepeatWrapping
34 | texture.userData.aspect = texture.source.data.width / texture.source.data.height
35 | Object.assign(this.mainScene.uniforms, { textureUnit: { value: texture } })
36 | }
37 |
38 | const cubeMapPath = params.cubeMapPath
39 | if (cubeMapPath) {
40 | const loader = new THREE.CubeTextureLoader()
41 | loader.setPath(cubeMapPath)
42 | const texture = await loader.loadAsync(['px', 'nx', 'py', 'ny', 'pz', 'nz'].map((f) => f + '.webp'))
43 | Object.assign(this.mainScene.uniforms, { cubeTextureUnit: { value: texture } })
44 | }
45 | }
46 |
47 | private createOutput(fs: string) {
48 | const geometry = new THREE.PlaneGeometry(2, 2)
49 | const material = new RawShaderMaterial({
50 | uniforms: {
51 | source: { value: null },
52 | resolution: { value: [this.size.width, this.size.height] },
53 | mouse: { value: mouse2d.position },
54 | time: { value: 0 },
55 | frame: { value: 0 },
56 | },
57 | vertexShader,
58 | fragmentShader: fs,
59 | glslVersion: '300 es',
60 | })
61 | const mesh = new THREE.Mesh(geometry, material)
62 | this.scene.add(mesh)
63 | return mesh
64 | }
65 |
66 | private disableMatrixAutoUpdate() {
67 | this.camera.matrixAutoUpdate = false
68 | this.scene.traverse((o) => (o.matrixAutoUpdate = false))
69 | }
70 |
71 | private get uniforms() {
72 | return this.output.material.uniforms
73 | }
74 |
75 | private resize() {
76 | this.uniforms.resolution.value = [this.size.width, this.size.height]
77 | this.uniforms.time.value = 0
78 | this.uniforms.frame.value = 0
79 | this.mainScene.resize()
80 | }
81 |
82 | private anime() {
83 | if (params.enableStats) this.stats.update()
84 | this.updateTime()
85 |
86 | this.mainScene.render(this.time.delta)
87 |
88 | this.uniforms.source.value = this.mainScene.texture
89 | this.uniforms.mouse.value = mouse2d.position
90 | this.uniforms.time.value += this.time.delta
91 | this.uniforms.frame.value += 1
92 | this.render()
93 | }
94 | }
95 |
--------------------------------------------------------------------------------
/src/20240225/sketch.fs:
--------------------------------------------------------------------------------
1 | #version 300 es
2 | precision highp float;
3 |
4 | uniform sampler2D backBuffer;
5 | uniform vec2 resolution;
6 | uniform vec2 mouse;
7 | uniform float time;
8 | uniform int frame;
9 | uniform sampler2D textureUnit;
10 |
11 | in vec2 vUv;
12 | out vec4 outColor;
13 |
14 | #define loop(n) for(int i; i < n; i++)
15 | #define grad(p, h) sdf(p + h) - sdf(p - h)
16 |
17 | const float PI = acos(-1.0);
18 | float lt, bt, tt;
19 |
20 | mat2 rot(float a) {
21 | float s = sin(a), c = cos(a);
22 | return mat2(c, s, -s, c);
23 | }
24 |
25 | float box(vec3 p, vec3 b) {
26 | p = abs(p) - b;
27 | return max(p.x, max(p.y, p.z));
28 | }
29 |
30 | float gyroid(vec3 p, float s, float t, float b) {
31 | p *= s;
32 | p.xy *= rot(lt * 0.2);
33 | p.yz *= rot(lt * 0.2);
34 | p.zx *= rot(lt * 0.2);
35 | return abs(dot(sin(p), cos(p.zxy)) - b) / s - t;
36 | }
37 |
38 | vec3 transform(vec3 p) {
39 | p.xy *= rot(time * 0.1);
40 | p.yz *= rot(time * 0.1);
41 | p.zx *= rot(time * 0.1);
42 | return p;
43 | }
44 |
45 | vec3 hash(vec3 v) {
46 | uvec3 x = floatBitsToUint(v + vec3(0.1, 0.2, 0.3));
47 | x = (x >> 8 ^ x.yzx) * 0x456789ABu;
48 | x = (x >> 8 ^ x.yzx) * 0x6789AB45u;
49 | x = (x >> 8 ^ x.yzx) * 0x89AB4567u;
50 | return vec3(x) / vec3(-1u);
51 | }
52 |
53 | mat3 orthbas(vec3 z) {
54 | z = normalize(z);
55 | vec3 up = abs(z.y) < 0.999 ? vec3(0, 1, 0) : vec3(0, 0, 1);
56 | vec3 x = normalize(cross(up, z));
57 | return mat3(x, cross(z, x), z);
58 | }
59 |
60 | vec3 cyc(vec3 p) {
61 | mat3 b = orthbas(vec3(-3.0, 2.0, -1.0));
62 | vec4 n;
63 | loop(8) {
64 | p *= b;
65 | p += sin(p.yzx);
66 | n = 2.0 * n + vec4(cross(cos(p), sin(p.zxy)), 1.0);
67 | p *= 2.0;
68 | }
69 | return n.xyz / n.w;
70 | }
71 |
72 | float sdf(vec3 p) {
73 | float d = 1e9, g;
74 | d = min(d, box(p, vec3(0.7)));
75 | p += cyc(p * 0.2) * 0.5;
76 | g = gyroid(p, 8.0, 0.03, 1.3);
77 | d = max(d, g * 0.5);
78 | return d;
79 | }
80 |
81 | void main() {
82 | vec2 uv = vUv, asp = resolution / min(resolution.x, resolution.y), suv = (uv * 2.0 - 1.0) * asp;
83 | vec3 rd = normalize(vec3(suv, -5.0)), ro = vec3(0.0, 0.0, 6.0);
84 |
85 | lt = time * 100.0 / 60.0;
86 | bt = floor(lt);
87 | tt = tanh(fract(lt) * 5.0);
88 | lt = bt + tt;
89 |
90 | float t;
91 | loop(64) {
92 | vec3 p = rd * t + ro;
93 | p = transform(p);
94 | float d = sdf(p);
95 | if (d < 1e-4 || 1e5 < t) break;
96 | t += d;
97 | }
98 |
99 | vec3 col;
100 | if (t < 1e5) {
101 | vec3 p = rd * t + ro;
102 | p = transform(p);
103 |
104 | vec2 h = vec2(1e-4, 0.0);
105 | vec3 n = normalize(vec3(grad(p, h.xyy), grad(p, h.yxy), grad(p, h.yyx)));
106 |
107 | vec3 l = normalize(transform(vec3(1, 1, 2)));
108 | float diff = clamp(dot(n, l), 0.2, 1.0);
109 | col = vec3(diff);
110 |
111 | vec3 uv3 = p * 0.5 + 0.5;
112 | vec3 colXZ = texture(textureUnit, uv3.xz).rgb;
113 | vec3 colYZ = texture(textureUnit, uv3.yz).rgb;
114 | vec3 colXY = texture(textureUnit, uv3.xy).rgb;
115 |
116 | n = abs(n);
117 | col *= colYZ * n.x + colXZ * n.y + colXY * n.z;
118 | }
119 |
120 | outColor = vec4(col, 1.0);
121 | }
122 |
123 | //----------------------------
124 | // Reference
125 | //----------------------------
126 | // https://youtu.be/VaYyPTw0V84?si=eVov17jGvBxXqfgg
127 | // https://youtu.be/-adHIyjIYgk?si=nkXdxIpaVjTkXhPt
--------------------------------------------------------------------------------