Rewrite line generation using transducers only

This commit is contained in:
arne 2024-07-19 01:28:22 +02:00
commit a846f38f61

View file

@ -2,7 +2,8 @@ import { line, group, translate, asSvg, svgDoc } from "@thi.ng/geom";
import { $canvas } from "@thi.ng/rdom-canvas"; import { $canvas } from "@thi.ng/rdom-canvas";
import { reactive, sync, } from "@thi.ng/rstream"; import { reactive, sync, } from "@thi.ng/rstream";
import { $compile, $input } from '@thi.ng/rdom' import { $compile, $input } from '@thi.ng/rdom'
import { cycle, takeWhile, comp, mapIndexed, transduce, push } from "@thi.ng/transducers" import { cycle, takeWhile, comp, mapIndexed, range, iterator, map, mapcat } from "@thi.ng/transducers"
import { vec2 } from "@thi.ng/vectors"
const cellSize_ = "12" const cellSize_ = "12"
const xs_ = "101110100101100" const xs_ = "101110100101100"
@ -25,15 +26,27 @@ const size = [width, height]
// build a list of start positions // build a list of start positions
const startPoints = (pattern: Iterable<number>, cellSize: number, maxCoord: number) => const startPoints = (pattern: Iterable<number>, maxCells: number) =>
transduce( [...iterator(
comp( comp(
mapIndexed((cell, val) => [cell * cellSize, val] as const), mapIndexed((cell, val) => [cell, val] as const),
takeWhile(([coord, _]) => coord <= maxCoord), takeWhile(([cell, _]) => cell <= maxCells),
), ),
push(),
cycle(pattern) cycle(pattern)
) as (readonly [number, number])[] )]
// points from which to which a stitch is showing for a given seed (1 or 0)
const stitches = (seed: number, maxCells: number) =>
[...iterator(
comp(
mapcat((cell) => (cell + seed) % 2 === 0 // start at the beginning or skip it
? [vec2(cell, cell + 1)]
: null),
takeWhile(([a, _]) => a < maxCells)
),
range()
)]
const scene = sync({ const scene = sync({
src: { cellSize, xs, ys, } src: { cellSize, xs, ys, }
@ -49,27 +62,19 @@ const scene = sync({
const yCells = Math.floor((height - 2 * minPadding) / cellSize) const yCells = Math.floor((height - 2 * minPadding) / cellSize)
const yPadding = (height - (yCells * cellSize)) / 2 const yPadding = (height - (yCells * cellSize)) / 2
const xStarts = startPoints(xs, cellSize, width - 2 * xPadding) const xStarts = startPoints(xs, xCells)
const yStarts = startPoints(ys, cellSize, height - 2 * yPadding) const yStarts = startPoints(ys, yCells)
const yLines = xStarts.flatMap( const yLines = iterator(
([xCoord, seed]) => mapcat(([x, seed]) =>
Array map(([y1, y2]) => line([x * cellSize, y1 * cellSize], [x * cellSize, y2 * cellSize]), stitches(seed, yCells))),
.from({ length: yCells }) xStarts
.map((_, cell) => (cell + seed) % 2 === 0 // start at the beginning or skip it
? line([xCoord, cell * cellSize], [xCoord, (cell + 1) * cellSize])
: null)
.filter(v => v != null)
) )
const xLines = yStarts.flatMap( const xLines = iterator(
([yCoord, seed]) => mapcat(([y, seed]) =>
Array map(([x1, x2]) => line([x1 * cellSize, y * cellSize], [x2 * cellSize, y * cellSize]), stitches(seed, xCells))),
.from({ length: xCells }) yStarts
.map((_, cell) => (cell + seed) % 2 === 0 // start at the beginning or skip it
? line([cell * cellSize, yCoord], [(cell + 1) * cellSize, yCoord])
: null)
.filter(v => v != null)
) )
const scene = translate( const scene = translate(