Created
June 18, 2024 01:01
-
-
Save ededejr/347684f414b62fe3539b3d08b2fed0b4 to your computer and use it in GitHub Desktop.
a sample implementation for a lignes model
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import { EtchModel, Grain, Palette } from './utils'; | |
const Token = { | |
pixelDensity: 5, | |
strokeWeight: 5, | |
pointVariance: 0.05, | |
lineSegments: 20, | |
numberOfLines: 5, | |
shouldUseFuzzyGrain: false, | |
shouldUseScaledColors: false, | |
}; | |
export const Roomates: EtchModel = { | |
meta: { | |
title: 'roomates', | |
description: | |
'several shapes fighting for their space on the canvas. a metaphor for internal conflict, or roomates.', | |
stability: 'development', | |
aspectRatio: { | |
width: 3, | |
height: 4, | |
}, | |
}, | |
render: ({ p, log, done, width, height }) => { | |
const palette = new Palette(); | |
const grain = Grain.withShader(p); | |
const background_color = '#fff2e4'; | |
// decide random values | |
Token.lineSegments = p.random([4, 20, 80]); | |
Token.numberOfLines = p.random([4, 5, 8, 16, 80]); | |
Token.shouldUseFuzzyGrain = Boolean(p.random() < 0.9); | |
Token.shouldUseScaledColors = Boolean(p.random() < 0.6); | |
log(Token); | |
const getColor = Token.shouldUseScaledColors | |
? () => palette.getScaledColor({ exclude: [background_color] }) | |
: () => palette.getColor({ exclude: [background_color] }); | |
p.setup = () => { | |
const c = p.createCanvas(width, height); | |
p.pixelDensity(Token.pixelDensity); | |
// no need to setup | |
if (!Token.shouldUseFuzzyGrain) { | |
grain.setup(c); | |
} | |
}; | |
p.draw = () => { | |
const segments = Token.lineSegments; | |
const numberOfLines = Token.numberOfLines; | |
const quarterHeight = p.height / numberOfLines; | |
p.background(getColor()); | |
for (let i = 0; i < numberOfLines; i++) { | |
const y = quarterHeight * i + quarterHeight / 2; | |
drawSquigglyLine({ | |
start: { | |
x: 0, | |
y, | |
}, | |
end: { | |
x: p.width, | |
y: p.randomGaussian(y), | |
}, | |
segments, | |
}); | |
} | |
p.noLoop(); | |
// draw border around | |
p.noFill(); | |
p.stroke('black'); | |
p.strokeWeight(12); | |
p.beginShape(); | |
p.vertex(0, 0); | |
p.vertex(p.width, 0); | |
p.vertex(p.width, p.height); | |
p.vertex(0, p.height); | |
p.vertex(0, 0); | |
p.endShape(); | |
if (Token.shouldUseFuzzyGrain) { | |
Grain.withFuzzification(p, 20); | |
} else { | |
grain.apply(); | |
} | |
done(); | |
}; | |
type SquigglyLineOptions = { | |
start: { | |
x: number; | |
y: number; | |
}; | |
end: { | |
x: number; | |
y: number; | |
}; | |
segments: number; | |
}; | |
function drawSquigglyLine(options: SquigglyLineOptions) { | |
const { start, end, segments } = options; | |
const { x: x1, y: y1 } = start; | |
const { x: x2, y: y2 } = end; | |
p.strokeWeight(Token.strokeWeight); | |
p.noFill(); | |
const lengthOfSegment = (x2 - x1) / segments; | |
const heightOfSegment = (y2 - y1) / segments; | |
const points = []; | |
for (let i = 0; i < segments; i++) { | |
const x = x1 + lengthOfSegment * i; | |
const y = | |
(y1 + heightOfSegment * i) * p.randomGaussian(1, Token.pointVariance); | |
p.point(x, y); | |
points.push({ x, y }); | |
} | |
points.push({ x: x2, y: y2 }); | |
p.fill(getColor()); | |
p.beginShape(); | |
p.curveVertex(x1, y1); | |
for (const point of points) { | |
p.curveVertex(point.x, point.y); | |
} | |
p.curveVertex(x2, y2); | |
p.vertex(p.width, p.height); | |
p.vertex(0, p.height); | |
p.vertex(x1, y1); | |
p.endShape(); | |
} | |
}, | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment