From 4b874246e32f50f9fade52dbd4423e7175eab1a6 Mon Sep 17 00:00:00 2001 From: max Date: Sat, 23 Jul 2022 19:53:03 +0300 Subject: [PATCH] refactor: lake group detection and features rendering --- src/dialogs/dialogs/heightmap-editor.js | 3 -- .../{drawCoastline.ts => drawFeatures.ts} | 12 +++--- src/layers/renderers/index.ts | 4 +- src/modules/dynamic/auto-update.js | 1 - src/modules/lakes.ts | 34 +---------------- src/modules/submap.js | 1 - src/scripts/generation/generation.ts | 4 +- src/scripts/generation/pack/lakes.ts | 37 +++++++++++++++++-- src/scripts/generation/pack/pack.ts | 12 +++--- src/scripts/generation/pack/rivers.ts | 4 +- 10 files changed, 52 insertions(+), 60 deletions(-) rename src/layers/renderers/{drawCoastline.ts => drawFeatures.ts} (82%) diff --git a/src/dialogs/dialogs/heightmap-editor.js b/src/dialogs/dialogs/heightmap-editor.js index 34b8de58..5c582c54 100644 --- a/src/dialogs/dialogs/heightmap-editor.js +++ b/src/dialogs/dialogs/heightmap-editor.js @@ -5,7 +5,6 @@ import {heightmapTemplates} from "config/heightmap-templates"; import {ERROR, INFO, TIME} from "config/logging"; import {closeDialogs} from "dialogs/utils"; import {layerIsOn, turnLayerButtonOff, turnLayerButtonOn, updatePresetInput, renderLayer} from "layers"; -import {drawCoastline} from "modules/coastline"; import {markupGridFeatures} from "modules/markup"; import {generatePrecipitation} from "modules/precipitation"; import {calculateTemperatures} from "modules/temperature"; @@ -225,7 +224,6 @@ export function open(options) { generatePrecipitation(grid); repackGrid(grid); markupPackFeatures(pack, newGrid); - drawCoastline(pack); Rivers.generate(pack, grid, erosionAllowed); @@ -344,7 +342,6 @@ export function open(options) { calculateTemperatures(grid); generatePrecipitation(grid); reGraph(grid); - drawCoastline(pack); if (erosionAllowed) Rivers.generate(pack, grid, true); diff --git a/src/layers/renderers/drawCoastline.ts b/src/layers/renderers/drawFeatures.ts similarity index 82% rename from src/layers/renderers/drawCoastline.ts rename to src/layers/renderers/drawFeatures.ts index b226f65f..7832e84a 100644 --- a/src/layers/renderers/drawCoastline.ts +++ b/src/layers/renderers/drawFeatures.ts @@ -4,7 +4,9 @@ import {simplify} from "scripts/simplify"; import {filterOutOfCanvasPoints} from "utils/lineUtils"; import {round} from "utils/stringUtils"; -export function drawCoastline(vertices: IGraphVertices, features: TPackFeatures) { +export function drawFeatures() { + /* uses */ const {vertices, features} = pack; + const landMask = defs.select("#land"); const waterMask = defs.select("#water"); @@ -12,8 +14,7 @@ export function drawCoastline(vertices: IGraphVertices, features: TPackFeatures) const SIMPLIFICATION_TOLERANCE = 0.3; // px for (const feature of features) { - if (!feature) continue; - if (feature.type === "ocean") continue; + if (!feature || feature.type === "ocean") continue; const points = feature.vertices.map(vertex => vertices.p[vertex]); const filteredPoints = filterOutOfCanvasPoints(points); @@ -28,7 +29,7 @@ export function drawCoastline(vertices: IGraphVertices, features: TPackFeatures) .attr("id", "land_" + feature.i); lakes - .select("#freshwater") + .select(`#${feature.group}`) .append("path") .attr("d", path) .attr("id", "lake_" + feature.i) @@ -46,9 +47,8 @@ export function drawCoastline(vertices: IGraphVertices, features: TPackFeatures) .attr("fill", "black") .attr("id", "water_" + feature.i); - const group = feature.group === "lake_island" ? "lake_island" : "sea_island"; coastline - .select("#" + group) + .select(`#${feature.group}`) .append("path") .attr("d", path) .attr("id", "island_" + feature.i) diff --git a/src/layers/renderers/index.ts b/src/layers/renderers/index.ts index 88dc56b8..750b6e69 100644 --- a/src/layers/renderers/index.ts +++ b/src/layers/renderers/index.ts @@ -3,7 +3,7 @@ import {TIME} from "config/logging"; import {drawBiomes} from "./drawBiomes"; import {drawBorders} from "./drawBorders"; import {drawCells} from "./drawCells"; -import {drawCoastline} from "./drawCoastline"; +import {drawFeatures} from "./drawFeatures"; import {drawCoordinates} from "./drawCoordinates"; import {drawCultures} from "./drawCultures"; import {drawEmblems} from "./drawEmblems"; @@ -24,10 +24,10 @@ const layerRenderersMap = { biomes: drawBiomes, borders: drawBorders, cells: drawCells, - coastline: drawCoastline, coordinates: drawCoordinates, cultures: drawCultures, emblems: drawEmblems, + features: drawFeatures, grid: drawGrid, heightmap: drawHeightmap, ice: drawIce, diff --git a/src/modules/dynamic/auto-update.js b/src/modules/dynamic/auto-update.js index 25011fd9..1df26e65 100644 --- a/src/modules/dynamic/auto-update.js +++ b/src/modules/dynamic/auto-update.js @@ -209,7 +209,6 @@ export function resolveVersionConflicts(version) { lakes.selectAll("path").remove(); reMarkFeatures(pack, newGrid); - drawCoastline(pack); } if (version < 1.11) { diff --git a/src/modules/lakes.ts b/src/modules/lakes.ts index ea419169..c29559dc 100644 --- a/src/modules/lakes.ts +++ b/src/modules/lakes.ts @@ -8,18 +8,6 @@ import {DISTANCE_FIELD, MIN_LAND_HEIGHT} from "config/generation"; import {byId} from "utils/shorthands"; window.Lakes = (function () { - const defineGroup = function (pack: IPack) { - for (const feature of pack.features) { - if (feature && feature.type === "lake") { - const lakeEl = lakes.select(`[data-f="${feature.i}"]`).node(); - if (!lakeEl) continue; - - feature.group = getGroup(feature); - byId(feature.group)?.appendChild(lakeEl); - } - } - }; - const generateName = function () { Math.random = aleaPRNG(seed); for (const feature of pack.features) { @@ -34,20 +22,6 @@ window.Lakes = (function () { return Names.getCulture(culture); }; - function getGroup(feature) { - if (feature.temp < -3) return "frozen"; - if (feature.height > 60 && feature.cells < 10 && feature.firstCell % 10 === 0) return "lava"; - - if (!feature.inlets && !feature.outlet) { - if (feature.evaporation > feature.flux * 4) return "dry"; - if (feature.cells < 3 && feature.firstCell % 10 === 0) return "sinkhole"; - } - - if (!feature.outlet && feature.evaporation > feature.flux) return "salt"; - - return "freshwater"; - } - const {LAND_COAST, WATER_COAST} = DISTANCE_FIELD; function addLakesInDeepDepressions(grid: IGraph & Partial) { @@ -162,11 +136,5 @@ window.Lakes = (function () { TIME && console.timeEnd("openLakes"); } - return { - defineGroup, - generateName, - getName, - addLakesInDeepDepressions, - openNearSeaLakes - }; + return {generateName, getName, addLakesInDeepDepressions, openNearSeaLakes}; })(); diff --git a/src/modules/submap.js b/src/modules/submap.js index eaf2fa34..753fe7c0 100644 --- a/src/modules/submap.js +++ b/src/modules/submap.js @@ -132,7 +132,6 @@ window.Submap = (function () { // remove misclassified cells stage("Define coastline."); reMarkFeatures(pack, newGrid); - drawCoastline(pack); /****************************************************/ /* Packed Graph */ diff --git a/src/scripts/generation/generation.ts b/src/scripts/generation/generation.ts index 3fa43760..838cc44a 100644 --- a/src/scripts/generation/generation.ts +++ b/src/scripts/generation/generation.ts @@ -5,8 +5,6 @@ import {closeDialogs} from "dialogs/utils"; import {openDialog} from "dialogs"; import {initLayers, renderLayer, restoreLayers} from "layers"; // @ts-expect-error js module -import {drawCoastline} from "layers/renderers/drawCoastline"; -// @ts-expect-error js module import {drawScaleBar, Rulers} from "modules/measurers"; // @ts-expect-error js module import {unfog} from "modules/ui/editors"; @@ -63,7 +61,7 @@ async function generate(options?: IGenerationOptions) { // temp rendering for debug renderLayer("cells"); - renderLayer("coastline", pack.vertices, pack.features); + renderLayer("features"); renderLayer("heightmap"); renderLayer("rivers", pack); diff --git a/src/scripts/generation/pack/lakes.ts b/src/scripts/generation/pack/lakes.ts index 66b00738..20139030 100644 --- a/src/scripts/generation/pack/lakes.ts +++ b/src/scripts/generation/pack/lakes.ts @@ -45,7 +45,7 @@ export const getClimateData = function ( return lakeData; }; -export const mergeLakeData = function ( +export const mergeLakeDataToFeatures = function ( features: TPackFeatures, lakeData: ILakeClimateData[], rivers: Pick[] @@ -57,11 +57,12 @@ export const mergeLakeData = function ( const lake = lakeData.find(lake => lake.i === feature.i); if (!lake) return feature; - const {flux, temp, evaporation} = lake; + const {firstCell, height, flux, temp, evaporation} = lake; const inlets = lake.inlets?.filter(inlet => rivers.find(river => river.i === inlet)); const outlet = rivers.find(river => river.i === lake.outlet)?.i; + const group = defineLakeGroup({firstCell, height, flux, temp, evaporation, inlets, outlet}); - const lakeFeature: IPackFeatureLake = {...feature, flux, temp, evaporation, inlets, outlet}; + const lakeFeature: IPackFeatureLake = {...feature, flux, temp, evaporation, inlets, outlet, group}; if (!inlets || !inlets.length) delete lakeFeature.inlets; if (!outlet) delete lakeFeature.outlet; @@ -70,3 +71,33 @@ export const mergeLakeData = function ( return updatedFeatures as TPackFeatures; }; + +function defineLakeGroup({ + firstCell, + height, + flux, + temp, + evaporation, + inlets, + outlet +}: { + firstCell: number; + height: number; + flux: number; + temp: number; + evaporation: number; + inlets?: number[]; + outlet?: number; +}): IPackFeatureLake["group"] { + if (temp < -3) return "frozen"; + if (height > 60 && cells < 10 && firstCell % 10 === 0) return "lava"; + + if ((!inlets || !inlets.length) && !outlet) { + if (evaporation > flux * 4) return "dry"; + if (cells < 3 && firstCell % 10 === 0) return "sinkhole"; + } + + if (!outlet && evaporation > flux) return "salt"; + + return "freshwater"; +} diff --git a/src/scripts/generation/pack/pack.ts b/src/scripts/generation/pack/pack.ts index be15c068..63fe6587 100644 --- a/src/scripts/generation/pack/pack.ts +++ b/src/scripts/generation/pack/pack.ts @@ -1,7 +1,5 @@ import * as d3 from "d3"; -// @ts-expect-error js module -import {drawCoastline} from "layers/renderers/drawCoastline"; import {markupPackFeatures} from "modules/markup"; // @ts-expect-error js module import {drawScaleBar} from "modules/measurers"; @@ -22,17 +20,19 @@ const {LAND_COAST, WATER_COAST, DEEPER_WATER} = DISTANCE_FIELD; export function createPack(grid: IGrid): IPack { const {vertices, cells} = repackGrid(grid); - const markup = markupPackFeatures(grid, vertices, pick(cells, "v", "c", "b", "p", "h")); - const {features, featureIds, distanceField, haven, harbor} = markup; + const {features, featureIds, distanceField, haven, harbor} = markupPackFeatures( + grid, + vertices, + pick(cells, "v", "c", "b", "p", "h") + ); const {heights, flux, r, conf, rivers, mergedFeatures} = generateRivers( grid.cells.prec, grid.cells.temp, - pick({...cells, f: featureIds, t: distanceField, haven}, "i", "c", "b", "g", "t", "h", "f", "haven", "p"), + {...pick(cells, "i", "c", "b", "g", "h", "p"), f: featureIds, t: distanceField, haven}, features ); - // Lakes.defineGroup(newPack); // Biomes.define(newPack, grid); // const rankCellsData = pick(newPack.cells, "i", "f", "fl", "conf", "r", "h", "area", "biome", "haven", "harbor"); diff --git a/src/scripts/generation/pack/rivers.ts b/src/scripts/generation/pack/rivers.ts index 77407122..462af9fb 100644 --- a/src/scripts/generation/pack/rivers.ts +++ b/src/scripts/generation/pack/rivers.ts @@ -7,7 +7,7 @@ import {DISTANCE_FIELD, MAX_HEIGHT, MIN_LAND_HEIGHT} from "config/generation"; import {getInputNumber} from "utils/nodeUtils"; import {pick} from "utils/functionUtils"; import {byId} from "utils/shorthands"; -import {mergeLakeData, getClimateData, ILakeClimateData} from "./lakes"; +import {mergeLakeDataToFeatures, getClimateData, ILakeClimateData} from "./lakes"; import {drawArrow} from "utils/debugUtils"; const {Rivers} = window; @@ -44,7 +44,7 @@ export function generateRivers( const {r, conf, rivers} = defineRivers(); const heights = downcutRivers(currentCellHeights); - const mergedFeatures = mergeLakeData(features, lakeData, rivers); + const mergedFeatures = mergeLakeDataToFeatures(features, lakeData, rivers); TIME && console.timeEnd("generateRivers");