Added Logging Options to Improve Performance (#529)

* Added Logging Options to Improve Performance

* Requested Changes

Co-authored-by: Onyx Azryn <brycekabat@onyxazryn.com>
This commit is contained in:
Bryce Kabat 2020-10-21 17:32:57 -05:00 committed by GitHub
parent e480c1c8e5
commit f4efedcf9d
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
18 changed files with 192 additions and 186 deletions

100
main.js
View file

@ -10,6 +10,12 @@
const version = "1.4"; // generator version const version = "1.4"; // generator version
document.title += " v" + version; document.title += " v" + version;
// Switches to disable/enable logging features
const INFO = 0;
const TIME = 0;
const WARN = 1;
const ERROR = 1;
// if map version is not stored, clear localStorage and show a message // if map version is not stored, clear localStorage and show a message
if (rn(localStorage.getItem("version"), 2) !== rn(version, 2)) { if (rn(localStorage.getItem("version"), 2) !== rn(version, 2)) {
localStorage.clear(); localStorage.clear();
@ -142,7 +148,7 @@ void function checkLoadParameters() {
// of there is a valid maplink, try to load .map file from URL // of there is a valid maplink, try to load .map file from URL
if (params.get("maplink")) { if (params.get("maplink")) {
console.warn("Load map from URL"); WARN && console.warn("Load map from URL");
const maplink = params.get("maplink"); const maplink = params.get("maplink");
const pattern = /(ftp|http|https):\/\/(\w+:{0,1}\w*@)?(\S+)(:[0-9]+)?(\/|\/([\w#!:.?+=&%@!\-\/]))?/; const pattern = /(ftp|http|https):\/\/(\w+:{0,1}\w*@)?(\S+)(:[0-9]+)?(\/|\/([\w#!:.?+=&%@!\-\/]))?/;
const valid = pattern.test(maplink); const valid = pattern.test(maplink);
@ -152,7 +158,7 @@ void function checkLoadParameters() {
// if there is a seed (user of MFCG provided), generate map for it // if there is a seed (user of MFCG provided), generate map for it
if (params.get("seed")) { if (params.get("seed")) {
console.warn("Generate map for seed"); WARN && console.warn("Generate map for seed");
generateMapOnLoad(); generateMapOnLoad();
return; return;
} }
@ -161,24 +167,24 @@ void function checkLoadParameters() {
if (onloadMap.value === "saved") { if (onloadMap.value === "saved") {
ldb.get("lastMap", blob => { ldb.get("lastMap", blob => {
if (blob) { if (blob) {
console.warn("Load last saved map"); WARN && console.warn("Load last saved map");
try { try {
uploadMap(blob); uploadMap(blob);
} }
catch(error) { catch(error) {
console.error(error); ERROR && console.error(error);
console.warn("Cannot load stored map, random map to be generated"); WARN && console.warn("Cannot load stored map, random map to be generated");
generateMapOnLoad(); generateMapOnLoad();
} }
} else { } else {
console.error("No map stored, random map to be generated"); ERROR && console.error("No map stored, random map to be generated");
generateMapOnLoad(); generateMapOnLoad();
} }
}); });
return; return;
} }
console.warn("Generate random map"); WARN && console.warn("Generate random map");
generateMapOnLoad(); generateMapOnLoad();
}() }()
@ -197,7 +203,7 @@ function loadMapFromURL(maplink, random) {
} }
function showUploadErrorMessage(error, URL, random) { function showUploadErrorMessage(error, URL, random) {
console.error(error); ERROR && console.error(error);
alertMessage.innerHTML = `Cannot load map from the ${link(URL, "link provided")}. alertMessage.innerHTML = `Cannot load map from the ${link(URL, "link provided")}.
${random?`A new random map is generated. `:''} ${random?`A new random map is generated. `:''}
Please ensure the linked file is reachable and CORS is allowed on server side`; Please ensure the linked file is reachable and CORS is allowed on server side`;
@ -249,7 +255,7 @@ function focusOn() {
// find burg for MFCG and focus on it // find burg for MFCG and focus on it
function findBurgForMFCG(params) { function findBurgForMFCG(params) {
const cells = pack.cells, burgs = pack.burgs; const cells = pack.cells, burgs = pack.burgs;
if (pack.burgs.length < 2) {console.error("Cannot select a burg for MFCG"); return;} if (pack.burgs.length < 2) {ERROR && console.error("Cannot select a burg for MFCG"); return;}
// used for selection // used for selection
const size = +params.get("size"); const size = +params.get("size");
@ -274,7 +280,7 @@ function findBurgForMFCG(params) {
// select a burg with closest population from selection // select a burg with closest population from selection
const selected = d3.scan(selection, (a, b) => Math.abs(a.population - size) - Math.abs(b.population - size)); const selected = d3.scan(selection, (a, b) => Math.abs(a.population - size) - Math.abs(b.population - size));
const burgId = selection[selected].i; const burgId = selection[selected].i;
if (!burgId) {console.error("Cannot select a burg for MFCG"); return;} if (!burgId) {ERROR && console.error("Cannot select a burg for MFCG"); return;}
const b = burgs[burgId]; const b = burgs[burgId];
const referrer = new URL(document.referrer); const referrer = new URL(document.referrer);
@ -507,7 +513,7 @@ function generate() {
const timeStart = performance.now(); const timeStart = performance.now();
invokeActiveZooming(); invokeActiveZooming();
generateSeed(); generateSeed();
console.group("Generated Map " + seed); INFO && console.group("Generated Map " + seed);
applyMapSize(); applyMapSize();
randomizeOptions(); randomizeOptions();
placePoints(); placePoints();
@ -548,12 +554,12 @@ function generate() {
addZones(); addZones();
Names.getMapName(); Names.getMapName();
console.warn(`TOTAL: ${rn((performance.now()-timeStart)/1000,2)}s`); WARN && console.warn(`TOTAL: ${rn((performance.now()-timeStart)/1000,2)}s`);
showStatistics(); showStatistics();
console.groupEnd("Generated Map " + seed); INFO && console.groupEnd("Generated Map " + seed);
} }
catch(error) { catch(error) {
console.error(error); ERROR && console.error(error);
clearMainTip(); clearMainTip();
alertMessage.innerHTML = `An error is occured on map generation. Please retry. alertMessage.innerHTML = `An error is occured on map generation. Please retry.
@ -586,35 +592,35 @@ function generateSeed() {
// Place points to calculate Voronoi diagram // Place points to calculate Voronoi diagram
function placePoints() { function placePoints() {
console.time("placePoints"); TIME && console.time("placePoints");
const cellsDesired = 10000 * densityInput.value; // generate 10k points for each densityInput point const cellsDesired = 10000 * densityInput.value; // generate 10k points for each densityInput point
const spacing = grid.spacing = rn(Math.sqrt(graphWidth * graphHeight / cellsDesired), 2); // spacing between points before jirrering const spacing = grid.spacing = rn(Math.sqrt(graphWidth * graphHeight / cellsDesired), 2); // spacing between points before jirrering
grid.boundary = getBoundaryPoints(graphWidth, graphHeight, spacing); grid.boundary = getBoundaryPoints(graphWidth, graphHeight, spacing);
grid.points = getJitteredGrid(graphWidth, graphHeight, spacing); // jittered square grid grid.points = getJitteredGrid(graphWidth, graphHeight, spacing); // jittered square grid
grid.cellsX = Math.floor((graphWidth + 0.5 * spacing) / spacing); grid.cellsX = Math.floor((graphWidth + 0.5 * spacing) / spacing);
grid.cellsY = Math.floor((graphHeight + 0.5 * spacing) / spacing); grid.cellsY = Math.floor((graphHeight + 0.5 * spacing) / spacing);
console.timeEnd("placePoints"); TIME && console.timeEnd("placePoints");
} }
// calculate Delaunay and then Voronoi diagram // calculate Delaunay and then Voronoi diagram
function calculateVoronoi(graph, points) { function calculateVoronoi(graph, points) {
console.time("calculateDelaunay"); TIME && console.time("calculateDelaunay");
const n = points.length; const n = points.length;
const allPoints = points.concat(grid.boundary); const allPoints = points.concat(grid.boundary);
const delaunay = Delaunator.from(allPoints); const delaunay = Delaunator.from(allPoints);
console.timeEnd("calculateDelaunay"); TIME && console.timeEnd("calculateDelaunay");
console.time("calculateVoronoi"); TIME && console.time("calculateVoronoi");
const voronoi = Voronoi(delaunay, allPoints, n); const voronoi = Voronoi(delaunay, allPoints, n);
graph.cells = voronoi.cells; graph.cells = voronoi.cells;
graph.cells.i = n < 65535 ? Uint16Array.from(d3.range(n)) : Uint32Array.from(d3.range(n)); // array of indexes graph.cells.i = n < 65535 ? Uint16Array.from(d3.range(n)) : Uint32Array.from(d3.range(n)); // array of indexes
graph.vertices = voronoi.vertices; graph.vertices = voronoi.vertices;
console.timeEnd("calculateVoronoi"); TIME && console.timeEnd("calculateVoronoi");
} }
// Mark features (ocean, lakes, islands) // Mark features (ocean, lakes, islands)
function markFeatures() { function markFeatures() {
console.time("markFeatures"); TIME && console.time("markFeatures");
Math.seedrandom(seed); // restart Math.random() to get the same result on heightmap edit in Erase mode Math.seedrandom(seed); // restart Math.random() to get the same result on heightmap edit in Erase mode
const cells = grid.cells, heights = grid.cells.h; const cells = grid.cells, heights = grid.cells.h;
cells.f = new Uint16Array(cells.i.length); // cell feature number cells.f = new Uint16Array(cells.i.length); // cell feature number
@ -648,7 +654,7 @@ function markFeatures() {
queue[0] = cells.f.findIndex(f => !f); // find unmarked cell queue[0] = cells.f.findIndex(f => !f); // find unmarked cell
} }
console.timeEnd("markFeatures"); TIME && console.timeEnd("markFeatures");
} }
// How to handle lakes generated near seas? They can be both open or closed. // How to handle lakes generated near seas? They can be both open or closed.
@ -658,7 +664,7 @@ function openNearSeaLakes() {
if (templateInput.value === "Atoll") return; // no need for Atolls if (templateInput.value === "Atoll") return; // no need for Atolls
const cells = grid.cells, features = grid.features; const cells = grid.cells, features = grid.features;
if (!features.find(f => f.type === "lake")) return; // no lakes if (!features.find(f => f.type === "lake")) return; // no lakes
console.time("openLakes"); TIME && console.time("openLakes");
const limit = 50; // max height that can be breached by water const limit = 50; // max height that can be breached by water
for (let t = 0, removed = true; t < 5 && removed; t++) { for (let t = 0, removed = true; t < 5 && removed; t++) {
@ -694,7 +700,7 @@ function openNearSeaLakes() {
return true; return true;
} }
console.timeEnd("openLakes"); TIME && console.timeEnd("openLakes");
} }
// define map size and position based on template and random factor // define map size and position based on template and random factor
@ -745,7 +751,7 @@ function calculateMapCoordinates() {
// temperature model // temperature model
function calculateTemperatures() { function calculateTemperatures() {
console.time('calculateTemperatures'); TIME && console.time('calculateTemperatures');
const cells = grid.cells; const cells = grid.cells;
cells.temp = new Int8Array(cells.i.length); // temperature array cells.temp = new Int8Array(cells.i.length); // temperature array
@ -771,12 +777,12 @@ function calculateTemperatures() {
return rn(height / 1000 * 6.5); return rn(height / 1000 * 6.5);
} }
console.timeEnd('calculateTemperatures'); TIME && console.timeEnd('calculateTemperatures');
} }
// simplest precipitation model // simplest precipitation model
function generatePrecipitation() { function generatePrecipitation() {
console.time('generatePrecipitation'); TIME && console.time('generatePrecipitation');
prec.selectAll("*").remove(); prec.selectAll("*").remove();
const cells = grid.cells; const cells = grid.cells;
cells.prec = new Uint8Array(cells.i.length); // precipitation array cells.prec = new Uint8Array(cells.i.length); // precipitation array
@ -887,12 +893,12 @@ function generatePrecipitation() {
if (southerly) wind.append("text").attr("x", graphWidth / 2).attr("y", graphHeight - 20).text("\u21C8"); if (southerly) wind.append("text").attr("x", graphWidth / 2).attr("y", graphHeight - 20).text("\u21C8");
}(); }();
console.timeEnd('generatePrecipitation'); TIME && console.timeEnd('generatePrecipitation');
} }
// recalculate Voronoi Graph to pack cells // recalculate Voronoi Graph to pack cells
function reGraph() { function reGraph() {
console.time("reGraph"); TIME && console.time("reGraph");
let cells = grid.cells, points = grid.points, features = grid.features; let cells = grid.cells, points = grid.points, features = grid.features;
const newCells = {p:[], g:[], h:[], t:[], f:[], r:[], biome:[]}; // to store new data const newCells = {p:[], g:[], h:[], t:[], f:[], r:[], biome:[]}; // to store new data
const spacing2 = grid.spacing ** 2; const spacing2 = grid.spacing ** 2;
@ -936,12 +942,12 @@ function reGraph() {
cells.area = new Uint16Array(cells.i.length); // cell area cells.area = new Uint16Array(cells.i.length); // cell area
cells.i.forEach(i => cells.area[i] = Math.abs(d3.polygonArea(getPackPolygon(i)))); cells.i.forEach(i => cells.area[i] = Math.abs(d3.polygonArea(getPackPolygon(i))));
console.timeEnd("reGraph"); TIME && console.timeEnd("reGraph");
} }
// Detect and draw the coasline // Detect and draw the coasline
function drawCoastline() { function drawCoastline() {
console.time('drawCoastline'); TIME && console.time('drawCoastline');
reMarkFeatures(); reMarkFeatures();
const cells = pack.cells, vertices = pack.vertices, n = cells.i.length, features = pack.features; const cells = pack.cells, vertices = pack.vertices, n = cells.i.length, features = pack.features;
const used = new Uint8Array(features.length); // store conneted features const used = new Uint8Array(features.length); // store conneted features
@ -1016,7 +1022,7 @@ function drawCoastline() {
if (v[0] !== prev && c0 !== c1) current = v[0]; else if (v[0] !== prev && c0 !== c1) current = v[0]; else
if (v[1] !== prev && c1 !== c2) current = v[1]; else if (v[1] !== prev && c1 !== c2) current = v[1]; else
if (v[2] !== prev && c0 !== c2) current = v[2]; if (v[2] !== prev && c0 !== c2) current = v[2];
if (current === chain[chain.length-1]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length-1]) {ERROR && console.error("Next vertex is not found"); break;}
} }
//chain.push(chain[0]); // push first vertex as the last one //chain.push(chain[0]); // push first vertex as the last one
return chain; return chain;
@ -1040,12 +1046,12 @@ function drawCoastline() {
} }
} }
console.timeEnd('drawCoastline'); TIME && console.timeEnd('drawCoastline');
} }
// Re-mark features (ocean, lakes, islands) // Re-mark features (ocean, lakes, islands)
function reMarkFeatures() { function reMarkFeatures() {
console.time("reMarkFeatures"); TIME && console.time("reMarkFeatures");
const cells = pack.cells, features = pack.features = [0], temp = grid.cells.temp; const cells = pack.cells, features = pack.features = [0], temp = grid.cells.temp;
cells.f = new Uint16Array(cells.i.length); // cell feature number cells.f = new Uint16Array(cells.i.length); // cell feature number
cells.t = new Int16Array(cells.i.length); // cell type: 1 = land along coast; -1 = water along coast; cells.t = new Int16Array(cells.i.length); // cell type: 1 = land along coast; -1 = water along coast;
@ -1113,13 +1119,13 @@ function reMarkFeatures() {
return "isle"; return "isle";
} }
console.timeEnd("reMarkFeatures"); TIME && console.timeEnd("reMarkFeatures");
} }
// temporary elevate some lakes to resolve depressions and flux the water to form an open (exorheic) lake // temporary elevate some lakes to resolve depressions and flux the water to form an open (exorheic) lake
function elevateLakes() { function elevateLakes() {
if (templateInput.value === "Atoll") return; // no need for Atolls if (templateInput.value === "Atoll") return; // no need for Atolls
console.time('elevateLakes'); TIME && console.time('elevateLakes');
const cells = pack.cells, features = pack.features; const cells = pack.cells, features = pack.features;
const maxCells = cells.i.length / 100; // size limit; let big lakes be closed (endorheic) const maxCells = cells.i.length / 100; // size limit; let big lakes be closed (endorheic)
cells.i.forEach(i => { cells.i.forEach(i => {
@ -1129,12 +1135,12 @@ function elevateLakes() {
//debug.append("circle").attr("cx", cells.p[i][0]).attr("cy", cells.p[i][1]).attr("r", .5).attr("fill", "blue"); //debug.append("circle").attr("cx", cells.p[i][0]).attr("cy", cells.p[i][1]).attr("r", .5).attr("fill", "blue");
}); });
console.timeEnd('elevateLakes'); TIME && console.timeEnd('elevateLakes');
} }
// assign biome id for each cell // assign biome id for each cell
function defineBiomes() { function defineBiomes() {
console.time("defineBiomes"); TIME && console.time("defineBiomes");
const cells = pack.cells, f = pack.features, temp = grid.cells.temp, prec = grid.cells.prec; const cells = pack.cells, f = pack.features, temp = grid.cells.temp, prec = grid.cells.prec;
cells.biome = new Uint8Array(cells.i.length); // biomes array cells.biome = new Uint8Array(cells.i.length); // biomes array
@ -1153,7 +1159,7 @@ function defineBiomes() {
return rn(4 + d3.mean(n)); return rn(4 + d3.mean(n));
} }
console.timeEnd("defineBiomes"); TIME && console.timeEnd("defineBiomes");
} }
// assign biome id to a cell // assign biome id to a cell
@ -1168,7 +1174,7 @@ function getBiomeId(moisture, temperature, height) {
// assess cells suitability to calculate population and rand cells for culture center and burgs placement // assess cells suitability to calculate population and rand cells for culture center and burgs placement
function rankCells() { function rankCells() {
console.time('rankCells'); TIME && console.time('rankCells');
const cells = pack.cells, f = pack.features; const cells = pack.cells, f = pack.features;
cells.s = new Int16Array(cells.i.length); // cell suitability array cells.s = new Int16Array(cells.i.length); // cell suitability array
cells.pop = new Float32Array(cells.i.length); // cell population array cells.pop = new Float32Array(cells.i.length); // cell population array
@ -1202,13 +1208,13 @@ function rankCells() {
cells.pop[i] = cells.s[i] > 0 ? cells.s[i] * cells.area[i] / areaMean : 0; cells.pop[i] = cells.s[i] > 0 ? cells.s[i] * cells.area[i] / areaMean : 0;
} }
console.timeEnd('rankCells'); TIME && console.timeEnd('rankCells');
} }
// generate some markers // generate some markers
function addMarkers(number = 1) { function addMarkers(number = 1) {
if (!number) return; if (!number) return;
console.time("addMarkers"); TIME && console.time("addMarkers");
const cells = pack.cells, states = pack.states; const cells = pack.cells, states = pack.states;
void function addVolcanoes() { void function addVolcanoes() {
@ -1374,12 +1380,12 @@ function addMarkers(number = 1) {
return id; return id;
} }
console.timeEnd("addMarkers"); TIME && console.timeEnd("addMarkers");
} }
// regenerate some zones // regenerate some zones
function addZones(number = 1) { function addZones(number = 1) {
console.time("addZones"); TIME && console.time("addZones");
const data = [], cells = pack.cells, states = pack.states, burgs = pack.burgs; const data = [], cells = pack.cells, states = pack.states, burgs = pack.burgs;
const used = new Uint8Array(cells.i.length); // to store used cells const used = new Uint8Array(cells.i.length); // to store used cells
@ -1690,7 +1696,7 @@ function addZones(number = 1) {
.attr("points", d => getPackPolygon(d)).attr("id", function(d) {return this.parentNode.id+"_"+d}); .attr("points", d => getPackPolygon(d)).attr("id", function(d) {return this.parentNode.id+"_"+d});
}() }()
console.timeEnd("addZones"); TIME && console.timeEnd("addZones");
} }
// show map stats on generation complete // show map stats on generation complete
@ -1712,11 +1718,11 @@ function showStatistics() {
mapId = Date.now(); // unique map id is it's creation date number mapId = Date.now(); // unique map id is it's creation date number
mapHistory.push({seed, width:graphWidth, height:graphHeight, template, created:mapId}); mapHistory.push({seed, width:graphWidth, height:graphHeight, template, created:mapId});
console.log(stats); INFO && console.log(stats);
} }
const regenerateMap = debounce(function() { const regenerateMap = debounce(function() {
console.warn("Generate new random map"); WARN && console.warn("Generate new random map");
closeDialogs("#worldConfigurator, #options3d"); closeDialogs("#worldConfigurator, #options3d");
customization = 0; customization = 0;
undraw(); undraw();

View file

@ -32,7 +32,7 @@
drawBurgs(); drawBurgs();
function placeCapitals() { function placeCapitals() {
console.time('placeCapitals'); TIME && console.time('placeCapitals');
let count = +regionsInput.value; let count = +regionsInput.value;
let burgs = [0]; let burgs = [0];
@ -41,8 +41,8 @@
if (sorted.length < count * 10) { if (sorted.length < count * 10) {
count = Math.floor(sorted.length / 10); count = Math.floor(sorted.length / 10);
if (!count) {console.warn(`There is no populated cells. Cannot generate states`); return burgs;} if (!count) {WARN && console.warn(`There is no populated cells. Cannot generate states`); return burgs;}
else {console.warn(`Not enough populated cells (${sorted.length}). Will generate only ${count} states`);} else {WARN && console.warn(`Not enough populated cells (${sorted.length}). Will generate only ${count} states`);}
} }
let burgsTree = d3.quadtree(); let burgsTree = d3.quadtree();
@ -57,20 +57,20 @@
} }
if (i === sorted.length - 1) { if (i === sorted.length - 1) {
console.warn("Cannot place capitals with current spacing. Trying again with reduced spacing"); WARN && console.warn("Cannot place capitals with current spacing. Trying again with reduced spacing");
burgsTree = d3.quadtree(); burgsTree = d3.quadtree();
i = -1, burgs = [0], spacing /= 1.2; i = -1, burgs = [0], spacing /= 1.2;
} }
} }
burgs[0] = burgsTree; burgs[0] = burgsTree;
console.timeEnd('placeCapitals'); TIME && console.timeEnd('placeCapitals');
return burgs; return burgs;
} }
// For each capital create a state // For each capital create a state
function createStates() { function createStates() {
console.time('createStates'); TIME && console.time('createStates');
const states = [{i:0, name: "Neutrals"}]; const states = [{i:0, name: "Neutrals"}];
const colors = getColors(burgs.length-1); const colors = getColors(burgs.length-1);
@ -94,13 +94,13 @@
cells.burg[b.cell] = i; cells.burg[b.cell] = i;
}); });
console.timeEnd('createStates'); TIME && console.timeEnd('createStates');
return states; return states;
} }
// place secondary settlements based on geo and economical evaluation // place secondary settlements based on geo and economical evaluation
function placeTowns() { function placeTowns() {
console.time('placeTowns'); TIME && console.time('placeTowns');
const score = new Int16Array(cells.s.map(s => s * gauss(1,3,0,20,3))); // a bit randomized cell score for towns placement const score = new Int16Array(cells.s.map(s => s * gauss(1,3,0,20,3))); // a bit randomized cell score for towns placement
const sorted = cells.i.filter(i => !cells.burg[i] && score[i] > 0 && cells.culture[i]).sort((a, b) => score[b] - score[a]); // filtered and sorted array of indexes const sorted = cells.i.filter(i => !cells.burg[i] && score[i] > 0 && cells.culture[i]).sort((a, b) => score[b] - score[a]); // filtered and sorted array of indexes
@ -129,17 +129,17 @@
} }
if (manorsInput.value != 1000 && burgsAdded < desiredNumber) { if (manorsInput.value != 1000 && burgsAdded < desiredNumber) {
console.error(`Cannot place all burgs. Requested ${desiredNumber}, placed ${burgsAdded}`); ERROR && console.error(`Cannot place all burgs. Requested ${desiredNumber}, placed ${burgsAdded}`);
} }
burgs[0] = {name:undefined}; // do not store burgsTree anymore burgs[0] = {name:undefined}; // do not store burgsTree anymore
console.timeEnd('placeTowns'); TIME && console.timeEnd('placeTowns');
} }
} }
// define burg coordinates, port status and define details // define burg coordinates, port status and define details
const specifyBurgs = function() { const specifyBurgs = function() {
console.time("specifyBurgs"); TIME && console.time("specifyBurgs");
const cells = pack.cells, vertices = pack.vertices, features = pack.features, temp = grid.cells.temp; const cells = pack.cells, vertices = pack.vertices, features = pack.features, temp = grid.cells.temp;
for (const b of pack.burgs) { for (const b of pack.burgs) {
@ -185,7 +185,7 @@
if (featurePorts.length === 1) featurePorts[0].port = 0; if (featurePorts.length === 1) featurePorts[0].port = 0;
} }
console.timeEnd("specifyBurgs"); TIME && console.timeEnd("specifyBurgs");
} }
const defineBurgFeatures = function(newburg) { const defineBurgFeatures = function(newburg) {
@ -202,7 +202,7 @@
} }
const drawBurgs = function() { const drawBurgs = function() {
console.time("drawBurgs"); TIME && console.time("drawBurgs");
// remove old data // remove old data
burgIcons.selectAll("circle").remove(); burgIcons.selectAll("circle").remove();
@ -251,12 +251,12 @@
.attr("x", d => rn(d.x - taSize * .47, 2)).attr("y", d => rn(d.y - taSize * .47, 2)) .attr("x", d => rn(d.x - taSize * .47, 2)).attr("y", d => rn(d.y - taSize * .47, 2))
.attr("width", taSize).attr("height", taSize); .attr("width", taSize).attr("height", taSize);
console.timeEnd("drawBurgs"); TIME && console.timeEnd("drawBurgs");
} }
// growth algorithm to assign cells to states like we did for cultures // growth algorithm to assign cells to states like we did for cultures
const expandStates = function() { const expandStates = function() {
console.time("expandStates"); TIME && console.time("expandStates");
const cells = pack.cells, states = pack.states, cultures = pack.cultures, burgs = pack.burgs; const cells = pack.cells, states = pack.states, cultures = pack.cultures, burgs = pack.burgs;
cells.state = new Uint16Array(cells.i.length); // cell state cells.state = new Uint16Array(cells.i.length); // cell state
@ -331,11 +331,11 @@
return 0; return 0;
} }
console.timeEnd("expandStates"); TIME && console.timeEnd("expandStates");
} }
const normalizeStates = function() { const normalizeStates = function() {
console.time("normalizeStates"); TIME && console.time("normalizeStates");
const cells = pack.cells, burgs = pack.burgs; const cells = pack.cells, burgs = pack.burgs;
for (const i of cells.i) { for (const i of cells.i) {
@ -350,13 +350,13 @@
cells.state[i] = cells.state[adversaries[0]]; cells.state[i] = cells.state[adversaries[0]];
//debug.append("circle").attr("cx", cells.p[i][0]).attr("cy", cells.p[i][1]).attr("r", .5).attr("fill", "red"); //debug.append("circle").attr("cx", cells.p[i][0]).attr("cy", cells.p[i][1]).attr("r", .5).attr("fill", "red");
} }
console.timeEnd("normalizeStates"); TIME && console.timeEnd("normalizeStates");
} }
// Resets the cultures of all burgs and states to their // Resets the cultures of all burgs and states to their
// cell or center cell's (respectively) culture. // cell or center cell's (respectively) culture.
const updateCultures = function () { const updateCultures = function () {
console.time('updateCulturesForBurgsAndStates'); TIME && console.time('updateCulturesForBurgsAndStates');
// Assign the culture associated with the burgs cell. // Assign the culture associated with the burgs cell.
pack.burgs = pack.burgs.map( (burg, index) => { pack.burgs = pack.burgs.map( (burg, index) => {
@ -376,12 +376,12 @@
return {...state, culture: pack.cells.culture[state.center]}; return {...state, culture: pack.cells.culture[state.center]};
}); });
console.timeEnd('updateCulturesForBurgsAndStates'); TIME && console.timeEnd('updateCulturesForBurgsAndStates');
} }
// calculate and draw curved state labels for a list of states // calculate and draw curved state labels for a list of states
const drawStateLabels = function(list) { const drawStateLabels = function(list) {
console.time("drawStateLabels"); TIME && console.time("drawStateLabels");
const cells = pack.cells, features = pack.features, states = pack.states; const cells = pack.cells, features = pack.features, states = pack.states;
const paths = []; // text paths const paths = []; // text paths
lineGen.curve(d3.curveBundle.beta(1)); lineGen.curve(d3.curveBundle.beta(1));
@ -563,12 +563,12 @@
if (!displayed) toggleLabels(); if (!displayed) toggleLabels();
}() }()
console.timeEnd("drawStateLabels"); TIME && console.timeEnd("drawStateLabels");
} }
// calculate states data like area, population etc. // calculate states data like area, population etc.
const collectStatistics = function() { const collectStatistics = function() {
console.time("collectStatistics"); TIME && console.time("collectStatistics");
const cells = pack.cells, states = pack.states; const cells = pack.cells, states = pack.states;
states.forEach(s => { states.forEach(s => {
s.cells = s.area = s.burgs = s.rural = s.urban = 0; s.cells = s.area = s.burgs = s.rural = s.urban = 0;
@ -595,11 +595,11 @@
// convert neighbors Set object into array // convert neighbors Set object into array
states.forEach(s => s.neighbors = Array.from(s.neighbors)); states.forEach(s => s.neighbors = Array.from(s.neighbors));
console.timeEnd("collectStatistics"); TIME && console.timeEnd("collectStatistics");
} }
const assignColors = function() { const assignColors = function() {
console.time("assignColors"); TIME && console.time("assignColors");
const colors = ["#66c2a5", "#fc8d62", "#8da0cb", "#e78ac3", "#a6d854", "#ffd92f"]; // d3.schemeSet2; const colors = ["#66c2a5", "#fc8d62", "#8da0cb", "#e78ac3", "#a6d854", "#ffd92f"]; // d3.schemeSet2;
// assin basic color using greedy coloring algorithm // assin basic color using greedy coloring algorithm
@ -620,7 +620,7 @@
}); });
}); });
console.timeEnd("assignColors"); TIME && console.timeEnd("assignColors");
} }
// generate historical conflicts of each state // generate historical conflicts of each state
@ -641,7 +641,7 @@
// generate Diplomatic Relationships // generate Diplomatic Relationships
const generateDiplomacy = function() { const generateDiplomacy = function() {
console.time("generateDiplomacy"); TIME && console.time("generateDiplomacy");
const cells = pack.cells, states = pack.states; const cells = pack.cells, states = pack.states;
const chronicle = states[0].diplomacy = []; const chronicle = states[0].diplomacy = [];
const valid = states.filter(s => s.i && !states.removed); const valid = states.filter(s => s.i && !states.removed);
@ -782,13 +782,13 @@
chronicle.push(war); // add a record to diplomatical history chronicle.push(war); // add a record to diplomatical history
} }
console.timeEnd("generateDiplomacy"); TIME && console.timeEnd("generateDiplomacy");
//console.table(states.map(s => s.diplomacy)); //console.table(states.map(s => s.diplomacy));
} }
// select a forms for listed or all valid states // select a forms for listed or all valid states
const defineStateForms = function(list) { const defineStateForms = function(list) {
console.time("defineStateForms"); TIME && console.time("defineStateForms");
const states = pack.states.filter(s => s.i && !s.removed); const states = pack.states.filter(s => s.i && !s.removed);
if (states.length < 1) return; if (states.length < 1) return;
@ -878,7 +878,7 @@
} }
} }
console.timeEnd("defineStateForms"); TIME && console.timeEnd("defineStateForms");
} }
const getFullName = function(s) { const getFullName = function(s) {
@ -890,7 +890,7 @@
} }
const generateProvinces = function(regenerate) { const generateProvinces = function(regenerate) {
console.time("generateProvinces"); TIME && console.time("generateProvinces");
const localSeed = regenerate ? Math.floor(Math.random() * 1e9).toString() : seed; const localSeed = regenerate ? Math.floor(Math.random() * 1e9).toString() : seed;
Math.seedrandom(localSeed); Math.seedrandom(localSeed);
@ -1050,7 +1050,7 @@
} }
}); });
console.timeEnd("generateProvinces"); TIME && console.timeEnd("generateProvinces");
} }
return {generate, expandStates, normalizeStates, assignColors, return {generate, expandStates, normalizeStates, assignColors,

View file

@ -7,7 +7,7 @@
let cells; let cells;
const generate = function() { const generate = function() {
console.time('generateCultures'); TIME && console.time('generateCultures');
cells = pack.cells; cells = pack.cells;
cells.culture = new Uint16Array(cells.i.length); // cell cultures cells.culture = new Uint16Array(cells.i.length); // cell cultures
let count = Math.min(+culturesInput.value, +culturesSet.selectedOptions[0].dataset.max); let count = Math.min(+culturesInput.value, +culturesSet.selectedOptions[0].dataset.max);
@ -16,7 +16,7 @@
if (populated.length < count * 25) { if (populated.length < count * 25) {
count = Math.floor(populated.length / 50); count = Math.floor(populated.length / 50);
if (!count) { if (!count) {
console.warn(`There are no populated cells. Cannot generate cultures`); WARN && console.warn(`There are no populated cells. Cannot generate cultures`);
pack.cultures = [{name:"Wildlands", i:0, base:1}]; pack.cultures = [{name:"Wildlands", i:0, base:1}];
alertMessage.innerHTML = ` alertMessage.innerHTML = `
The climate is harsh and people cannot live in this world.<br> The climate is harsh and people cannot live in this world.<br>
@ -27,7 +27,7 @@
}); });
return; return;
} else { } else {
console.warn(`Not enough populated cells (${populated.length}). Will generate only ${count} cultures`); WARN && console.warn(`Not enough populated cells (${populated.length}). Will generate only ${count} cultures`);
alertMessage.innerHTML = ` alertMessage.innerHTML = `
There are only ${populated.length} populated cells and it's insufficient livable area.<br> There are only ${populated.length} populated cells and it's insufficient livable area.<br>
Only ${count} out of ${culturesInput.value} requested cultures will be generated.<br> Only ${count} out of ${culturesInput.value} requested cultures will be generated.<br>
@ -68,7 +68,7 @@
cultures.unshift({name:"Wildlands", i:0, base:1, origin:null}); cultures.unshift({name:"Wildlands", i:0, base:1, origin:null});
// make sure all bases exist in nameBases // make sure all bases exist in nameBases
if (!nameBases.length) {console.error("Name base is empty, default nameBases will be applied"); nameBases = Names.getNameBases();} if (!nameBases.length) {ERROR && console.error("Name base is empty, default nameBases will be applied"); nameBases = Names.getNameBases();}
cultures.forEach(c => c.base = c.base % nameBases.length); cultures.forEach(c => c.base = c.base % nameBases.length);
function getRandomCultures(c) { function getRandomCultures(c) {
@ -108,7 +108,7 @@
return rn((Math.random() * powerInput.value / 2 + 1) * base, 1); return rn((Math.random() * powerInput.value / 2 + 1) * base, 1);
} }
console.timeEnd('generateCultures'); TIME && console.timeEnd('generateCultures');
} }
// assign a unique two-letters code (abbreviation) // assign a unique two-letters code (abbreviation)
@ -355,7 +355,7 @@
// expand cultures across the map (Dijkstra-like algorithm) // expand cultures across the map (Dijkstra-like algorithm)
const expand = function() { const expand = function() {
console.time('expandCultures'); TIME && console.time('expandCultures');
cells = pack.cells; cells = pack.cells;
const queue = new PriorityQueue({comparator: (a, b) => a.p - b.p}); const queue = new PriorityQueue({comparator: (a, b) => a.p - b.p});
@ -392,7 +392,7 @@
}); });
} }
//debug.selectAll(".text").data(cost).enter().append("text").attr("x", (d, e) => cells.p[e][0]-1).attr("y", (d, e) => cells.p[e][1]-1).text(d => d ? rn(d) : "").attr("font-size", 2); //debug.selectAll(".text").data(cost).enter().append("text").attr("x", (d, e) => cells.p[e][0]-1).attr("y", (d, e) => cells.p[e][1]-1).text(d => d ? rn(d) : "").attr("font-size", 2);
console.timeEnd('expandCultures'); TIME && console.timeEnd('expandCultures');
} }
function getBiomeCost(c, biome, type) { function getBiomeCost(c, biome, type) {

View file

@ -7,7 +7,7 @@
let cells, p; let cells, p;
const generate = function() { const generate = function() {
console.time('generateHeightmap'); TIME && console.time('generateHeightmap');
cells = grid.cells, p = grid.points; cells = grid.cells, p = grid.points;
cells.h = new Uint8Array(grid.points.length); cells.h = new Uint8Array(grid.points.length);
@ -25,7 +25,7 @@
case "Shattered": templateShattered(); break; case "Shattered": templateShattered(); break;
} }
console.timeEnd('generateHeightmap'); TIME && console.timeEnd('generateHeightmap');
} }
// parse template step // parse template step
@ -507,7 +507,7 @@
} }
function getPointInRange(range, length) { function getPointInRange(range, length) {
if (typeof range !== "string") {console.error("Range should be a string"); return;} if (typeof range !== "string") {ERROR && console.error("Range should be a string"); return;}
const min = range.split("-")[0]/100 || 0; const min = range.split("-")[0]/100 || 0;
const max = range.split("-")[1]/100 || 100; const max = range.split("-")[1]/100 || 100;
return rand(min * length, max * length); return rand(min * length, max * length);

View file

@ -7,7 +7,7 @@
let cells, p, states; let cells, p, states;
const generate = function() { const generate = function() {
console.time("generateMilitaryForces"); TIME && console.time("generateMilitaryForces");
cells = pack.cells, p = cells.p, states = pack.states; cells = pack.cells, p = cells.p, states = pack.states;
const valid = states.filter(s => s.i && !s.removed); // valid states const valid = states.filter(s => s.i && !s.removed); // valid states
if (!options.military) options.military = getDefaultOptions(); if (!options.military) options.military = getDefaultOptions();
@ -176,7 +176,7 @@
return regiments; return regiments;
} }
console.timeEnd("generateMilitaryForces"); TIME && console.timeEnd("generateMilitaryForces");
} }
const getDefaultOptions = function() { const getDefaultOptions = function() {

View file

@ -56,13 +56,13 @@
// generate name using Markov's chain // generate name using Markov's chain
const getBase = function(base, min, max, dupl) { const getBase = function(base, min, max, dupl) {
if (base === undefined) {console.error("Please define a base"); return;} if (base === undefined) {ERROR && console.error("Please define a base"); return;}
if (!chains[base]) updateChain(base); if (!chains[base]) updateChain(base);
const data = chains[base]; const data = chains[base];
if (!data || data[""] === undefined) { if (!data || data[""] === undefined) {
tip("Namesbase " + base + " is incorrect. Please check in namesbase editor", false, "error"); tip("Namesbase " + base + " is incorrect. Please check in namesbase editor", false, "error");
console.error("Namebase " + base + " is incorrect!"); ERROR && console.error("Namebase " + base + " is incorrect!");
return "ERROR"; return "ERROR";
} }
@ -106,7 +106,7 @@
if (name.split(" ").some(part => part.length < 2)) name = name.split(" ").map((p,i) => i ? p.toLowerCase() : p).join(""); if (name.split(" ").some(part => part.length < 2)) name = name.split(" ").map((p,i) => i ? p.toLowerCase() : p).join("");
if (name.length < 2) { if (name.length < 2) {
console.error("Name is too short! Random name will be selected"); ERROR && console.error("Name is too short! Random name will be selected");
name = ra(nameBases[base].b.split(",")); name = ra(nameBases[base].b.split(","));
} }
@ -115,14 +115,14 @@
// generate name for culture // generate name for culture
const getCulture = function(culture, min, max, dupl) { const getCulture = function(culture, min, max, dupl) {
if (culture === undefined) {console.error("Please define a culture"); return;} if (culture === undefined) {ERROR && console.error("Please define a culture"); return;}
const base = pack.cultures[culture].base; const base = pack.cultures[culture].base;
return getBase(base, min, max, dupl); return getBase(base, min, max, dupl);
} }
// generate short name for culture // generate short name for culture
const getCultureShort = function(culture) { const getCultureShort = function(culture) {
if (culture === undefined) {console.error("Please define a culture"); return;} if (culture === undefined) {ERROR && console.error("Please define a culture"); return;}
return getBaseShort(pack.cultures[culture].base); return getBaseShort(pack.cultures[culture].base);
} }
@ -139,8 +139,8 @@
// generate state name based on capital or random name and culture-specific suffix // generate state name based on capital or random name and culture-specific suffix
const getState = function(name, culture, base) { const getState = function(name, culture, base) {
if (name === undefined) {console.error("Please define a base name"); return;} if (name === undefined) {ERROR && console.error("Please define a base name"); return;}
if (culture === undefined && base === undefined) {console.error("Please define a culture"); return;} if (culture === undefined && base === undefined) {ERROR && console.error("Please define a culture"); return;}
if (base === undefined) base = pack.cultures[culture].base; if (base === undefined) base = pack.cultures[culture].base;
// exclude endings inappropriate for states name // exclude endings inappropriate for states name

View file

@ -9,7 +9,7 @@
const OceanLayers = function OceanLayers() { const OceanLayers = function OceanLayers() {
const outline = oceanLayers.attr("layers"); const outline = oceanLayers.attr("layers");
if (outline === "none") return; if (outline === "none") return;
console.time("drawOceanLayers"); TIME && console.time("drawOceanLayers");
lineGen.curve(d3.curveBasisClosed); lineGen.curve(d3.curveBasisClosed);
cells = grid.cells, pointsN = grid.cells.i.length, vertices = grid.vertices; cells = grid.cells, pointsN = grid.cells.i.length, vertices = grid.vertices;
@ -51,7 +51,7 @@
return cells.v[i][cells.c[i].findIndex(c => cells.t[c] < t || !cells.t[c])]; return cells.v[i][cells.c[i].findIndex(c => cells.t[c] < t || !cells.t[c])];
} }
console.timeEnd("drawOceanLayers"); TIME && console.timeEnd("drawOceanLayers");
} }
function randomizeOutline() { function randomizeOutline() {
@ -89,7 +89,7 @@
if (v[0] !== undefined && v[0] !== prev && c0 !== c1) current = v[0]; if (v[0] !== undefined && v[0] !== prev && c0 !== c1) current = v[0];
else if (v[1] !== undefined && v[1] !== prev && c1 !== c2) current = v[1]; else if (v[1] !== undefined && v[1] !== prev && c1 !== c2) current = v[1];
else if (v[2] !== undefined && v[2] !== prev && c0 !== c2) current = v[2]; else if (v[2] !== undefined && v[2] !== prev && c0 !== c2) current = v[2];
if (current === chain[chain.length - 1]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length - 1]) {ERROR && console.error("Next vertex is not found"); break;}
} }
chain.push(chain[0]); // push first vertex as the last one chain.push(chain[0]); // push first vertex as the last one
return chain; return chain;

View file

@ -5,7 +5,7 @@
}(this, (function () {'use strict'; }(this, (function () {'use strict';
const ReliefIcons = function() { const ReliefIcons = function() {
console.time('drawRelief'); TIME && console.time('drawRelief');
terrain.selectAll("*").remove(); terrain.selectAll("*").remove();
const density = terrain.attr("density") || .4; const density = terrain.attr("density") || .4;
const size = 1.6 * (terrain.attr("size") || 1); const size = 1.6 * (terrain.attr("size") || 1);
@ -69,7 +69,7 @@
terrain.html(reliefHTML); terrain.html(reliefHTML);
}() }()
console.timeEnd('drawRelief'); TIME && console.timeEnd('drawRelief');
} }
function getBiomeIcon(i, b) { function getBiomeIcon(i, b) {

View file

@ -54,7 +54,7 @@
}; };
const generate = function() { const generate = function() {
console.time('generateReligions'); TIME && console.time('generateReligions');
const cells = pack.cells, states = pack.states, cultures = pack.cultures; const cells = pack.cells, states = pack.states, cultures = pack.cultures;
const religions = pack.religions = []; const religions = pack.religions = [];
cells.religion = new Uint16Array(cells.culture); // cell religion; initially based on culture cells.religion = new Uint16Array(cells.culture); // cell religion; initially based on culture
@ -164,7 +164,7 @@
expandHeresies(); expandHeresies();
checkCenters(); checkCenters();
console.timeEnd('generateReligions'); TIME && console.timeEnd('generateReligions');
} }
const add = function(center) { const add = function(center) {
@ -280,14 +280,14 @@
} }
function updateCultures() { function updateCultures() {
console.time('updateCulturesForReligions'); TIME && console.time('updateCulturesForReligions');
pack.religions = pack.religions.map( (religion, index) => { pack.religions = pack.religions.map( (religion, index) => {
if(index === 0) { if(index === 0) {
return religion; return religion;
} }
return {...religion, culture: pack.cells.culture[religion.center]}; return {...religion, culture: pack.cells.culture[religion.center]};
}); });
console.timeEnd('updateCulturesForReligions'); TIME && console.timeEnd('updateCulturesForReligions');
} }
// assign a unique two-letters code (abbreviation) // assign a unique two-letters code (abbreviation)
@ -303,7 +303,7 @@
// get supreme deity name // get supreme deity name
const getDeityName = function(culture) { const getDeityName = function(culture) {
if (culture === undefined) {console.error("Please define a culture"); return;} if (culture === undefined) {ERROR && console.error("Please define a culture"); return;}
const meaning = generateMeaning(); const meaning = generateMeaning();
const cultureName = Names.getCulture(culture, null, null, "", .8); const cultureName = Names.getCulture(culture, null, null, "", .8);
return cultureName + ", The " + meaning; return cultureName + ", The " + meaning;

View file

@ -5,7 +5,7 @@
}(this, (function () {'use strict'; }(this, (function () {'use strict';
const generate = function(changeHeights = true) { const generate = function(changeHeights = true) {
console.time('generateRivers'); TIME && console.time('generateRivers');
Math.seedrandom(seed); Math.seedrandom(seed);
const cells = pack.cells, p = cells.p, features = pack.features; const cells = pack.cells, p = cells.p, features = pack.features;
@ -136,7 +136,7 @@
// apply change heights as basic one // apply change heights as basic one
if (changeHeights) cells.h = Uint8Array.from(h); if (changeHeights) cells.h = Uint8Array.from(h);
console.timeEnd('generateRivers'); TIME && console.timeEnd('generateRivers');
} }
// depression filling algorithm (for a correct water flux modeling) // depression filling algorithm (for a correct water flux modeling)

View file

@ -5,7 +5,7 @@
}(this, (function () {'use strict'; }(this, (function () {'use strict';
const getRoads = function() { const getRoads = function() {
console.time("generateMainRoads"); TIME && console.time("generateMainRoads");
const cells = pack.cells, burgs = pack.burgs.filter(b => b.i && !b.removed); const cells = pack.cells, burgs = pack.burgs.filter(b => b.i && !b.removed);
const capitals = burgs.filter(b => b.capital); const capitals = burgs.filter(b => b.capital);
if (capitals.length < 2) return []; // not enough capitals to build main roads if (capitals.length < 2) return []; // not enough capitals to build main roads
@ -21,12 +21,12 @@
} }
cells.i.forEach(i => cells.s[i] += cells.road[i] / 2); // add roads to suitability score cells.i.forEach(i => cells.s[i] += cells.road[i] / 2); // add roads to suitability score
console.timeEnd("generateMainRoads"); TIME && console.timeEnd("generateMainRoads");
return paths; return paths;
} }
const getTrails = function() { const getTrails = function() {
console.time("generateTrails"); TIME && console.time("generateTrails");
const cells = pack.cells, burgs = pack.burgs.filter(b => b.i && !b.removed); const cells = pack.cells, burgs = pack.burgs.filter(b => b.i && !b.removed);
if (burgs.length < 2) return []; // not enough burgs to build trails if (burgs.length < 2) return []; // not enough burgs to build trails
@ -55,12 +55,12 @@
}); });
} }
console.timeEnd("generateTrails"); TIME && console.timeEnd("generateTrails");
return paths; return paths;
} }
const getSearoutes = function() { const getSearoutes = function() {
console.time("generateSearoutes"); TIME && console.time("generateSearoutes");
const allPorts = pack.burgs.filter(b => b.port > 0 && !b.removed); const allPorts = pack.burgs.filter(b => b.port > 0 && !b.removed);
if (allPorts.length < 2) return []; if (allPorts.length < 2) return [];
@ -93,12 +93,12 @@
}); });
console.timeEnd("generateSearoutes"); TIME && console.timeEnd("generateSearoutes");
return paths; return paths;
} }
const draw = function(main, small, ocean) { const draw = function(main, small, ocean) {
console.time("drawRoutes"); TIME && console.time("drawRoutes");
const cells = pack.cells, burgs = pack.burgs; const cells = pack.cells, burgs = pack.burgs;
lineGen.curve(d3.curveCatmullRom.alpha(0.1)); lineGen.curve(d3.curveCatmullRom.alpha(0.1));
@ -133,7 +133,7 @@
return [x, y]; return [x, y];
})), 1)); })), 1));
console.timeEnd("drawRoutes"); TIME && console.timeEnd("drawRoutes");
} }
const regenerate = function() { const regenerate = function() {

View file

@ -3,7 +3,7 @@
// download map as SVG // download map as SVG
async function saveSVG() { async function saveSVG() {
console.time("saveSVG"); TIME && console.time("saveSVG");
const url = await getMapURL("svg"); const url = await getMapURL("svg");
const link = document.createElement("a"); const link = document.createElement("a");
link.download = getFileName() + ".svg"; link.download = getFileName() + ".svg";
@ -12,12 +12,12 @@ async function saveSVG() {
link.click(); link.click();
tip(`${link.download} is saved. Open "Downloads" screen (crtl + J) to check. You can set image scale in options`, true, "success", 5000); tip(`${link.download} is saved. Open "Downloads" screen (crtl + J) to check. You can set image scale in options`, true, "success", 5000);
console.timeEnd("saveSVG"); TIME && console.timeEnd("saveSVG");
} }
// download map as PNG // download map as PNG
async function savePNG() { async function savePNG() {
console.time("savePNG"); TIME && console.time("savePNG");
const url = await getMapURL("png"); const url = await getMapURL("png");
const link = document.createElement("a"); const link = document.createElement("a");
@ -43,12 +43,12 @@ async function savePNG() {
}); });
} }
console.timeEnd("savePNG"); TIME && console.timeEnd("savePNG");
} }
// download map as JPEG // download map as JPEG
async function saveJPEG() { async function saveJPEG() {
console.time("saveJPEG"); TIME && console.time("saveJPEG");
const url = await getMapURL("png"); const url = await getMapURL("png");
const canvas = document.createElement("canvas"); const canvas = document.createElement("canvas");
@ -70,7 +70,7 @@ async function saveJPEG() {
window.setTimeout(() => window.URL.revokeObjectURL(URL), 5000); window.setTimeout(() => window.URL.revokeObjectURL(URL), 5000);
} }
console.timeEnd("saveJPEG"); TIME && console.timeEnd("saveJPEG");
} }
// parse map svg to object url // parse map svg to object url
@ -228,7 +228,7 @@ function GFontToDataURI(url) {
// prepare map data for saving // prepare map data for saving
function getMapData() { function getMapData() {
console.time("createMapDataBlob"); TIME && console.time("createMapDataBlob");
return new Promise(resolve => { return new Promise(resolve => {
const date = new Date(); const date = new Date();
@ -283,7 +283,7 @@ function getMapData() {
namesData, rivers].join("\r\n"); namesData, rivers].join("\r\n");
const blob = new Blob([data], {type: "text/plain"}); const blob = new Blob([data], {type: "text/plain"});
console.timeEnd("createMapDataBlob"); TIME && console.timeEnd("createMapDataBlob");
resolve(blob); resolve(blob);
}); });
@ -448,7 +448,7 @@ function quickLoad() {
loadMapPrompt(blob); loadMapPrompt(blob);
} else { } else {
tip("No map stored. Save map to storage first", true, "error", 2000); tip("No map stored. Save map to storage first", true, "error", 2000);
console.error("No map stored"); ERROR && console.error("No map stored");
} }
}); });
} }
@ -467,12 +467,12 @@ function loadMapPrompt(blob) {
}); });
function loadLastSavedMap() { function loadLastSavedMap() {
console.warn("Load last saved map"); WARN && console.warn("Load last saved map");
try { try {
uploadMap(blob); uploadMap(blob);
} }
catch(error) { catch(error) {
console.error(error); ERROR && console.error(error);
tip("Cannot load last saved map", true, "error", 2000); tip("Cannot load last saved map", true, "error", 2000);
} }
} }
@ -564,7 +564,7 @@ function parseLoadedData(data) {
mapId = params[6] ? +params[6] : Date.now(); mapId = params[6] ? +params[6] : Date.now();
}() }()
console.group("Loaded Map " + seed); INFO && console.group("Loaded Map " + seed);
void function parseSettings() { void function parseSettings() {
const settings = data[1].split("|"); const settings = data[1].split("|");
@ -1006,49 +1006,49 @@ function parseLoadedData(data) {
invalidStates.forEach(s => { invalidStates.forEach(s => {
const invalidCells = cells.i.filter(i => cells.state[i] === s); const invalidCells = cells.i.filter(i => cells.state[i] === s);
invalidCells.forEach(i => cells.state[i] = 0); invalidCells.forEach(i => cells.state[i] = 0);
console.error("Data Integrity Check. Invalid state", s, "is assigned to cells", invalidCells); ERROR && console.error("Data Integrity Check. Invalid state", s, "is assigned to cells", invalidCells);
}); });
const invalidProvinces = [...new Set(cells.province)].filter(p => p && (!pack.provinces[p] || pack.provinces[p].removed)); const invalidProvinces = [...new Set(cells.province)].filter(p => p && (!pack.provinces[p] || pack.provinces[p].removed));
invalidProvinces.forEach(p => { invalidProvinces.forEach(p => {
const invalidCells = cells.i.filter(i => cells.province[i] === p); const invalidCells = cells.i.filter(i => cells.province[i] === p);
invalidCells.forEach(i => cells.province[i] = 0); invalidCells.forEach(i => cells.province[i] = 0);
console.error("Data Integrity Check. Invalid province", p, "is assigned to cells", invalidCells); ERROR && console.error("Data Integrity Check. Invalid province", p, "is assigned to cells", invalidCells);
}); });
const invalidCultures = [...new Set(cells.culture)].filter(c => !pack.cultures[c] || pack.cultures[c].removed); const invalidCultures = [...new Set(cells.culture)].filter(c => !pack.cultures[c] || pack.cultures[c].removed);
invalidCultures.forEach(c => { invalidCultures.forEach(c => {
const invalidCells = cells.i.filter(i => cells.culture[i] === c); const invalidCells = cells.i.filter(i => cells.culture[i] === c);
invalidCells.forEach(i => cells.province[i] = 0); invalidCells.forEach(i => cells.province[i] = 0);
console.error("Data Integrity Check. Invalid culture", c, "is assigned to cells", invalidCells); ERROR && console.error("Data Integrity Check. Invalid culture", c, "is assigned to cells", invalidCells);
}); });
const invalidReligions = [...new Set(cells.religion)].filter(r => !pack.religions[r] || pack.religions[r].removed); const invalidReligions = [...new Set(cells.religion)].filter(r => !pack.religions[r] || pack.religions[r].removed);
invalidReligions.forEach(r => { invalidReligions.forEach(r => {
const invalidCells = cells.i.filter(i => cells.religion[i] === r); const invalidCells = cells.i.filter(i => cells.religion[i] === r);
invalidCells.forEach(i => cells.religion[i] = 0); invalidCells.forEach(i => cells.religion[i] = 0);
console.error("Data Integrity Check. Invalid religion", c, "is assigned to cells", invalidCells); ERROR && console.error("Data Integrity Check. Invalid religion", c, "is assigned to cells", invalidCells);
}); });
const invalidFeatures = [...new Set(cells.f)].filter(f => f && !pack.features[f]); const invalidFeatures = [...new Set(cells.f)].filter(f => f && !pack.features[f]);
invalidFeatures.forEach(f => { invalidFeatures.forEach(f => {
const invalidCells = cells.i.filter(i => cells.f[i] === f); const invalidCells = cells.i.filter(i => cells.f[i] === f);
// No fix as for now // No fix as for now
console.error("Data Integrity Check. Invalid feature", f, "is assigned to cells", invalidCells); ERROR && console.error("Data Integrity Check. Invalid feature", f, "is assigned to cells", invalidCells);
}); });
const invalidBurgs = [...new Set(cells.burg)].filter(b => b && (!pack.burgs[b] || pack.burgs[b].removed)); const invalidBurgs = [...new Set(cells.burg)].filter(b => b && (!pack.burgs[b] || pack.burgs[b].removed));
invalidBurgs.forEach(b => { invalidBurgs.forEach(b => {
const invalidCells = cells.i.filter(i => cells.burg[i] === b); const invalidCells = cells.i.filter(i => cells.burg[i] === b);
invalidCells.forEach(i => cells.burg[i] = 0); invalidCells.forEach(i => cells.burg[i] = 0);
console.error("Data Integrity Check. Invalid burg", b, "is assigned to cells", invalidCells); ERROR && console.error("Data Integrity Check. Invalid burg", b, "is assigned to cells", invalidCells);
}); });
pack.burgs.forEach(b => { pack.burgs.forEach(b => {
if (!b.i || b.removed) return; if (!b.i || b.removed) return;
if (b.port < 0) {console.error("Data Integrity Check. Burg", b.i, "has invalid port value", b.port); b.port = 0;} if (b.port < 0) {ERROR && console.error("Data Integrity Check. Burg", b.i, "has invalid port value", b.port); b.port = 0;}
if (b.cell < cells.i.length) return; if (b.cell < cells.i.length) return;
console.error("Data Integrity Check. Burg", b.i, "is linked to invalid cell", b.cell); ERROR && console.error("Data Integrity Check. Burg", b.i, "is linked to invalid cell", b.cell);
b.cell = findCell(b.x, b.y); b.cell = findCell(b.x, b.y);
cells.i.filter(i => cells.burg[i] === b.i).forEach(i => cells.burg[i] = 0); cells.i.filter(i => cells.burg[i] === b.i).forEach(i => cells.burg[i] = 0);
cells.burg[b.cell] = b.i; cells.burg[b.cell] = b.i;
@ -1065,13 +1065,13 @@ function parseLoadedData(data) {
focusOn(); // based on searchParams focus on point, cell or burg focusOn(); // based on searchParams focus on point, cell or burg
invokeActiveZooming(); invokeActiveZooming();
console.warn(`TOTAL: ${rn((performance.now()-uploadMap.timeStart)/1000,2)}s`); WARN && console.warn(`TOTAL: ${rn((performance.now()-uploadMap.timeStart)/1000,2)}s`);
showStatistics(); showStatistics();
console.groupEnd("Loaded Map " + seed); INFO && console.groupEnd("Loaded Map " + seed);
tip("Map is successfully loaded", true, "success", 7000); tip("Map is successfully loaded", true, "success", 7000);
} }
catch(error) { catch(error) {
console.error(error); ERROR && console.error(error);
clearMainTip(); clearMainTip();
alertMessage.innerHTML = `An error is occured on map loading. Select a different file to load, alertMessage.innerHTML = `An error is occured on map loading. Select a different file to load,

View file

@ -141,7 +141,7 @@ function editBurg(id) {
const label = document.querySelector("#burgLabels [data-id='" + id + "']"); const label = document.querySelector("#burgLabels [data-id='" + id + "']");
const icon = document.querySelector("#burgIcons [data-id='" + id + "']"); const icon = document.querySelector("#burgIcons [data-id='" + id + "']");
const anchor = document.querySelector("#anchors [data-id='" + id + "']"); const anchor = document.querySelector("#anchors [data-id='" + id + "']");
if (!label || !icon) {console.error("Cannot find label or icon elements"); return;} if (!label || !icon) {ERROR && console.error("Cannot find label or icon elements"); return;}
const labelG = document.querySelector("#burgLabels > #"+oldGroup); const labelG = document.querySelector("#burgLabels > #"+oldGroup);
const iconG = document.querySelector("#burgIcons > #"+oldGroup); const iconG = document.querySelector("#burgIcons > #"+oldGroup);

View file

@ -141,7 +141,7 @@ function moveBurgToGroup(id, g) {
const label = document.querySelector("#burgLabels [data-id='" + id + "']"); const label = document.querySelector("#burgLabels [data-id='" + id + "']");
const icon = document.querySelector("#burgIcons [data-id='" + id + "']"); const icon = document.querySelector("#burgIcons [data-id='" + id + "']");
const anchor = document.querySelector("#anchors [data-id='" + id + "']"); const anchor = document.querySelector("#anchors [data-id='" + id + "']");
if (!label || !icon) {console.error("Cannot find label or icon elements"); return;} if (!label || !icon) {ERROR && console.error("Cannot find label or icon elements"); return;}
document.querySelector("#burgLabels > #"+g).appendChild(label); document.querySelector("#burgLabels > #"+g).appendChild(label);
document.querySelector("#burgIcons > #"+g).appendChild(icon); document.querySelector("#burgIcons > #"+g).appendChild(icon);
@ -639,7 +639,7 @@ function selectIcon(initial, callback) {
// Calls the refresh functionality on all editors currently open. // Calls the refresh functionality on all editors currently open.
function refreshAllEditors() { function refreshAllEditors() {
console.time('refreshAllEditors'); TIME && console.time('refreshAllEditors');
if (document.getElementById('culturesEditorRefresh').offsetParent) culturesEditorRefresh.click(); if (document.getElementById('culturesEditorRefresh').offsetParent) culturesEditorRefresh.click();
if (document.getElementById('biomesEditorRefresh').offsetParent) biomesEditorRefresh.click(); if (document.getElementById('biomesEditorRefresh').offsetParent) biomesEditorRefresh.click();
if (document.getElementById('diplomacyEditorRefresh').offsetParent) diplomacyEditorRefresh.click(); if (document.getElementById('diplomacyEditorRefresh').offsetParent) diplomacyEditorRefresh.click();
@ -647,5 +647,5 @@ function refreshAllEditors() {
if (document.getElementById('religionsEditorRefresh').offsetParent) religionsEditorRefresh.click(); if (document.getElementById('religionsEditorRefresh').offsetParent) religionsEditorRefresh.click();
if (document.getElementById('statesEditorRefresh').offsetParent) statesEditorRefresh.click(); if (document.getElementById('statesEditorRefresh').offsetParent) statesEditorRefresh.click();
if (document.getElementById('zonesEditorRefresh').offsetParent) zonesEditorRefresh.click(); if (document.getElementById('zonesEditorRefresh').offsetParent) zonesEditorRefresh.click();
console.timeEnd('refreshAllEditors'); TIME && console.timeEnd('refreshAllEditors');
} }

View file

@ -164,8 +164,8 @@ function editHeightmap() {
} }
function regenerateErasedData() { function regenerateErasedData() {
console.group("Edit Heightmap"); INFO && console.group("Edit Heightmap");
console.time("regenerateErasedData"); TIME && console.time("regenerateErasedData");
const change = changeHeights.checked; const change = changeHeights.checked;
markFeatures(); markFeatures();
@ -204,8 +204,8 @@ function editHeightmap() {
Military.generate(); Military.generate();
addMarkers(); addMarkers();
addZones(); addZones();
console.timeEnd("regenerateErasedData"); TIME && console.timeEnd("regenerateErasedData");
console.groupEnd("Edit Heightmap"); INFO && console.groupEnd("Edit Heightmap");
} }
function restoreKeptData() { function restoreKeptData() {
@ -216,8 +216,8 @@ function editHeightmap() {
} }
function restoreRiskedData() { function restoreRiskedData() {
console.group("Edit Heightmap"); INFO && console.group("Edit Heightmap");
console.time("restoreRiskedData"); TIME && console.time("restoreRiskedData");
// assign pack data to grid cells // assign pack data to grid cells
const l = grid.cells.i.length; const l = grid.cells.i.length;
@ -401,8 +401,8 @@ function editHeightmap() {
.attr("points", d => getPackPolygon(d)).attr("id", d => base + d); .attr("points", d => getPackPolygon(d)).attr("id", d => base + d);
}); });
console.timeEnd("restoreRiskedData"); TIME && console.timeEnd("restoreRiskedData");
console.groupEnd("Edit Heightmap"); INFO && console.groupEnd("Edit Heightmap");
} }
// trigger heightmap redraw and history update if at least 1 cell is changed // trigger heightmap redraw and history update if at least 1 cell is changed
@ -954,7 +954,7 @@ function editHeightmap() {
templateBody.innerHTML = ""; templateBody.innerHTML = "";
for (const s of steps) { for (const s of steps) {
const step = s.split(" "); const step = s.split(" ");
if (step.length !== 5) {console.error("Cannot parse step, wrong arguments count", s); continue;} if (step.length !== 5) {ERROR && console.error("Cannot parse step, wrong arguments count", s); continue;}
addStep(step[0], step[1], step[2], step[3], step[4]); addStep(step[0], step[1], step[2], step[3], step[4]);
} }

View file

@ -131,7 +131,7 @@ function toggleHeight(event) {
} }
function drawHeightmap() { function drawHeightmap() {
console.time("drawHeightmap"); TIME && console.time("drawHeightmap");
terrs.selectAll("*").remove(); terrs.selectAll("*").remove();
const cells = pack.cells, vertices = pack.vertices, n = cells.i.length; const cells = pack.cells, vertices = pack.vertices, n = cells.i.length;
const used = new Uint8Array(cells.i.length); const used = new Uint8Array(cells.i.length);
@ -188,7 +188,7 @@ function drawHeightmap() {
if (v[0] !== prev && c0 !== c1) current = v[0]; if (v[0] !== prev && c0 !== c1) current = v[0];
else if (v[1] !== prev && c1 !== c2) current = v[1]; else if (v[1] !== prev && c1 !== c2) current = v[1];
else if (v[2] !== prev && c0 !== c2) current = v[2]; else if (v[2] !== prev && c0 !== c2) current = v[2];
if (current === chain[chain.length - 1]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length - 1]) {ERROR && console.error("Next vertex is not found"); break;}
} }
return chain; return chain;
} }
@ -199,7 +199,7 @@ function drawHeightmap() {
return chain.filter((d, i) => i % n === 0); return chain.filter((d, i) => i % n === 0);
} }
console.timeEnd("drawHeightmap"); TIME && console.timeEnd("drawHeightmap");
} }
function getColorScheme() { function getColorScheme() {
@ -228,7 +228,7 @@ function toggleTemp(event) {
} }
function drawTemp() { function drawTemp() {
console.time("drawTemp"); TIME && console.time("drawTemp");
temperature.selectAll("*").remove(); temperature.selectAll("*").remove();
lineGen.curve(d3.curveBasisClosed); lineGen.curve(d3.curveBasisClosed);
const scheme = d3.scaleSequential(d3.interpolateSpectral); const scheme = d3.scaleSequential(d3.interpolateSpectral);
@ -311,12 +311,12 @@ function drawTemp() {
if (v[0] !== prev && c0 !== c1) current = v[0]; if (v[0] !== prev && c0 !== c1) current = v[0];
else if (v[1] !== prev && c1 !== c2) current = v[1]; else if (v[1] !== prev && c1 !== c2) current = v[1];
else if (v[2] !== prev && c0 !== c2) current = v[2]; else if (v[2] !== prev && c0 !== c2) current = v[2];
if (current === chain[chain.length - 1]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length - 1]) {ERROR && console.error("Next vertex is not found"); break;}
} }
chain.push(start); chain.push(start);
return chain; return chain;
} }
console.timeEnd("drawTemp"); TIME && console.timeEnd("drawTemp");
} }
function toggleBiomes(event) { function toggleBiomes(event) {
@ -370,7 +370,7 @@ function drawBiomes() {
if (v[0] !== prev && c0 !== c1) current = v[0]; if (v[0] !== prev && c0 !== c1) current = v[0];
else if (v[1] !== prev && c1 !== c2) current = v[1]; else if (v[1] !== prev && c1 !== c2) current = v[1];
else if (v[2] !== prev && c0 !== c2) current = v[2]; else if (v[2] !== prev && c0 !== c2) current = v[2];
if (current === chain[chain.length - 1]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length - 1]) {ERROR && console.error("Next vertex is not found"); break;}
} }
return chain; return chain;
} }
@ -526,7 +526,7 @@ function drawIce() {
if (v[0] !== prev && c0 !== c1) current = v[0]; if (v[0] !== prev && c0 !== c1) current = v[0];
else if (v[1] !== prev && c1 !== c2) current = v[1]; else if (v[1] !== prev && c1 !== c2) current = v[1];
else if (v[2] !== prev && c0 !== c2) current = v[2]; else if (v[2] !== prev && c0 !== c2) current = v[2];
if (current === chain[chain.length - 1]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length - 1]) {ERROR && console.error("Next vertex is not found"); break;}
} }
return chain; return chain;
} }
@ -547,7 +547,7 @@ function toggleCultures(event) {
} }
function drawCultures() { function drawCultures() {
console.time("drawCultures"); TIME && console.time("drawCultures");
cults.selectAll("path").remove(); cults.selectAll("path").remove();
const cells = pack.cells, vertices = pack.vertices, cultures = pack.cultures, n = cells.i.length; const cells = pack.cells, vertices = pack.vertices, cultures = pack.cultures, n = cells.i.length;
@ -586,11 +586,11 @@ function drawCultures() {
if (v[0] !== prev && c0 !== c1) current = v[0]; if (v[0] !== prev && c0 !== c1) current = v[0];
else if (v[1] !== prev && c1 !== c2) current = v[1]; else if (v[1] !== prev && c1 !== c2) current = v[1];
else if (v[2] !== prev && c0 !== c2) current = v[2]; else if (v[2] !== prev && c0 !== c2) current = v[2];
if (current === chain[chain.length - 1]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length - 1]) {ERROR && console.error("Next vertex is not found"); break;}
} }
return chain; return chain;
} }
console.timeEnd("drawCultures"); TIME && console.timeEnd("drawCultures");
} }
function toggleReligions(event) { function toggleReligions(event) {
@ -607,7 +607,7 @@ function toggleReligions(event) {
} }
function drawReligions() { function drawReligions() {
console.time("drawReligions"); TIME && console.time("drawReligions");
relig.selectAll("path").remove(); relig.selectAll("path").remove();
const cells = pack.cells, vertices = pack.vertices, religions = pack.religions, features = pack.features, n = cells.i.length; const cells = pack.cells, vertices = pack.vertices, religions = pack.religions, features = pack.features, n = cells.i.length;
@ -657,12 +657,12 @@ function drawReligions() {
if (v[0] !== prev && c0 !== c1) {current = v[0]; check(c0 ? c[0] : c[1]);} else if (v[0] !== prev && c0 !== c1) {current = v[0]; check(c0 ? c[0] : c[1]);} else
if (v[1] !== prev && c1 !== c2) {current = v[1]; check(c1 ? c[1] : c[2]);} else if (v[1] !== prev && c1 !== c2) {current = v[1]; check(c1 ? c[1] : c[2]);} else
if (v[2] !== prev && c0 !== c2) {current = v[2]; check(c2 ? c[2] : c[0]);} if (v[2] !== prev && c0 !== c2) {current = v[2]; check(c2 ? c[2] : c[0]);}
if (current === chain[chain.length - 1][0]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length - 1][0]) {ERROR && console.error("Next vertex is not found"); break;}
} }
return chain; return chain;
} }
console.timeEnd("drawReligions"); TIME && console.timeEnd("drawReligions");
} }
function toggleStates(event) { function toggleStates(event) {
@ -680,7 +680,7 @@ function toggleStates(event) {
// draw states // draw states
function drawStates() { function drawStates() {
console.time("drawStates"); TIME && console.time("drawStates");
regions.selectAll("path").remove(); regions.selectAll("path").remove();
const cells = pack.cells, vertices = pack.vertices, states = pack.states, n = cells.i.length; const cells = pack.cells, vertices = pack.vertices, states = pack.states, n = cells.i.length;
@ -741,18 +741,18 @@ function drawStates() {
if (v[0] !== prev && c0 !== c1) {current = v[0]; check(c0 ? c[0] : c[1]);} else if (v[0] !== prev && c0 !== c1) {current = v[0]; check(c0 ? c[0] : c[1]);} else
if (v[1] !== prev && c1 !== c2) {current = v[1]; check(c1 ? c[1] : c[2]);} else if (v[1] !== prev && c1 !== c2) {current = v[1]; check(c1 ? c[1] : c[2]);} else
if (v[2] !== prev && c0 !== c2) {current = v[2]; check(c2 ? c[2] : c[0]);} if (v[2] !== prev && c0 !== c2) {current = v[2]; check(c2 ? c[2] : c[0]);}
if (current === chain[chain.length - 1][0]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length - 1][0]) {ERROR && console.error("Next vertex is not found"); break;}
} }
chain.push([start, state, land]); // add starting vertex to sequence to close the path chain.push([start, state, land]); // add starting vertex to sequence to close the path
return chain; return chain;
} }
invokeActiveZooming(); invokeActiveZooming();
console.timeEnd("drawStates"); TIME && console.timeEnd("drawStates");
} }
// draw state and province borders // draw state and province borders
function drawBorders() { function drawBorders() {
console.time("drawBorders"); TIME && console.time("drawBorders");
borders.selectAll("path").remove(); borders.selectAll("path").remove();
const cells = pack.cells, vertices = pack.vertices, n = cells.i.length; const cells = pack.cells, vertices = pack.vertices, n = cells.i.length;
@ -807,7 +807,7 @@ function drawBorders() {
// find starting vertex // find starting vertex
for (let i=0; i < 1000; i++) { for (let i=0; i < 1000; i++) {
if (i === 999) console.error("Find starting vertex: limit is reached", current, f, t); if (i === 999) ERROR && console.error("Find starting vertex: limit is reached", current, f, t);
const p = chain[chain.length-2] || -1; // previous vertex const p = chain[chain.length-2] || -1; // previous vertex
const v = vertices.v[current], c = vertices.c[current]; const v = vertices.v[current], c = vertices.c[current];
@ -825,7 +825,7 @@ function drawBorders() {
chain = [current]; // vertices chain to form a path chain = [current]; // vertices chain to form a path
// find path // find path
for (let i=0; i < 1000; i++) { for (let i=0; i < 1000; i++) {
if (i === 999) console.error("Find path: limit is reached", current, f, t); if (i === 999) ERROR && console.error("Find path: limit is reached", current, f, t);
const p = chain[chain.length-2] || -1; // previous vertex const p = chain[chain.length-2] || -1; // previous vertex
const v = vertices.v[current], c = vertices.c[current]; const v = vertices.v[current], c = vertices.c[current];
c.filter(c => array[c] === t).forEach(c => used[f][c] = t); c.filter(c => array[c] === t).forEach(c => used[f][c] = t);
@ -845,7 +845,7 @@ function drawBorders() {
return chain; return chain;
} }
console.timeEnd("drawBorders"); TIME && console.timeEnd("drawBorders");
} }
function toggleBorders(event) { function toggleBorders(event) {
@ -873,7 +873,7 @@ function toggleProvinces(event) {
} }
function drawProvinces() { function drawProvinces() {
console.time("drawProvinces"); TIME && console.time("drawProvinces");
const labelsOn = provs.attr("data-labels") == 1; const labelsOn = provs.attr("data-labels") == 1;
provs.selectAll("*").remove(); provs.selectAll("*").remove();
@ -937,12 +937,12 @@ function drawProvinces() {
if (v[0] !== prev && c0 !== c1) {current = v[0]; check(c0 ? c[0] : c[1]);} else if (v[0] !== prev && c0 !== c1) {current = v[0]; check(c0 ? c[0] : c[1]);} else
if (v[1] !== prev && c1 !== c2) {current = v[1]; check(c1 ? c[1] : c[2]);} else if (v[1] !== prev && c1 !== c2) {current = v[1]; check(c1 ? c[1] : c[2]);} else
if (v[2] !== prev && c0 !== c2) {current = v[2]; check(c2 ? c[2] : c[0]);} if (v[2] !== prev && c0 !== c2) {current = v[2]; check(c2 ? c[2] : c[0]);}
if (current === chain[chain.length-1][0]) {console.error("Next vertex is not found"); break;} if (current === chain[chain.length-1][0]) {ERROR && console.error("Next vertex is not found"); break;}
} }
chain.push([start, province, land]); // add starting vertex to sequence to close the path chain.push([start, province, land]); // add starting vertex to sequence to close the path
return chain; return chain;
} }
console.timeEnd("drawProvinces"); TIME && console.timeEnd("drawProvinces");
} }
function toggleGrid(event) { function toggleGrid(event) {
@ -959,7 +959,7 @@ function toggleGrid(event) {
} }
function drawGrid() { function drawGrid() {
console.time("drawGrid"); TIME && console.time("drawGrid");
gridOverlay.selectAll("*").remove(); gridOverlay.selectAll("*").remove();
const type = styleGridType.value; const type = styleGridType.value;
const size = Math.max(+styleGridSize.value, 2); const size = Math.max(+styleGridSize.value, 2);
@ -1003,7 +1003,7 @@ function drawGrid() {
}); });
} }
console.timeEnd("drawGrid"); TIME && console.timeEnd("drawGrid");
} }
function toggleCoordinates(event) { function toggleCoordinates(event) {

View file

@ -653,7 +653,7 @@ function setBase64Texture(url) {
}; };
function fetchTextureURL(url) { function fetchTextureURL(url) {
console.log("Provided URL is", url); INFO && console.log("Provided URL is", url);
const img = new Image(); const img = new Image();
img.onload = function () { img.onload = function () {
const canvas = document.getElementById("texturePreview"); const canvas = document.getElementById("texturePreview");

View file

@ -471,14 +471,14 @@ function lim(v) {
// get number from string in format "1-3" or "2" or "0.5" // get number from string in format "1-3" or "2" or "0.5"
function getNumberInRange(r) { function getNumberInRange(r) {
if (typeof r !== "string") {console.error("The value should be a string", r); return 0;} if (typeof r !== "string") {ERROR && console.error("The value should be a string", r); return 0;}
if (!isNaN(+r)) return ~~r + +P(r - ~~r); if (!isNaN(+r)) return ~~r + +P(r - ~~r);
const sign = r[0] === "-" ? -1 : 1; const sign = r[0] === "-" ? -1 : 1;
if (isNaN(+r[0])) r = r.slice(1); if (isNaN(+r[0])) r = r.slice(1);
const range = r.includes("-") ? r.split("-") : null; const range = r.includes("-") ? r.split("-") : null;
if (!range) {console.error("Cannot parse the number. Check the format", r); return 0;} if (!range) {ERROR && console.error("Cannot parse the number. Check the format", r); return 0;}
const count = rand(range[0] * sign, +range[1]); const count = rand(range[0] * sign, +range[1]);
if (isNaN(count) || count < 0) {console.error("Cannot parse number. Check the format", r); return 0;} if (isNaN(count) || count < 0) {ERROR && console.error("Cannot parse number. Check the format", r); return 0;}
return count; return count;
} }
@ -603,7 +603,7 @@ void function() {
const form = prompt.querySelector("#promptForm"); const form = prompt.querySelector("#promptForm");
window.prompt = function(promptText = "Please provide an input", options = {default:1, step:.01, min:0, max:100}, callback) { window.prompt = function(promptText = "Please provide an input", options = {default:1, step:.01, min:0, max:100}, callback) {
if (options.default === undefined) {console.error("Prompt: options object does not have default value defined"); return;} if (options.default === undefined) {ERROR && console.error("Prompt: options object does not have default value defined"); return;}
const input = prompt.querySelector("#promptInput"); const input = prompt.querySelector("#promptInput");
prompt.querySelector("#promptText").innerHTML = promptText; prompt.querySelector("#promptText").innerHTML = promptText;
const type = typeof(options.default) === "number" ? "number" : "text"; const type = typeof(options.default) === "number" ? "number" : "text";
@ -628,4 +628,4 @@ void function() {
}() }()
// indexedDB; ldb object // indexedDB; ldb object
!function(){function e(t,o){return n?void(n.transaction("s").objectStore("s").get(t).onsuccess=function(e){var t=e.target.result&&e.target.result.v||null;o(t)}):void setTimeout(function(){e(t,o)},100)}var t=window.indexedDB||window.mozIndexedDB||window.webkitIndexedDB||window.msIndexedDB;if(!t)return void console.error("indexedDB not supported");var n,o={k:"",v:""},r=t.open("d2",1);r.onsuccess=function(e){n=this.result},r.onerror=function(e){console.error("indexedDB request error"),console.log(e)},r.onupgradeneeded=function(e){n=null;var t=e.target.result.createObjectStore("s",{keyPath:"k"});t.transaction.oncomplete=function(e){n=e.target.db}},window.ldb={get:e,set:function(e,t){o.k=e,o.v=t,n.transaction("s","readwrite").objectStore("s").put(o)}}}(); !function(){function e(t,o){return n?void(n.transaction("s").objectStore("s").get(t).onsuccess=function(e){var t=e.target.result&&e.target.result.v||null;o(t)}):void setTimeout(function(){e(t,o)},100)}var t=window.indexedDB||window.mozIndexedDB||window.webkitIndexedDB||window.msIndexedDB;if(!t)return void ERROR && console.error("indexedDB not supported");var n,o={k:"",v:""},r=t.open("d2",1);r.onsuccess=function(e){n=this.result},r.onerror=function(e){ERROR && console.error("indexedDB request error"),INFO && console.log(e)},r.onupgradeneeded=function(e){n=null;var t=e.target.result.createObjectStore("s",{keyPath:"k"});t.transaction.oncomplete=function(e){n=e.target.db}},window.ldb={get:e,set:function(e,t){o.k=e,o.v=t,n.transaction("s","readwrite").objectStore("s").put(o)}}}();