jevstrudel.git / website / src / repl / drawings.mjs
1export const lightflower = `Pattern.prototype.nest = function(n, cycles) {
2  n = reify(n)
3  return this.echo(n, pure(cycles).div(n), 1)
4}
5
6Pattern.prototype.deepimpose = function(func, times) {
7  if(times===0) return this;
8  return this.superimpose(x=>func(x).deepimpose(func, times-1))
9}
10
11angle(saw)
12  .fill('#aaffee12')
13  .r(.18)
14  .w(.06)
15  .h(.06)
16  .deepimpose(x=>x.mul(r(2).w(2).h(2)).late(1/12), 3)
17  .nest(6, 1)
18  .s('ellipse')
19  .mul(w(sine).h(sine).range(.5,1.25))
20  .off(.5, x=>x.fill('#ffeeaa12').rev().div(r(1.2)))
21  .slow(16)
22  .smear(0.6)
23  .animate({smear:0})
24`;
25
26// https://strudel.cc/?C31_NrcMfZEO
27export const spiralflower = `let {innerWidth:ww,innerHeight:wh} = window;
28ww*=window.devicePixelRatio;
29wh*=window.devicePixelRatio;
30const ctx = getDrawContext()
31const piDiv180 = Math.PI / 180;
32function fromPolar(angle, radius, cx, cy) {
33  const radians = (angle-90) * piDiv180
34  return [cx + Math.cos(radians) * radius, cy + Math.sin(radians) * radius]
35}
36const [w, h] = [200,200]
37const [cx,cy] = [ww/2,wh/2];
38function drawSpiralSegment(ctx, {angle,b,r, density = 2, color = 'darkseagreen', thick = 2, long = 1}) {
39  let i = angle;
40  ctx.beginPath();
41  while(i < b){
42    const radius = Math.max(Math.min(r - i*.2,1000),20);
43    const [x1,y1] = fromPolar(i, radius, cx, cy)
44    const [x2,y2] = fromPolar(i, radius+long, cx, cy)
45    ctx.lineWidth = thick;
46    ctx.moveTo(x1,y1);
47    ctx.strokeStyle= color
48    ctx.lineTo(x2,y2);
49    ctx.stroke()
50    i+=300/density;
51  }
52}
53const { r, angle, b, color, density,thick} = 
54  createParams('r', 'angle', 'b', 'color','density','thick','long');
55
56
57const pattern = 
58  r(sine.range(200,800).slow(4))
59  .angle(cosine.range(0, 45).slow(3))
60  .b(perlin.range(1000, 4000).slow(5))
61  .thick(sine.range(2,50).slow(2))
62  .long(perlin.range(1,100).slow(3))
63  .off(1, x=>x.color('white'))
64  .off(2, x=>x.color('salmon'))
65  .off(4, x=>x.color('purple'))
66  .slow(4)//.mask("x(5,8)")
67
68
69function onDraw(f) {  
70  ctx.beginPath();
71  drawSpiralSegment(ctx, f.value);
72}
73
74
75// generic draw logic
76window.frame && cancelAnimationFrame(window.frame);
77
78function render(t) {
79  t = Math.round(t)
80  const frame = pattern.slow(1000).queryArc(t, t)
81  ctx.fillStyle='#20001005'
82  ctx.fillRect(0,0,ww,wh)
83  //ctx.clearRect(0,0,ww,wh)
84  ctx.stroke()
85  frame.forEach(onDraw)
86  window.frame = requestAnimationFrame(render);
87};
88
89window.frame = requestAnimationFrame(render);
90
91silence
92`;
93
94export const syncexample = `"<0 1 2 3>/2"
95.off(1/2, add(4))
96.off(1, add(2))
97.scale(cat('C minor','C major').slow(8))
98.layer(
99  x=>x.note().piano(),
100  p=>stack(
101    p
102    .angle(p.sub('c3').div(12))
103    .r(.5)
104    .s('ellipse')
105    .w(.1)
106    .h(.1),
107    p.x(p.sub('c3').div(12))
108    .y(.9)
109    .w(1/12)
110    .h(.1)
111    .s('rect')
112  ).animate({sync:true,smear:0.9})
113)
114`;
115
116export const moveRescaleZoom = `
117const rescale = register('rescale', function (f, pat) {
118  return pat.mul(x(f).w(f).y(f).h(f));
119})
120
121const move = register('move', function (dx, dy, pat) {
122  return pat.add(x(dx).y(dy));
123})
124
125const zoom = register('zoom', function (f, pat) {
126  const d = pure(1).sub(f).div(2);
127  return pat.rescale(f).move(d, d);
128})
129
130x(.5).y(.5).w(1).h(1)
131  .zoom(saw.slow(3))
132  .move(sine.range(-.1,.1),0)
133  .fill("#ffeeaa10")
134  .s('rect')
135  .echo(6,.5,1)
136  .animate({smear:0.5})`;
137
138export const strudelS = `
139const rescale = register('rescale', function (f, pat) {
140  return pat.mul(x(f).w(f).y(f).h(f));
141})
142
143const move = register('move', function (dx, dy, pat) {
144  return pat.add(x(dx).y(dy));
145})
146
147const flipY = register('flipY', function (pat) {
148  return pat.fmap(v => ({...v, y:1-v.y}))
149})
150
151const zoom = register('zoom', function (f, pat) {
152  const d = pure(1).sub(f).div(2);
153  return pat.rescale(f).move(d, d);
154})
155
156Pattern.prototype.nest = function(n, cycles) {
157  n = reify(n)
158  return this.echo(n, pure(cycles).div(n), 1)
159}
160
161x(sine.div(1)).y(cosine.range(0,.5))
162  .w(.1).h(.1)
163  .mul(w(square).h(square).slow(8))
164  .zoom(saw.slow(8))
165  .layer(
166    id,
167    _=>_.flipY().move(0,0).rev()
168  )
169  .mask("0 1@2").rev()
170  .nest(16,9)
171  .s('rect')
172  .fill("royalblue steelblue".fast(14))
173  .slow(8)
174  .animate({smear:.99})`;