From f692f8dfbf754abd30659af6a0287f517d857c80 Mon Sep 17 00:00:00 2001 From: max Date: Fri, 29 Jul 2022 01:20:34 +0300 Subject: [PATCH] refactor(generation): drawCultures start --- src/layers/renderers/drawCultures.js | 54 ---------------------------- src/layers/renderers/drawCultures.ts | 41 +++++++++++++++++++++ src/scripts/connectVertices.ts | 12 +++---- 3 files changed, 46 insertions(+), 61 deletions(-) delete mode 100644 src/layers/renderers/drawCultures.js create mode 100644 src/layers/renderers/drawCultures.ts diff --git a/src/layers/renderers/drawCultures.js b/src/layers/renderers/drawCultures.js deleted file mode 100644 index 6fdf3ea6..00000000 --- a/src/layers/renderers/drawCultures.js +++ /dev/null @@ -1,54 +0,0 @@ -export function drawCultures() { - cults.selectAll("path").remove(); - const {cells, vertices, cultures} = pack; - const n = cells.i.length; - const used = new Uint8Array(cells.i.length); - const paths = new Array(cultures.length).fill(""); - - for (const i of cells.i) { - if (!cells.culture[i]) continue; - if (used[i]) continue; - used[i] = 1; - const c = cells.culture[i]; - const onborder = cells.c[i].some(n => cells.culture[n] !== c); - if (!onborder) continue; - const vertex = cells.v[i].find(v => vertices.c[v].some(i => cells.culture[i] !== c)); - const chain = connectVertices(vertex, c); - if (chain.length < 3) continue; - const points = chain.map(v => vertices.p[v]); - paths[c] += "M" + points.join("L") + "Z"; - } - - const data = paths.map((p, i) => [p, i]).filter(d => d[0].length > 10); - cults - .selectAll("path") - .data(data) - .enter() - .append("path") - .attr("d", d => d[0]) - .attr("fill", d => cultures[d[1]].color) - .attr("id", d => "culture" + d[1]); - - // connect vertices to chain - function connectVertices(start, t) { - const chain = []; // vertices chain to form a path - for (let i = 0, current = start; i === 0 || (current !== start && i < 20000); i++) { - const prev = chain[chain.length - 1]; // previous vertex in chain - chain.push(current); // add current vertex to sequence - const c = vertices.c[current]; // cells adjacent to vertex - c.filter(c => cells.culture[c] === t).forEach(c => (used[c] = 1)); - const c0 = c[0] >= n || cells.culture[c[0]] !== t; - const c1 = c[1] >= n || cells.culture[c[1]] !== t; - const c2 = c[2] >= n || cells.culture[c[2]] !== t; - const v = vertices.v[current]; // neighboring vertices - if (v[0] !== prev && c0 !== c1) current = v[0]; - else if (v[1] !== prev && c1 !== c2) current = v[1]; - else if (v[2] !== prev && c0 !== c2) current = v[2]; - if (current === chain[chain.length - 1]) { - ERROR && console.error("Next vertex is not found"); - break; - } - } - return chain; - } -} diff --git a/src/layers/renderers/drawCultures.ts b/src/layers/renderers/drawCultures.ts new file mode 100644 index 00000000..4458a0ab --- /dev/null +++ b/src/layers/renderers/drawCultures.ts @@ -0,0 +1,41 @@ +import {connectVertices} from "scripts/connectVertices"; + +export function drawCultures() { + /* uses */ const {cells, vertices, cultures} = pack; + + cults.selectAll("path").remove(); // cleanup + + const used = new Uint8Array(cells.i.length); + const paths = new Array(cultures.length).fill(""); + + for (const i of cells.i) { + if (!cells.culture[i]) continue; + if (used[i]) continue; + used[i] = 1; + const cultureId = cells.culture[i]; + const onborder = cells.c[i].some(n => cells.culture[n] !== cultureId); + if (!onborder) continue; + + const startingVertex = cells.v[i].find(v => vertices.c[v].some(i => cells.culture[i] !== cultureId)); + if (startingVertex === undefined) + throw new Error(`Draw cultures: starting vertex for culture ${cultureId} is not found`); + + const ofSameType = (cellId: number) => cells.culture[cellId] === cultureId; + const chain = connectVertices({vertices, startingVertex, ofSameType}); + + if (chain.length < 3) continue; + const points = chain.map(v => vertices.p[v]); + + paths[cultureId] += "M" + points.join("L") + "Z"; + } + + const data = paths.map((p, i) => [p, i]).filter(d => d[0].length > 10); + cults + .selectAll("path") + .data(data) + .enter() + .append("path") + .attr("d", d => d[0]) + .attr("fill", d => cultures[d[1]].color) + .attr("id", d => "culture" + d[1]); +} diff --git a/src/scripts/connectVertices.ts b/src/scripts/connectVertices.ts index 8ba29ec9..5fbd1b47 100644 --- a/src/scripts/connectVertices.ts +++ b/src/scripts/connectVertices.ts @@ -17,7 +17,8 @@ export function getFeatureVertices({ const startingCell = findStartingCell({firstCell, featureIds, featureId, vertices, cells, packCellsNumber}); const startingVertex = findStartingVertex({startingCell, featureIds, featureId, vertices, cells, packCellsNumber}); - const featureVertices = connectVertices({vertices, startingVertex, featureIds, featureId}); + const ofSameType = (cellId: number) => featureIds[cellId] === featureId; + const featureVertices = connectVertices({vertices, startingVertex, ofSameType}); return featureVertices; } @@ -90,18 +91,15 @@ function findStartingVertex({ const CONNECT_VERTICES_MAX_ITERATIONS = 50000; // connect vertices around feature -function connectVertices({ +export function connectVertices({ vertices, startingVertex, - featureIds, - featureId + ofSameType }: { vertices: IGraphVertices; startingVertex: number; - featureIds: Uint16Array; - featureId: number; + ofSameType: (cellId: number) => boolean; }) { - const ofSameType = (cellId: number) => featureIds[cellId] === featureId; const chain: number[] = []; // vertices chain to form a path let next = startingVertex;