mirror of
https://github.com/Azgaar/Fantasy-Map-Generator.git
synced 2025-12-17 09:41:24 +01:00
v1.22.27
This commit is contained in:
parent
07bc3dee33
commit
e3e2de9e9b
15 changed files with 255 additions and 32 deletions
22
index.css
22
index.css
|
|
@ -1178,13 +1178,6 @@ div.states>input {
|
||||||
border: 0;
|
border: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
div.states>input.stateColor {
|
|
||||||
width: .9em;
|
|
||||||
height: .9em;
|
|
||||||
padding: 0px;
|
|
||||||
margin-right: -1px;
|
|
||||||
}
|
|
||||||
|
|
||||||
div.states div {
|
div.states div {
|
||||||
width: 3.2em;
|
width: 3.2em;
|
||||||
}
|
}
|
||||||
|
|
@ -1425,10 +1418,21 @@ div.states > div.biomeArea {
|
||||||
width: 5em;
|
width: 5em;
|
||||||
}
|
}
|
||||||
|
|
||||||
.zoneFill {
|
rect.fillRect {
|
||||||
stroke: #666666;
|
stroke: #666666;
|
||||||
stroke-width: 2;
|
stroke-width: 2;
|
||||||
cursor: pointer;
|
}
|
||||||
|
|
||||||
|
#militaryBody div.states > div {
|
||||||
|
width: 4em;
|
||||||
|
}
|
||||||
|
|
||||||
|
#militaryBody div.states > input.militaryArmy {
|
||||||
|
width: 5em;
|
||||||
|
}
|
||||||
|
|
||||||
|
#militaryBody div.states > input.militaryFleet {
|
||||||
|
width: 3.3em;
|
||||||
}
|
}
|
||||||
|
|
||||||
#picker text {
|
#picker text {
|
||||||
|
|
|
||||||
29
index.html
29
index.html
|
|
@ -1544,7 +1544,7 @@
|
||||||
</td>
|
</td>
|
||||||
<td>
|
<td>
|
||||||
<i data-tip="Show seed history to apply a previous seed" id="optionsMapHistory" class="icon-history"></i>
|
<i data-tip="Show seed history to apply a previous seed" id="optionsMapHistory" class="icon-history"></i>
|
||||||
<i data-tip="Copy map seed as URL. It will produce the same map only if map was generated with default options" id="optionsCopySeed" class="icon-docs"></i>
|
<i data-tip="Copy map seed as URL. It will produce the same map only if options are default or the same" id="optionsCopySeed" class="icon-docs"></i>
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
|
|
||||||
|
|
@ -1807,6 +1807,7 @@
|
||||||
<p>Click to overview:</p>
|
<p>Click to overview:</p>
|
||||||
<button id="overviewBurgsButton" data-tip="Click to open Burgs Overview. Shortcut: Shift + T">Burgs</button>
|
<button id="overviewBurgsButton" data-tip="Click to open Burgs Overview. Shortcut: Shift + T">Burgs</button>
|
||||||
<button id="overviewRiversButton" data-tip="Click to open Rivers Overview. Shortcut: Shift + V">Rivers</button>
|
<button id="overviewRiversButton" data-tip="Click to open Rivers Overview. Shortcut: Shift + V">Rivers</button>
|
||||||
|
<!-- <button id="overviewMilitaryButton" data-tip="Click to open Military Forces Overview. Shortcut: Shift + M">Military</button> -->
|
||||||
<button id="overviewCellsButton" data-tip="Click to open Cell details view. Shortcut: Shift + E">Cells</button>
|
<button id="overviewCellsButton" data-tip="Click to open Cell details view. Shortcut: Shift + E">Cells</button>
|
||||||
<!-- <button id="overviewLandmassedButton" data-tip="Click to open Landmasses Overview. Shortcut: Shift + L">Landmasses</button> -->
|
<!-- <button id="overviewLandmassedButton" data-tip="Click to open Landmasses Overview. Shortcut: Shift + L">Landmasses</button> -->
|
||||||
<!-- <button id="overviewWaterbodiesButton" data-tip="Click to open Waterbodies Overview. Shortcut: Shift + W">Waterbodies</button> -->
|
<!-- <button id="overviewWaterbodiesButton" data-tip="Click to open Waterbodies Overview. Shortcut: Shift + W">Waterbodies</button> -->
|
||||||
|
|
@ -3211,6 +3212,31 @@
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div id="militaryOverview" class="dialog stable" style="display: none">
|
||||||
|
<div id="militaryHeader" class="header">
|
||||||
|
<div style="left:1.4em" data-tip="State name. Click to sort" class="sortable alphabetically" data-sortby="state">State </div>
|
||||||
|
<div style="left: 7.8em" data-tip="State infantry number. Click to sort" class="sortable" data-sortby="infantry">Infantry </div>
|
||||||
|
<div style="left: 13em" data-tip="State archers number. Click to sort" class="sortable" data-sortby="archers">Archers </div>
|
||||||
|
<div style="left: 18em" data-tip="State cavalry number. Click to sort" class="sortable" data-sortby="cavalry">Cavalry </div>
|
||||||
|
<div style="left: 23em" data-tip="Number of ships in navy. Click to sort" class="sortable" data-sortby="fleet">Fleet </div>
|
||||||
|
<div style="left: 27em" data-tip="Total military personnel (including ships crew). Click to sort" class="sortable icon-sort-number-down" data-sortby="total">Total </div>
|
||||||
|
<div style="left: 31.4em" data-tip="Military personnel rate (% of state population). Depends on diplomatic situation. Click to sort" class="sortable" data-sortby="rate">Rate </div>
|
||||||
|
<div style="left: 36em" data-tip="State manpower (reserve). Click to sort" class="sortable" data-sortby="reserve">Reserve </div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div id="militaryBody" class="table" data-type="absolute"></div>
|
||||||
|
|
||||||
|
<div id="militaryFooter" class="totalLine">
|
||||||
|
<div data-tip="States number" style="margin-left: 4px">States: <span id="militaryFooterStates">0</span></div>
|
||||||
|
<div data-tip="Average military per state" style="margin-left: 14px">Average military: <span id="militaryFooterAverage">0</span></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div id="militaryBottom">
|
||||||
|
<button id="militaryOverviewRefresh" data-tip="Refresh the Editor" class="icon-cw"></button>
|
||||||
|
<button id="militaryExport" data-tip="Save military-related data as a text file (.csv)" class="icon-download"></button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div id="styleSaver" class="dialog stable textual" style="display: none">
|
<div id="styleSaver" class="dialog stable textual" style="display: none">
|
||||||
<div id="styleSaverHeader" style="padding:2px 0">
|
<div id="styleSaverHeader" style="padding:2px 0">
|
||||||
<span>Preset name:</span>
|
<span>Preset name:</span>
|
||||||
|
|
@ -3415,6 +3441,7 @@
|
||||||
<script defer src="modules/ui/zones-editor.js"></script>
|
<script defer src="modules/ui/zones-editor.js"></script>
|
||||||
<script defer src="modules/ui/burgs-overview.js"></script>
|
<script defer src="modules/ui/burgs-overview.js"></script>
|
||||||
<script defer src="modules/ui/rivers-overview.js"></script>
|
<script defer src="modules/ui/rivers-overview.js"></script>
|
||||||
|
<!-- <script defer src="modules/ui/military-overview.js"></script> -->
|
||||||
<script defer src="modules/ui/editors.js"></script>
|
<script defer src="modules/ui/editors.js"></script>
|
||||||
<script defer src="modules/ui/3d.js"></script>
|
<script defer src="modules/ui/3d.js"></script>
|
||||||
<script defer src="libs/quantize.min.js"></script>
|
<script defer src="libs/quantize.min.js"></script>
|
||||||
|
|
|
||||||
78
main.js
78
main.js
|
|
@ -516,6 +516,7 @@ function generate() {
|
||||||
BurgsAndStates.drawStateLabels();
|
BurgsAndStates.drawStateLabels();
|
||||||
|
|
||||||
Rivers.specify();
|
Rivers.specify();
|
||||||
|
//calculateMilitaryForces();
|
||||||
addMarkers();
|
addMarkers();
|
||||||
addZones();
|
addZones();
|
||||||
Names.getMapName();
|
Names.getMapName();
|
||||||
|
|
@ -1162,6 +1163,83 @@ function rankCells() {
|
||||||
console.timeEnd('rankCells');
|
console.timeEnd('rankCells');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// calculate army and fleet based on state cells polulation
|
||||||
|
function calculateMilitaryForces() {
|
||||||
|
const cells = pack.cells, states = pack.states;
|
||||||
|
const valid = states.filter(s => s.i && !s.removed); // valid states
|
||||||
|
valid.forEach(s => s.military = {infantry:0, cavalry:0, archers:0, reserve:0, fleet:0});
|
||||||
|
|
||||||
|
for (const i of cells.i) {
|
||||||
|
const s = states[cells.state[i]]; // cell state
|
||||||
|
if (!s.i || s.removed) continue;
|
||||||
|
|
||||||
|
let m = cells.pop[i] / 100; // basic army is 1% of rural population
|
||||||
|
if (cells.culture[i] !== s.culture) m = s.form === "Union" ? m / 1.2 : m / 2; // non-dominant culture
|
||||||
|
if (cells.religion[i] !== cells.religion[s.center]) m = s.form === "Theocracy" ? m / 2.2 : m / 1.4; // non-dominant religion
|
||||||
|
if (cells.f[i] !== cells.f[s.center]) m = s.type === "Naval" ? m / 1.2 : m / 1.8; // different landmass
|
||||||
|
|
||||||
|
let infantry = m * .5; // basic infantry is 50% of army
|
||||||
|
let archers = m * .25; // basic archers is 25% of army
|
||||||
|
let cavalry = m * .25; // basic cavalry is 25% of army
|
||||||
|
|
||||||
|
if ([1, 2, 3, 4].includes(cells.biome[i])) {cavalry *= 3; infantry /= 5; archers /= 2;} else // "nomadic" biomes have lots of cavalry
|
||||||
|
if ([7, 8, 9, 12].includes(cells.biome[i])) {cavalry /= 2.5; infantry *= 1.2; archers *= 1.2;} // "wet" biomes have reduced number of cavalry
|
||||||
|
|
||||||
|
s.military.infantry += infantry;
|
||||||
|
s.military.archers += archers;
|
||||||
|
s.military.cavalry += cavalry;
|
||||||
|
s.military.reserve += m * 3 + cells.pop[i] * .02; // reserve is ~5% of population
|
||||||
|
}
|
||||||
|
|
||||||
|
for (const b of pack.burgs) {
|
||||||
|
if (!b.i || b.removed || !b.state) continue;
|
||||||
|
const s = states[b.state]; // burg state
|
||||||
|
|
||||||
|
let m = b.population / 50; // basic army is 2% of urban population
|
||||||
|
if (b.capital) m *= 2; // capital has household troops
|
||||||
|
if (b.culture !== s.culture) m = s.form === "Union" ? m / 1.2 : m / 2; // non-dominant culture
|
||||||
|
if (cells.religion[b.cell] !== cells.religion[s.center]) m = s.form === "Theocracy" ? m / 2.2 : m / 1.4; // non-dominant religion
|
||||||
|
if (cells.f[b.cell] !== cells.f[s.center]) m = s.type === "Naval" ? m / 1.2 : m / 1.8; // different landmass
|
||||||
|
|
||||||
|
let infantry = m * .6; // basic infantry is 60% of army
|
||||||
|
let archers = m * .3; // basic archers is 3% of army
|
||||||
|
let cavalry = m * .1; // basic cavalry is 10% of army
|
||||||
|
|
||||||
|
const biome = cells.biome[b.cell]; // burg biome
|
||||||
|
if ([1, 2, 3, 4].includes(biome)) {cavalry *= 3; infantry /= 2;} else // "nomadic" biomes have lots of cavalry
|
||||||
|
if ([7, 8, 9, 12].includes(biome)) {cavalry /= 4; infantry *= 1.2; archers *= 1.4;} // "wet" biomes have reduced number of cavalry
|
||||||
|
|
||||||
|
s.military.infantry += infantry;
|
||||||
|
s.military.archers += archers;
|
||||||
|
s.military.cavalry += cavalry;
|
||||||
|
s.military.reserve += m * 2 + b.population * .01; // reserve is ~5% of population
|
||||||
|
|
||||||
|
if (!b.port) continue; // only ports have fleet
|
||||||
|
let ships = b.capital ? b.population / 3 : b.population / 5; // ~1 ship per 5 population points
|
||||||
|
if (s.type === "Naval") ships *= 1.8; // "naval" states have more ships
|
||||||
|
s.military.fleet += ~~ships + +P(ships % 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
const expn = d3.sum(valid.map(s => s.expansionism)); // total expansion
|
||||||
|
const area = d3.sum(valid.map(s => s.area)); // total area
|
||||||
|
const rate = {x:0, Ally:-.2, Friendly:-.1, Neutral:0, Suspicion:.1, Enemy:1, Unknown:0, Rival:.5, Vassal:.5, Suzerain:-.5};
|
||||||
|
|
||||||
|
valid.forEach(s => {
|
||||||
|
const m = s.military, d = s.diplomacy;
|
||||||
|
const expansionRate = Math.min(Math.max((s.expansionism / expn) / (s.area / area), .25), 4); // how much state expansionism is relized
|
||||||
|
const diplomacyRate = d.some(d => d === "Enemy") ? 1 : d.some(d => d === "Rival") ? .8 : d.some(d => d === "Suspicion") ? .5 : .1; // peacefulness
|
||||||
|
const neighborsRate = Math.min(Math.max(s.neighbors.map(n => n ? pack.states[n].diplomacy[s.i] : "Suspicion").reduce((s, r) => s += rate[r], .5), .3), 3); // neighbors rate
|
||||||
|
m.alert = rn(expansionRate * diplomacyRate * neighborsRate, 2); // war alert rate (army modifier)
|
||||||
|
|
||||||
|
m.infantry = rn(m.infantry * m.alert, 3);
|
||||||
|
m.cavalry = rn(m.cavalry * m.alert, 3);
|
||||||
|
m.archers = rn(m.archers * m.alert, 3);
|
||||||
|
m.reserve = rn(m.reserve, 3);
|
||||||
|
});
|
||||||
|
|
||||||
|
console.table(valid.map(s=>[s.name, s.military.alert, s.military.infantry, s.military.archers, s.military.cavalry, s.military.reserve, rn(s.military.reserve/(s.urban+s.rural)*100,2)+"%", s.military.fleet]));
|
||||||
|
}
|
||||||
|
|
||||||
// generate some markers
|
// generate some markers
|
||||||
function addMarkers(number = 1) {
|
function addMarkers(number = 1) {
|
||||||
if (!number) return;
|
if (!number) return;
|
||||||
|
|
|
||||||
|
|
@ -35,7 +35,7 @@ function editBiomes() {
|
||||||
|
|
||||||
body.addEventListener("click", function(ev) {
|
body.addEventListener("click", function(ev) {
|
||||||
const el = ev.target, cl = el.classList;
|
const el = ev.target, cl = el.classList;
|
||||||
if (cl.contains("zoneFill")) biomeChangeColor(el); else
|
if (cl.contains("fillRect")) biomeChangeColor(el); else
|
||||||
if (cl.contains("icon-info-circled")) openWiki(el); else
|
if (cl.contains("icon-info-circled")) openWiki(el); else
|
||||||
if (cl.contains("icon-trash-empty")) removeCustomBiome(el);
|
if (cl.contains("icon-trash-empty")) removeCustomBiome(el);
|
||||||
if (customization === 6) selectBiomeOnLineClick(el);
|
if (customization === 6) selectBiomeOnLineClick(el);
|
||||||
|
|
@ -87,7 +87,7 @@ function editBiomes() {
|
||||||
|
|
||||||
lines += `<div class="states biomes" data-id="${i}" data-name="${b.name[i]}" data-habitability="${b.habitability[i]}"
|
lines += `<div class="states biomes" data-id="${i}" data-name="${b.name[i]}" data-habitability="${b.habitability[i]}"
|
||||||
data-cells=${b.cells[i]} data-area=${area} data-population=${population} data-color=${b.color[i]}>
|
data-cells=${b.cells[i]} data-area=${area} data-population=${population} data-color=${b.color[i]}>
|
||||||
<svg data-tip="Biomes fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${b.color[i]}" class="zoneFill"></svg>
|
<svg data-tip="Biomes fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${b.color[i]}" class="fillRect pointer"></svg>
|
||||||
<input data-tip="Biome name. Click and type to change" class="biomeName" value="${b.name[i]}" autocorrect="off" spellcheck="false">
|
<input data-tip="Biome name. Click and type to change" class="biomeName" value="${b.name[i]}" autocorrect="off" spellcheck="false">
|
||||||
<span data-tip="Biome habitability percent" class="hide">%</span>
|
<span data-tip="Biome habitability percent" class="hide">%</span>
|
||||||
<input data-tip="Biome habitability percent. Click and set new value to change" type="number" min=0 max=9999 class="biomeHabitability hide" value=${b.habitability[i]}>
|
<input data-tip="Biome habitability percent. Click and set new value to change" type="number" min=0 max=9999 class="biomeHabitability hide" value=${b.habitability[i]}>
|
||||||
|
|
@ -230,7 +230,7 @@ function editBiomes() {
|
||||||
|
|
||||||
const unit = areaUnit.value === "square" ? " " + distanceUnitInput.value + "²" : " " + areaUnit.value;
|
const unit = areaUnit.value === "square" ? " " + distanceUnitInput.value + "²" : " " + areaUnit.value;
|
||||||
const line = `<div class="states biomes" data-id="${i}" data-name="${b.name[i]}" data-habitability=${b.habitability[i]} data-cells=0 data-area=0 data-population=0 data-color=${b.color[i]}>
|
const line = `<div class="states biomes" data-id="${i}" data-name="${b.name[i]}" data-habitability=${b.habitability[i]} data-cells=0 data-area=0 data-population=0 data-color=${b.color[i]}>
|
||||||
<svg data-tip="Biomes fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${b.color[i]}" class="zoneFill"></svg>
|
<svg data-tip="Biomes fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${b.color[i]}" class="fillRect pointer"></svg>
|
||||||
<input data-tip="Biome name. Click and type to change" class="biomeName" value="${b.name[i]}" autocorrect="off" spellcheck="false">
|
<input data-tip="Biome name. Click and type to change" class="biomeName" value="${b.name[i]}" autocorrect="off" spellcheck="false">
|
||||||
<span data-tip="Biome habitability percent" class="hide">%</span>
|
<span data-tip="Biome habitability percent" class="hide">%</span>
|
||||||
<input data-tip="Biome habitability percent. Click and set new value to change" type="number" min=0 max=9999 step=1 class="biomeHabitability hide" value=${b.habitability[i]}>
|
<input data-tip="Biome habitability percent. Click and set new value to change" type="number" min=0 max=9999 step=1 class="biomeHabitability hide" value=${b.habitability[i]}>
|
||||||
|
|
|
||||||
|
|
@ -92,7 +92,7 @@ function editCultures() {
|
||||||
|
|
||||||
lines += `<div class="states cultures" data-id=${c.i} data-name="${c.name}" data-color="${c.color}" data-cells=${c.cells}
|
lines += `<div class="states cultures" data-id=${c.i} data-name="${c.name}" data-color="${c.color}" data-cells=${c.cells}
|
||||||
data-area=${area} data-population=${population} data-base=${c.base} data-type=${c.type} data-expansionism=${c.expansionism}>
|
data-area=${area} data-population=${population} data-base=${c.base} data-type=${c.type} data-expansionism=${c.expansionism}>
|
||||||
<svg data-tip="Culture fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${c.color}" class="zoneFill"></svg>
|
<svg data-tip="Culture fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${c.color}" class="fillRect pointer"></svg>
|
||||||
<input data-tip="Culture name. Click and type to change" class="cultureName" value="${c.name}" autocorrect="off" spellcheck="false">
|
<input data-tip="Culture name. Click and type to change" class="cultureName" value="${c.name}" autocorrect="off" spellcheck="false">
|
||||||
<span data-tip="Cells count" class="icon-check-empty hide"></span>
|
<span data-tip="Cells count" class="icon-check-empty hide"></span>
|
||||||
<div data-tip="Cells count" class="stateCells hide">${c.cells}</div>
|
<div data-tip="Cells count" class="stateCells hide">${c.cells}</div>
|
||||||
|
|
@ -122,7 +122,7 @@ function editCultures() {
|
||||||
body.querySelectorAll("div.cultures").forEach(el => el.addEventListener("mouseenter", ev => cultureHighlightOn(ev)));
|
body.querySelectorAll("div.cultures").forEach(el => el.addEventListener("mouseenter", ev => cultureHighlightOn(ev)));
|
||||||
body.querySelectorAll("div.cultures").forEach(el => el.addEventListener("mouseleave", ev => cultureHighlightOff(ev)));
|
body.querySelectorAll("div.cultures").forEach(el => el.addEventListener("mouseleave", ev => cultureHighlightOff(ev)));
|
||||||
body.querySelectorAll("div.states").forEach(el => el.addEventListener("click", selectCultureOnLineClick));
|
body.querySelectorAll("div.states").forEach(el => el.addEventListener("click", selectCultureOnLineClick));
|
||||||
body.querySelectorAll("rect.zoneFill").forEach(el => el.addEventListener("click", cultureChangeColor));
|
body.querySelectorAll("rect.fillRect").forEach(el => el.addEventListener("click", cultureChangeColor));
|
||||||
body.querySelectorAll("div > input.cultureName").forEach(el => el.addEventListener("input", cultureChangeName));
|
body.querySelectorAll("div > input.cultureName").forEach(el => el.addEventListener("input", cultureChangeName));
|
||||||
body.querySelectorAll("div > input.statePower").forEach(el => el.addEventListener("input", cultureChangeExpansionism));
|
body.querySelectorAll("div > input.statePower").forEach(el => el.addEventListener("input", cultureChangeExpansionism));
|
||||||
body.querySelectorAll("div > select.cultureType").forEach(el => el.addEventListener("change", cultureChangeType));
|
body.querySelectorAll("div > select.cultureType").forEach(el => el.addEventListener("change", cultureChangeType));
|
||||||
|
|
|
||||||
|
|
@ -70,7 +70,7 @@ function editDiplomacy() {
|
||||||
lines += `<div class="states" data-id=${s.i} data-name="${s.fullName}" data-relations="${relation}">
|
lines += `<div class="states" data-id=${s.i} data-name="${s.fullName}" data-relations="${relation}">
|
||||||
<div data-tip="${tipSelect}" style="width:12em">${s.fullName}</div>
|
<div data-tip="${tipSelect}" style="width:12em">${s.fullName}</div>
|
||||||
<svg data-tip="${tipChange}" width=".9em" height=".9em" style="margin-bottom:-1px" class="changeRelations">
|
<svg data-tip="${tipChange}" width=".9em" height=".9em" style="margin-bottom:-1px" class="changeRelations">
|
||||||
<rect x="0" y="0" width="100%" height="100%" fill="${color}" class="zoneFill" style="pointer-events: none"></rect>
|
<rect x="0" y="0" width="100%" height="100%" fill="${color}" class="fillRect pointer" style="pointer-events: none"></rect>
|
||||||
</svg>
|
</svg>
|
||||||
<input data-tip="${tipChange}" class="changeRelations diplomacyRelations" value="${relation}" readonly/>
|
<input data-tip="${tipChange}" class="changeRelations diplomacyRelations" value="${relation}" readonly/>
|
||||||
</div>`;
|
</div>`;
|
||||||
|
|
|
||||||
|
|
@ -341,6 +341,7 @@ document.addEventListener("keyup", event => {
|
||||||
else if (shift && key === 79) editNotes(); // Shift + "O" to edit Notes
|
else if (shift && key === 79) editNotes(); // Shift + "O" to edit Notes
|
||||||
else if (shift && key === 84) overviewBurgs(); // Shift + "T" to open Burgs overview
|
else if (shift && key === 84) overviewBurgs(); // Shift + "T" to open Burgs overview
|
||||||
else if (shift && key === 86) overviewRivers(); // Shift + "V" to open Rivers overview
|
else if (shift && key === 86) overviewRivers(); // Shift + "V" to open Rivers overview
|
||||||
|
//else if (shift && key === 77) overviewMilitary(); // Shift + "M" to open Military overview
|
||||||
else if (shift && key === 69) viewCellDetails(); // Shift + "E" to open Cell Details
|
else if (shift && key === 69) viewCellDetails(); // Shift + "E" to open Cell Details
|
||||||
|
|
||||||
else if (shift && key === 49) toggleAddBurg(); // Shift + "1" to click to add Burg
|
else if (shift && key === 49) toggleAddBurg(); // Shift + "1" to click to add Burg
|
||||||
|
|
|
||||||
111
modules/ui/military-overview.js
Normal file
111
modules/ui/military-overview.js
Normal file
|
|
@ -0,0 +1,111 @@
|
||||||
|
"use strict";
|
||||||
|
function overviewMilitary() {
|
||||||
|
if (customization) return;
|
||||||
|
closeDialogs("#militaryOverview, .stable");
|
||||||
|
if (!layerIsOn("toggleStates")) toggleStates();
|
||||||
|
if (!layerIsOn("toggleBorders")) toggleBorders();
|
||||||
|
|
||||||
|
const body = document.getElementById("militaryBody");
|
||||||
|
militaryOverviewAddLines();
|
||||||
|
$("#militaryOverview").dialog();
|
||||||
|
|
||||||
|
if (modules.overviewMilitary) return;
|
||||||
|
modules.overviewMilitary = true;
|
||||||
|
|
||||||
|
$("#militaryOverview").dialog({
|
||||||
|
title: "Military Overview", resizable: false, width: fitContent(),
|
||||||
|
position: {my: "right top", at: "right-10 top+10", of: "svg", collision: "fit"}
|
||||||
|
});
|
||||||
|
|
||||||
|
// add listeners
|
||||||
|
document.getElementById("militaryOverviewRefresh").addEventListener("click", militaryOverviewAddLines);
|
||||||
|
document.getElementById("militaryExport").addEventListener("click", downloadMilitaryData);
|
||||||
|
|
||||||
|
// add line for each river
|
||||||
|
function militaryOverviewAddLines() {
|
||||||
|
body.innerHTML = "";
|
||||||
|
let lines = "", militaryTotal = 0;
|
||||||
|
|
||||||
|
const states = pack.states.filter(s => s.i && !s.removed);
|
||||||
|
const popRate = +populationRate.value;
|
||||||
|
|
||||||
|
for (const s of states) {
|
||||||
|
const total = (s.military.infantry + s.military.cavalry + s.military.archers + s.military.fleet / 10);
|
||||||
|
const rate = total / (s.rural + s.urban * urbanization.value) * 100;
|
||||||
|
militaryTotal += total;
|
||||||
|
|
||||||
|
lines += `<div class="states" data-id=${s.i} data-state="${s.name}" data-infantry="${s.military.infantry}"
|
||||||
|
data-archers="${s.military.archers}" data-cavalry="${s.military.cavalry}" data-reserve="${s.military.reserve}"
|
||||||
|
data-fleet="${s.military.fleet}" data-rate="${rate}" data-total="${total}">
|
||||||
|
<svg data-tip="State color" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${s.color}" class="fillRect"></svg>
|
||||||
|
<input data-tip="State name" class="stateName" value="${s.name}" readonly>
|
||||||
|
|
||||||
|
<input data-tip="State infantry number" type="number" class="militaryArmy" min=0 step=1 value="${rn(s.military.infantry * popRate)}">
|
||||||
|
<input data-tip="State archers number" type="number" class="militaryArmy" min=0 step=1 value="${rn(s.military.archers * popRate)}">
|
||||||
|
<input data-tip="State cavalry number" type="number" class="militaryArmy" min=0 step=1 value="${rn(s.military.cavalry * popRate)}">
|
||||||
|
<input data-tip="Number of ships in state navy" class="militaryFleet" type="number" min=0 step=1 value="${s.military.fleet}">
|
||||||
|
|
||||||
|
<div data-tip="Total military personnel (including ships crew)">${si(total * popRate)}</div>
|
||||||
|
<div data-tip="Armed forces personnel (% of state population). Depends on diplomatic situation">${rn(rate, 2)}%</div>
|
||||||
|
<div data-tip="State manpower (reserve)">${si(s.military.reserve * popRate)}</div>
|
||||||
|
</div>`;
|
||||||
|
}
|
||||||
|
body.insertAdjacentHTML("beforeend", lines);
|
||||||
|
|
||||||
|
// update footer
|
||||||
|
militaryFooterStates.innerHTML = states.length;
|
||||||
|
militaryFooterAverage.innerHTML = si(militaryTotal / states.length * popRate);
|
||||||
|
|
||||||
|
// add listeners
|
||||||
|
body.querySelectorAll("div.states").forEach(el => el.addEventListener("mouseenter", ev => stateHighlightOn(ev)));
|
||||||
|
body.querySelectorAll("div.states").forEach(el => el.addEventListener("mouseleave", ev => stateHighlightOff(ev)));
|
||||||
|
applySorting(militaryHeader);
|
||||||
|
}
|
||||||
|
|
||||||
|
function stateHighlightOn(event) {
|
||||||
|
if (!layerIsOn("toggleStates")) return;
|
||||||
|
const state = +event.target.dataset.id;
|
||||||
|
if (customization || !state) return;
|
||||||
|
const path = regions.select("#state"+state).attr("d");
|
||||||
|
debug.append("path").attr("class", "highlight").attr("d", path)
|
||||||
|
.attr("fill", "none").attr("stroke", "red").attr("stroke-width", 1).attr("opacity", 1)
|
||||||
|
.attr("filter", "url(#blur1)").call(transition);
|
||||||
|
}
|
||||||
|
|
||||||
|
function transition(path) {
|
||||||
|
const duration = (path.node().getTotalLength() + 5000) / 2;
|
||||||
|
path.transition().duration(duration).attrTween("stroke-dasharray", tweenDash);
|
||||||
|
}
|
||||||
|
|
||||||
|
function tweenDash() {
|
||||||
|
const l = this.getTotalLength();
|
||||||
|
const i = d3.interpolateString("0," + l, l + "," + l);
|
||||||
|
return t => i(t);
|
||||||
|
}
|
||||||
|
|
||||||
|
function removePath(path) {
|
||||||
|
path.transition().duration(1000).attr("opacity", 0).remove();
|
||||||
|
}
|
||||||
|
|
||||||
|
function stateHighlightOff() {
|
||||||
|
debug.selectAll(".highlight").each(function(el) {
|
||||||
|
d3.select(this).call(removePath);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function downloadMilitaryData() {
|
||||||
|
let data = "Id,River,Type,Length,Basin\n"; // headers
|
||||||
|
|
||||||
|
body.querySelectorAll(":scope > div").forEach(function(el) {
|
||||||
|
data += el.dataset.id + ",";
|
||||||
|
data += el.dataset.name + ",";
|
||||||
|
data += el.dataset.type + ",";
|
||||||
|
data += el.querySelector(".biomeArea").innerHTML + ",";
|
||||||
|
data += el.dataset.basin + "\n";
|
||||||
|
});
|
||||||
|
|
||||||
|
const name = getFileName("Military") + ".csv";
|
||||||
|
downloadFile(data, name);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -219,11 +219,12 @@ function restoreDefaultZoomExtent() {
|
||||||
}
|
}
|
||||||
|
|
||||||
function copyMapURL() {
|
function copyMapURL() {
|
||||||
const search = `?seed=${optionsSeed.value}&width=${graphWidth}&height=${graphHeight}`;
|
const locked = document.querySelectorAll("i.icon-lock").length; // check if some options are locked
|
||||||
|
const search = `?seed=${optionsSeed.value}&width=${graphWidth}&height=${graphHeight}${locked?'':'&options=default'}`;
|
||||||
navigator.clipboard.writeText("https://azgaar.github.io/Fantasy-Map-Generator/"+search)
|
navigator.clipboard.writeText("https://azgaar.github.io/Fantasy-Map-Generator/"+search)
|
||||||
.then(() => {
|
.then(() => {
|
||||||
tip("Map URL is copied to clipboard", false, "success", 3000);
|
tip("Map URL is copied to clipboard", false, "success", 3000);
|
||||||
window.history.pushState({}, null, search);
|
//window.history.pushState({}, null, search);
|
||||||
})
|
})
|
||||||
.catch(err => tip("Could not copy URL: "+err, false, "error", 5000));
|
.catch(err => tip("Could not copy URL: "+err, false, "error", 5000));
|
||||||
}
|
}
|
||||||
|
|
@ -323,12 +324,13 @@ function applyStoredOptions() {
|
||||||
const height = +params.get("height");
|
const height = +params.get("height");
|
||||||
if (width) mapWidthInput.value = width;
|
if (width) mapWidthInput.value = width;
|
||||||
if (height) mapHeightInput.value = height;
|
if (height) mapHeightInput.value = height;
|
||||||
|
//window.history.pushState({}, null, "?");
|
||||||
}
|
}
|
||||||
|
|
||||||
// randomize options if randomization is allowed (not locked or default=1)
|
// randomize options if randomization is allowed (not locked or options='default')
|
||||||
function randomizeOptions() {
|
function randomizeOptions() {
|
||||||
Math.seedrandom(seed); // reset seed to initial one
|
Math.seedrandom(seed); // reset seed to initial one
|
||||||
const randomize = new URL(window.location.href).searchParams.get("seed"); // ignore stored options if seed is provided
|
const randomize = new URL(window.location.href).searchParams.get("options") === "default"; // ignore stored options
|
||||||
|
|
||||||
// 'Options' settings
|
// 'Options' settings
|
||||||
if (randomize || !locked("template")) randomizeHeightmapTemplate();
|
if (randomize || !locked("template")) randomizeHeightmapTemplate();
|
||||||
|
|
|
||||||
|
|
@ -35,7 +35,7 @@ function editProvinces() {
|
||||||
body.addEventListener("click", function(ev) {
|
body.addEventListener("click", function(ev) {
|
||||||
if (customization) return;
|
if (customization) return;
|
||||||
const el = ev.target, cl = el.classList, line = el.parentNode, p = +line.dataset.id;
|
const el = ev.target, cl = el.classList, line = el.parentNode, p = +line.dataset.id;
|
||||||
if (cl.contains("zoneFill")) changeFill(el); else
|
if (cl.contains("fillRect")) changeFill(el); else
|
||||||
if (cl.contains("name")) editProvinceName(p); else
|
if (cl.contains("name")) editProvinceName(p); else
|
||||||
if (cl.contains("icon-fleur")) provinceOpenCOA(ev, p); else
|
if (cl.contains("icon-fleur")) provinceOpenCOA(ev, p); else
|
||||||
if (cl.contains("icon-star-empty")) capitalZoomIn(p); else
|
if (cl.contains("icon-star-empty")) capitalZoomIn(p); else
|
||||||
|
|
@ -114,7 +114,7 @@ function editProvinces() {
|
||||||
const separable = p.burg && p.burg !== pack.states[p.state].capital;
|
const separable = p.burg && p.burg !== pack.states[p.state].capital;
|
||||||
const focused = defs.select("#fog #focusProvince"+p.i).size();
|
const focused = defs.select("#fog #focusProvince"+p.i).size();
|
||||||
lines += `<div class="states" data-id=${p.i} data-name=${p.name} data-form=${p.formName} data-color="${p.color}" data-capital="${capital}" data-state="${stateName}" data-area=${area} data-population=${population}>
|
lines += `<div class="states" data-id=${p.i} data-name=${p.name} data-form=${p.formName} data-color="${p.color}" data-capital="${capital}" data-state="${stateName}" data-area=${area} data-population=${population}>
|
||||||
<svg data-tip="Province fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${p.color}" class="zoneFill"></svg>
|
<svg data-tip="Province fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${p.color}" class="fillRect pointer"></svg>
|
||||||
<input data-tip="Province name. Click to change" class="name pointer" value="${p.name}" readonly>
|
<input data-tip="Province name. Click to change" class="name pointer" value="${p.name}" readonly>
|
||||||
<span data-tip="Click to open province COA in the Iron Arachne Heraldry Generator. Ctrl + click to change the seed" class="icon-fleur pointer hide"></span>
|
<span data-tip="Click to open province COA in the Iron Arachne Heraldry Generator. Ctrl + click to change the seed" class="icon-fleur pointer hide"></span>
|
||||||
<input data-tip="Province form name. Click to change" class="name pointer hide" value="${p.formName}" readonly>
|
<input data-tip="Province form name. Click to change" class="name pointer hide" value="${p.formName}" readonly>
|
||||||
|
|
|
||||||
|
|
@ -73,7 +73,7 @@ function editReligions() {
|
||||||
if (r.i) {
|
if (r.i) {
|
||||||
lines += `<div class="states religions" data-id=${r.i} data-name="${r.name}" data-color="${r.color}" data-area=${area}
|
lines += `<div class="states religions" data-id=${r.i} data-name="${r.name}" data-color="${r.color}" data-area=${area}
|
||||||
data-population=${population} data-type=${r.type} data-form=${r.form} data-deity="${r.deity?r.deity:''}" data-expansionism=${r.expansionism}>
|
data-population=${population} data-type=${r.type} data-form=${r.form} data-deity="${r.deity?r.deity:''}" data-expansionism=${r.expansionism}>
|
||||||
<svg data-tip="Religion fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${r.color}" class="zoneFill"></svg>
|
<svg data-tip="Religion fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${r.color}" class="fillRect pointer"></svg>
|
||||||
<input data-tip="Religion name. Click and type to change" class="religionName" value="${r.name}" autocorrect="off" spellcheck="false">
|
<input data-tip="Religion name. Click and type to change" class="religionName" value="${r.name}" autocorrect="off" spellcheck="false">
|
||||||
<select data-tip="Religion type" class="religionType">${getTypeOptions(r.type)}</select>
|
<select data-tip="Religion type" class="religionType">${getTypeOptions(r.type)}</select>
|
||||||
<input data-tip="Religion form" class="religionForm hide" value="${r.form}" autocorrect="off" spellcheck="false">
|
<input data-tip="Religion form" class="religionForm hide" value="${r.form}" autocorrect="off" spellcheck="false">
|
||||||
|
|
@ -118,7 +118,7 @@ function editReligions() {
|
||||||
body.querySelectorAll("div.religions").forEach(el => el.addEventListener("mouseenter", ev => religionHighlightOn(ev)));
|
body.querySelectorAll("div.religions").forEach(el => el.addEventListener("mouseenter", ev => religionHighlightOn(ev)));
|
||||||
body.querySelectorAll("div.religions").forEach(el => el.addEventListener("mouseleave", ev => religionHighlightOff(ev)));
|
body.querySelectorAll("div.religions").forEach(el => el.addEventListener("mouseleave", ev => religionHighlightOff(ev)));
|
||||||
body.querySelectorAll("div.states").forEach(el => el.addEventListener("click", selectReligionOnLineClick));
|
body.querySelectorAll("div.states").forEach(el => el.addEventListener("click", selectReligionOnLineClick));
|
||||||
body.querySelectorAll("rect.zoneFill").forEach(el => el.addEventListener("click", religionChangeColor));
|
body.querySelectorAll("rect.fillRect").forEach(el => el.addEventListener("click", religionChangeColor));
|
||||||
body.querySelectorAll("div > input.religionName").forEach(el => el.addEventListener("input", religionChangeName));
|
body.querySelectorAll("div > input.religionName").forEach(el => el.addEventListener("input", religionChangeName));
|
||||||
body.querySelectorAll("div > select.religionType").forEach(el => el.addEventListener("change", religionChangeType));
|
body.querySelectorAll("div > select.religionType").forEach(el => el.addEventListener("change", religionChangeType));
|
||||||
body.querySelectorAll("div > input.religionForm").forEach(el => el.addEventListener("input", religionChangeForm));
|
body.querySelectorAll("div > input.religionForm").forEach(el => el.addEventListener("input", religionChangeForm));
|
||||||
|
|
|
||||||
|
|
@ -40,7 +40,7 @@ function editStates() {
|
||||||
|
|
||||||
body.addEventListener("click", function(ev) {
|
body.addEventListener("click", function(ev) {
|
||||||
const el = ev.target, cl = el.classList, line = el.parentNode, state = +line.dataset.id;
|
const el = ev.target, cl = el.classList, line = el.parentNode, state = +line.dataset.id;
|
||||||
if (cl.contains("zoneFill")) stateChangeFill(el); else
|
if (cl.contains("fillRect")) stateChangeFill(el); else
|
||||||
if (cl.contains("name")) editStateName(state); else
|
if (cl.contains("name")) editStateName(state); else
|
||||||
if (cl.contains("icon-fleur")) stateOpenCOA(ev, state); else
|
if (cl.contains("icon-fleur")) stateOpenCOA(ev, state); else
|
||||||
if (cl.contains("icon-star-empty")) stateCapitalZoomIn(state); else
|
if (cl.contains("icon-star-empty")) stateCapitalZoomIn(state); else
|
||||||
|
|
@ -112,9 +112,9 @@ function editStates() {
|
||||||
const capital = pack.burgs[s.capital].name;
|
const capital = pack.burgs[s.capital].name;
|
||||||
lines += `<div class="states" data-id=${s.i} data-name="${s.name}" data-form="${s.formName}" data-capital="${capital}" data-color="${s.color}" data-cells=${s.cells}
|
lines += `<div class="states" data-id=${s.i} data-name="${s.name}" data-form="${s.formName}" data-capital="${capital}" data-color="${s.color}" data-cells=${s.cells}
|
||||||
data-area=${area} data-population=${population} data-burgs=${s.burgs} data-culture=${pack.cultures[s.culture].name} data-type=${s.type} data-expansionism=${s.expansionism}>
|
data-area=${area} data-population=${population} data-burgs=${s.burgs} data-culture=${pack.cultures[s.culture].name} data-type=${s.type} data-expansionism=${s.expansionism}>
|
||||||
<svg data-tip="State fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${s.color}" class="zoneFill"></svg>
|
<svg data-tip="State fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${s.color}" class="fillRect pointer"></svg>
|
||||||
<input data-tip="State name. Click to change" class="stateName name pointer" value="${s.name}" readonly>
|
<input data-tip="State name. Click to change" class="stateName name pointer" value="${s.name}" readonly>
|
||||||
<span data-tip="Click to open state COA in the Iron Arachne Heraldry Generator. Ctrl + click to change the seed" class="icon-fleur pointer hide"></span>
|
<span data-tip="Click to open state COA in the Iron Arachne Heraldry Generator. Ctrl + click to change the seed" class="icon-fleur pointer hide"></span>
|
||||||
<input data-tip="State form name. Click to change" class="stateForm name pointer" value="${s.formName}" readonly>
|
<input data-tip="State form name. Click to change" class="stateForm name pointer" value="${s.formName}" readonly>
|
||||||
<span data-tip="State capital. Click to zoom into view" class="icon-star-empty pointer hide"></span>
|
<span data-tip="State capital. Click to zoom into view" class="icon-star-empty pointer hide"></span>
|
||||||
<input data-tip="Capital name. Click and type to rename" class="stateCapital hide" value="${capital}" autocorrect="off" spellcheck="false"/>
|
<input data-tip="Capital name. Click and type to rename" class="stateCapital hide" value="${capital}" autocorrect="off" spellcheck="false"/>
|
||||||
|
|
|
||||||
|
|
@ -20,6 +20,7 @@ toolsContent.addEventListener("click", function(event) {
|
||||||
if (button === "editZonesButton") editZones(); else
|
if (button === "editZonesButton") editZones(); else
|
||||||
if (button === "overviewBurgsButton") overviewBurgs(); else
|
if (button === "overviewBurgsButton") overviewBurgs(); else
|
||||||
if (button === "overviewRiversButton") overviewRivers(); else
|
if (button === "overviewRiversButton") overviewRivers(); else
|
||||||
|
if (button === "overviewMilitaryButton") overviewMilitary(); else
|
||||||
if (button === "overviewCellsButton") viewCellDetails();
|
if (button === "overviewCellsButton") viewCellDetails();
|
||||||
|
|
||||||
// Click to Regenerate buttons
|
// Click to Regenerate buttons
|
||||||
|
|
|
||||||
|
|
@ -31,7 +31,7 @@ function editZones() {
|
||||||
if (cl.contains("icon-trash-empty")) {zoneRemove(zone); return;}
|
if (cl.contains("icon-trash-empty")) {zoneRemove(zone); return;}
|
||||||
if (cl.contains("icon-eye")) {toggleVisibility(el); return;}
|
if (cl.contains("icon-eye")) {toggleVisibility(el); return;}
|
||||||
if (cl.contains("icon-pin")) {focusOnZone(zone, cl); return;}
|
if (cl.contains("icon-pin")) {focusOnZone(zone, cl); return;}
|
||||||
if (cl.contains("zoneFill")) {changeFill(el); return;}
|
if (cl.contains("fillRect")) {changeFill(el); return;}
|
||||||
if (customization) selectZone(el);
|
if (customization) selectZone(el);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -58,7 +58,7 @@ function editZones() {
|
||||||
const focused = defs.select("#fog #focus"+this.id).size();
|
const focused = defs.select("#fog #focus"+this.id).size();
|
||||||
|
|
||||||
lines += `<div class="states" data-id="${this.id}" data-fill="${fill}" data-description="${description}" data-cells=${c.length} data-area=${area} data-population=${population}>
|
lines += `<div class="states" data-id="${this.id}" data-fill="${fill}" data-description="${description}" data-cells=${c.length} data-area=${area} data-population=${population}>
|
||||||
<svg data-tip="Zone fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${fill}" class="zoneFill"></svg>
|
<svg data-tip="Zone fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${fill}" class="fillRect pointer"></svg>
|
||||||
<input data-tip="Zone description. Click and type to change" class="religionName" value="${description}" autocorrect="off" spellcheck="false">
|
<input data-tip="Zone description. Click and type to change" class="religionName" value="${description}" autocorrect="off" spellcheck="false">
|
||||||
<span data-tip="Cells count" class="icon-check-empty hide"></span>
|
<span data-tip="Cells count" class="icon-check-empty hide"></span>
|
||||||
<div data-tip="Cells count" class="stateCells hide">${c.length}</div>
|
<div data-tip="Cells count" class="stateCells hide">${c.length}</div>
|
||||||
|
|
@ -314,7 +314,7 @@ function editZones() {
|
||||||
const unit = areaUnit.value === "square" ? " " + distanceUnitInput.value + "²" : " " + areaUnit.value;
|
const unit = areaUnit.value === "square" ? " " + distanceUnitInput.value + "²" : " " + areaUnit.value;
|
||||||
|
|
||||||
const line = `<div class="states" data-id="${id}" data-fill="${fill}" data-description="${description}" data-cells=0 data-area=0 data-population=0>
|
const line = `<div class="states" data-id="${id}" data-fill="${fill}" data-description="${description}" data-cells=0 data-area=0 data-population=0>
|
||||||
<svg data-tip="Zone fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${fill}" class="zoneFill"></svg>
|
<svg data-tip="Zone fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${fill}" class="fillRect pointer"></svg>
|
||||||
<input data-tip="Zone description. Click and type to change" class="religionName" value="${description}" autocorrect="off" spellcheck="false">
|
<input data-tip="Zone description. Click and type to change" class="religionName" value="${description}" autocorrect="off" spellcheck="false">
|
||||||
<span data-tip="Cells count" class="icon-check-empty hide"></span>
|
<span data-tip="Cells count" class="icon-check-empty hide"></span>
|
||||||
<div data-tip="Cells count" class="stateCells hide">0</div>
|
<div data-tip="Cells count" class="stateCells hide">0</div>
|
||||||
|
|
|
||||||
|
|
@ -396,9 +396,8 @@ function getAdjective(string) {
|
||||||
|
|
||||||
const end = string.slice(-1); // last letter of string
|
const end = string.slice(-1); // last letter of string
|
||||||
if (end === "a") return string += "n";
|
if (end === "a") return string += "n";
|
||||||
if (end === "i") return string += "an";
|
|
||||||
if (end === "o") return string = trimVowels(string) + "an";
|
if (end === "o") return string = trimVowels(string) + "an";
|
||||||
if (end === "c" || end === "y" || end === "u") return string += "an";
|
if (vowel(end) || end === "c") return string += "an"; // ceiuy
|
||||||
if (end === "m" || end === "n") return string += "ese";
|
if (end === "m" || end === "n") return string += "ese";
|
||||||
if (end === "q") return string += "i";
|
if (end === "q") return string += "i";
|
||||||
return trimVowels(string) + "ian";
|
return trimVowels(string) + "ian";
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue