Modification of Seeded winds
Intended to do 3 bands of color (channel 0, 1, 2), and blend between the channels to make it more of a continuous fade
Log in to post a comment.
// You can find the Turtle API reference here: https://turtletoy.net/syntax
Canvas.setpenopacity(0.2);
// Global code will be evaluated once.
const turtle = new Turtle();
turtle.penup();
var seed = 789;
function random() {
var x = Math.sin(seed++) * 10000;
return x - Math.floor(x);
}
var seed1 = 789;
function random1() {
var x = Math.sin(seed1++) * 10000;
return x - Math.floor(x);
}
// Cardinal Splines ref: https://stackoverflow.com/questions/7054272/how-to-draw-smooth-curve-through-n-points-using-javascript-html5-canvas
turtle.drawSpline = (pts, tension = 0.5, isClosed = false, numOfSegments = 16) => {
const res = []; // clone array
const _pts = pts.slice(0);
// The algorithm require a previous and next point to the actual point array.
// Check if we will draw closed or open curve.
// If closed, copy end points to beginning and first points to end
// If open, duplicate first points to befinning, end points to end
if (isClosed) {
_pts.unshift(pts[pts.length - 1]);
_pts.unshift(pts[pts.length - 2]);
_pts.unshift(pts[pts.length - 1]);
_pts.unshift(pts[pts.length - 2]);
_pts.push(pts[0]);
_pts.push(pts[1]);
}
else {
_pts.unshift(pts[1]); //copy 1. point and insert at beginning
_pts.unshift(pts[0]);
_pts.push(pts[pts.length - 2]); //copy last point and append
_pts.push(pts[pts.length - 1]);
}
// ok, lets start..
// 1. loop goes through point array
// 2. loop goes through each segment between the 2 pts + 1e point before and after
for (let i = 2; i < (_pts.length - 4); i += 2) {
for (let t = 0; t <= numOfSegments; t++) {
// calc tension vectors
const t1x = (_pts[i+2] - _pts[i-2]) * tension;
const t2x = (_pts[i+4] - _pts[i]) * tension;
const t1y = (_pts[i+3] - _pts[i-1]) * tension;
const t2y = (_pts[i+5] - _pts[i+1]) * tension;
// calc step
const st = t / numOfSegments;
// calc cardinals
const c1 = 2 * Math.pow(st, 3) - 3 * Math.pow(st, 2) + 1;
const c2 = -(2 * Math.pow(st, 3)) + 3 * Math.pow(st, 2);
const c3 = Math.pow(st, 3) - 2 * Math.pow(st, 2) + st;
const c4 = Math.pow(st, 3) - Math.pow(st, 2);
// calc x and y cords with common control vectors
const x = c1 * _pts[i] + c2 * _pts[i+2] + c3 * t1x + c4 * t2x;
const y = c1 * _pts[i+1] + c2 * _pts[i+3] + c3 * t1y + c4 * t2y;
//store points in array
res.push(x);
res.push(y);
}
}
// draw
turtle.goto(res[0], res[1]);
turtle.down();
for(let i = 2; i < res.length - 1; i += 2) turtle.goto(res[i], res[i+ 1]);
turtle.up();
return res;
}
//////////////////////////////////////////
const points = [];
const velocities = [];
for (let i = 0; i < 30; i++) {
points.push(i * (200 / 30) - 100, 0.25 * 100 * (random() - random()));
velocities.push(0, 0);
}
const total_channels = 4;
const channel = 1;
const blend_width = 20
j = 0;
// The walk function will be called until it returns false.
function walk(i) {
for (let y = 0; y < 60; y++) {
velocities[y] += 0.03 * (random() - random());
points[y] += velocities[y];
}
ichannel = 4;
if(i<100-blend_width){
ichannel = 0;
} else if (i>=100-blend_width & i<100+blend_width){
if(random1()>0.5){
ichannel = 0;
}else{
ichannel = 1;
}
} else if(i<200-blend_width){
ichannel = 1;
} else if (i>=200-blend_width & i<200+blend_width){
if(random1()>0.5){
ichannel = 1;
}else{
ichannel = 2;
}
} else {
ichannel = 2;
}
if(ichannel == channel){
turtle.drawSpline(points);
}
return i < 300;
}