-
Notifications
You must be signed in to change notification settings - Fork 43
/
NeuralCA.js
43 lines (42 loc) · 1.66 KB
/
NeuralCA.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
/** @license
* Copyright 2023 Google LLC.
* SPDX-License-Identifier: Apache-2.0
*/
// Based on "μNCA: Texture Generation with Ultra-Compact Neural Cellular Automata"
// https://arxiv.org/abs/2111.13545
class NeuralCA {
static Tags = ['2d', 'ca'];
constructor() {
this.W = new Float32Array([
-67,1,2,44,-13,-59,4,30,-1,16,-57,9,-10,-4,-2,-41, 19,-18,-1,8,-4,35,8,0,-4,-4,-1,0,34,31,21,-25,
4,13,18,-57,-79,-22,-25,71,-12,-11,24,27,-17,-8,-7,6, 11,10,4,0,4,1,2,7,-26,-33,-15,-3,22,27,20,-34]);
this.b = new Float32Array([2,-5,-14,9]);
}
frame(glsl, {DPR}) {
const state = glsl({W:this.W, b:this.b, FP:`
uniform mat4 W[4];
uniform vec4 b;
vec4 rule(vec4 s, vec4 p) {
return 1e-3*(b + W[0]*s + W[1]*p + W[2]*abs(s) + W[3]*abs(p));
}
void fragment() {
vec4 s = Src(UV);
if (s == vec4(0)) {
ivec2 I = ivec2(gl_FragCoord.xy);
FOut = 0.1+vec4(hash(I.xyy).x)*0.4;
return;
}
vec2 dp = Src_step();
float x=UV.x, y=UV.y;
float l=x-dp.x, r=x+dp.x, u=y-dp.y, d=y+dp.y;
#define R(x, y) Src(vec2(x, y))
// perception
vec4 p = R(l,u)*vec4(1,1,-1, 1) + R(x,u)*vec4(2,2,0, 2) + R(r,u)*vec4(1,1,1, 1)
+ R(l,y)*vec4(2,2,-2, 0) + s*vec4(-12,-12,0, 0) + R(r,y)*vec4(2,2,2, 0)
+ R(l,d)*vec4(1,1,-1,-1) + R(x,d)*vec4(2,2,0,-2) + R(r,d)*vec4(1,1,1,-1);
vec4 ds = rule(s-0.5, p); // NCA rule application
FOut = s+ds;
}`}, {story:2, scale:1/4/DPR, tag:'state'});
glsl({tex:state[0], FP:`tex(UV)*2.-.5`});
}
}