Merge branch 'upstream' into dev-submaps
2
.gitignore
vendored
|
|
@ -1,2 +1,4 @@
|
||||||
.bat
|
.bat
|
||||||
.vscode
|
.vscode
|
||||||
|
.idea
|
||||||
|
.idea/Fantasy-Map-Generator.iml
|
||||||
|
|
|
||||||
74
components/fill-box.js
Normal file
|
|
@ -0,0 +1,74 @@
|
||||||
|
// fill-box cannot use Shadow DOM as it needs access to svg hatches
|
||||||
|
// append stylesheet
|
||||||
|
{
|
||||||
|
const style = `
|
||||||
|
fill-box:not([disabled]) {
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
|
fill-box > svg {
|
||||||
|
vertical-align: middle;
|
||||||
|
pointer-events: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
fill-box > svg > rect {
|
||||||
|
stroke: #666666;
|
||||||
|
stroke-width: 2;
|
||||||
|
}`;
|
||||||
|
|
||||||
|
const styleElement = document.createElement("style");
|
||||||
|
styleElement.setAttribute("type", "text/css");
|
||||||
|
styleElement.innerHTML = style;
|
||||||
|
document.head.appendChild(styleElement);
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
const template = document.createElement("template");
|
||||||
|
template.innerHTML = `
|
||||||
|
<svg>
|
||||||
|
<rect x="0" y="0" width="100%" height="100%">
|
||||||
|
</svg>
|
||||||
|
`;
|
||||||
|
|
||||||
|
class FillBox extends HTMLElement {
|
||||||
|
constructor() {
|
||||||
|
super();
|
||||||
|
|
||||||
|
this.appendChild(template.content.cloneNode(true));
|
||||||
|
this.querySelector("rect")?.setAttribute("fill", this.fill);
|
||||||
|
this.querySelector("svg")?.setAttribute("width", this.size);
|
||||||
|
this.querySelector("svg")?.setAttribute("height", this.size);
|
||||||
|
}
|
||||||
|
|
||||||
|
static showTip() {
|
||||||
|
tip(this.tip);
|
||||||
|
}
|
||||||
|
|
||||||
|
connectedCallback() {
|
||||||
|
this.addEventListener("mousemove", this.constructor.showTip);
|
||||||
|
}
|
||||||
|
|
||||||
|
disconnectedCallback() {
|
||||||
|
this.removeEventListener("mousemove", this.constructor.showTip);
|
||||||
|
}
|
||||||
|
|
||||||
|
get fill() {
|
||||||
|
return this.getAttribute("fill") || "#333";
|
||||||
|
}
|
||||||
|
|
||||||
|
set fill(newFill) {
|
||||||
|
this.setAttribute("fill", newFill);
|
||||||
|
this.querySelector("rect")?.setAttribute("fill", newFill);
|
||||||
|
}
|
||||||
|
|
||||||
|
get size() {
|
||||||
|
return this.getAttribute("size") || "1em";
|
||||||
|
}
|
||||||
|
|
||||||
|
get tip() {
|
||||||
|
return this.dataset.tip || "Fill style. Click to change";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
customElements.define("fill-box", FillBox);
|
||||||
|
}
|
||||||
31
dropbox.html
|
|
@ -7,35 +7,34 @@
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<script>
|
<script>
|
||||||
/*
|
// open this page in a new window without query parameter to start auth
|
||||||
open this page in a new window without query parameter to start auth
|
// setDropBoxToken(token) will be called on the opener window
|
||||||
window.opener.setDropBoxToken(token) will be called on the opener
|
|
||||||
window.
|
|
||||||
*/
|
|
||||||
const REDIRECT_URI = window.location.origin + window.location.pathname;
|
const REDIRECT_URI = window.location.origin + window.location.pathname;
|
||||||
const dbxAuth = new Dropbox.DropboxAuth({clientId: "pdr9ae64ip0qno4"});
|
const auth = new Dropbox.DropboxAuth({clientId: "pdr9ae64ip0qno4"});
|
||||||
|
|
||||||
const spObj = new URLSearchParams(window.location.search);
|
const params = new URLSearchParams(window.location.search);
|
||||||
const searchParams = Object.fromEntries(spObj.entries());
|
const code = params.get("code");
|
||||||
|
const error = params.get("error");
|
||||||
|
|
||||||
if (searchParams.code) getToken();
|
if (code) getToken();
|
||||||
else doAuth(); // start authentication
|
else if (error) window.opener.Cloud.providers.dropbox.returnError(params.get("error_description"));
|
||||||
|
else startAuth();
|
||||||
|
|
||||||
function doAuth() {
|
function startAuth() {
|
||||||
dbxAuth
|
auth
|
||||||
.getAuthenticationUrl(REDIRECT_URI, undefined, "code", "offline", undefined, undefined, true)
|
.getAuthenticationUrl(REDIRECT_URI, undefined, "code", "offline", undefined, undefined, true)
|
||||||
.then(authUrl => {
|
.then(authUrl => {
|
||||||
window.sessionStorage.clear();
|
window.sessionStorage.clear();
|
||||||
window.sessionStorage.setItem("codeVerifier", dbxAuth.codeVerifier);
|
window.sessionStorage.setItem("codeVerifier", auth.codeVerifier);
|
||||||
window.location.href = authUrl;
|
window.location.href = authUrl;
|
||||||
})
|
})
|
||||||
.catch(error => console.error(error));
|
.catch(error => console.error(error));
|
||||||
}
|
}
|
||||||
|
|
||||||
function getToken() {
|
function getToken() {
|
||||||
dbxAuth.setCodeVerifier(window.sessionStorage.getItem("codeVerifier"));
|
auth.setCodeVerifier(window.sessionStorage.getItem("codeVerifier"));
|
||||||
dbxAuth
|
auth
|
||||||
.getAccessTokenFromCode(REDIRECT_URI, searchParams.code)
|
.getAccessTokenFromCode(REDIRECT_URI, code)
|
||||||
.then(resp => {
|
.then(resp => {
|
||||||
const token = resp.result.access_token;
|
const token = resp.result.access_token;
|
||||||
window.opener.Cloud.providers.dropbox.setDropBoxToken(token);
|
window.opener.Cloud.providers.dropbox.setDropBoxToken(token);
|
||||||
|
|
|
||||||
BIN
heightmaps/africa-centric.png
Normal file
|
After Width: | Height: | Size: 65 KiB |
BIN
heightmaps/arabia.png
Normal file
|
After Width: | Height: | Size: 95 KiB |
BIN
heightmaps/atlantics.png
Normal file
|
After Width: | Height: | Size: 95 KiB |
BIN
heightmaps/britain.png
Normal file
|
After Width: | Height: | Size: 49 KiB |
BIN
heightmaps/caribbean.png
Normal file
|
After Width: | Height: | Size: 57 KiB |
BIN
heightmaps/east-asia.png
Normal file
|
After Width: | Height: | Size: 59 KiB |
BIN
heightmaps/eurasia.png
Normal file
|
After Width: | Height: | Size: 94 KiB |
BIN
heightmaps/europe-accented.png
Normal file
|
After Width: | Height: | Size: 122 KiB |
BIN
heightmaps/europe-and-central-asia.png
Normal file
|
After Width: | Height: | Size: 101 KiB |
BIN
heightmaps/europe-central.png
Normal file
|
After Width: | Height: | Size: 105 KiB |
BIN
heightmaps/europe-north.png
Normal file
|
After Width: | Height: | Size: 91 KiB |
BIN
heightmaps/europe.png
Normal file
|
After Width: | Height: | Size: 114 KiB |
BIN
heightmaps/greenland.png
Normal file
|
After Width: | Height: | Size: 102 KiB |
BIN
heightmaps/hellenica.png
Normal file
|
After Width: | Height: | Size: 94 KiB |
BIN
heightmaps/iceland.png
Normal file
|
After Width: | Height: | Size: 105 KiB |
8
heightmaps/import-rules.txt
Normal file
|
|
@ -0,0 +1,8 @@
|
||||||
|
To get heightmap with correct height scale:
|
||||||
|
1. Open tangrams.github.io
|
||||||
|
2. Toggle off auto-exposure
|
||||||
|
3. Set max elevation to 2000
|
||||||
|
4. Set min elevation to -500
|
||||||
|
5. Find region you like
|
||||||
|
6. Render image
|
||||||
|
7. Optionally rescale image to a smaller size (e.g. 500x300px) as high resolution is not used
|
||||||
BIN
heightmaps/indian-ocean.png
Normal file
|
After Width: | Height: | Size: 66 KiB |
BIN
heightmaps/mediterranean-sea.png
Normal file
|
After Width: | Height: | Size: 99 KiB |
BIN
heightmaps/middle-east.png
Normal file
|
After Width: | Height: | Size: 100 KiB |
BIN
heightmaps/north-america.png
Normal file
|
After Width: | Height: | Size: 82 KiB |
BIN
heightmaps/us-centric.png
Normal file
|
After Width: | Height: | Size: 84 KiB |
BIN
heightmaps/us-mainland.png
Normal file
|
After Width: | Height: | Size: 75 KiB |
BIN
heightmaps/world-from-pacific.png
Normal file
|
After Width: | Height: | Size: 98 KiB |
BIN
heightmaps/world.png
Normal file
|
After Width: | Height: | Size: 99 KiB |
BIN
images/Discord.png
Normal file
|
After Width: | Height: | Size: 869 B |
88
index.css
|
|
@ -1531,6 +1531,11 @@ div.states > .riverType {
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.changeRelations > * {
|
||||||
|
pointer-events: none;
|
||||||
|
cursor: pointer;
|
||||||
|
}
|
||||||
|
|
||||||
#diplomacySelect {
|
#diplomacySelect {
|
||||||
width: 5em;
|
width: 5em;
|
||||||
margin: 0.1em 0 0 -0.3em;
|
margin: 0.1em 0 0 -0.3em;
|
||||||
|
|
@ -1668,11 +1673,6 @@ div.states > div.biomeArea {
|
||||||
width: 5em;
|
width: 5em;
|
||||||
}
|
}
|
||||||
|
|
||||||
rect.fillRect {
|
|
||||||
stroke: #666666;
|
|
||||||
stroke-width: 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
#militaryHeader > div,
|
#militaryHeader > div,
|
||||||
#regimentsHeader > div {
|
#regimentsHeader > div {
|
||||||
width: 5.2em;
|
width: 5.2em;
|
||||||
|
|
@ -2036,7 +2036,7 @@ div.textual span,
|
||||||
fill: none;
|
fill: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
div#notes {
|
#notes {
|
||||||
display: none;
|
display: none;
|
||||||
position: fixed;
|
position: fixed;
|
||||||
width: 28vw;
|
width: 28vw;
|
||||||
|
|
@ -2046,22 +2046,47 @@ div#notes {
|
||||||
border: 1px solid #5e4fa2;
|
border: 1px solid #5e4fa2;
|
||||||
background: rgba(255, 250, 228, 0.7);
|
background: rgba(255, 250, 228, 0.7);
|
||||||
box-shadow: 2px 2px 5px -3px #3a2804;
|
box-shadow: 2px 2px 5px -3px #3a2804;
|
||||||
white-space: pre-line;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
div#notesHeader {
|
@media screen and (max-width: 600px) {
|
||||||
|
#notes {
|
||||||
|
width: 50vw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#notesHeader {
|
||||||
font-weight: bold;
|
font-weight: bold;
|
||||||
font-size: 1.3em;
|
font-size: 1.3em;
|
||||||
padding: 0 0 4px 14px;
|
padding: 16px 0 4px 12px;
|
||||||
border-bottom: 1px solid #5e4fa2;
|
border-bottom: 1px solid #5e4fa2;
|
||||||
}
|
}
|
||||||
|
|
||||||
div#notesBody {
|
#notesBody {
|
||||||
padding: 0 1em;
|
padding: 14px 12px;
|
||||||
max-height: 80vh;
|
max-height: 80vh;
|
||||||
overflow: auto;
|
overflow: auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#notesBody > iframe {
|
||||||
|
pointer-events: none;
|
||||||
|
user-select: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
#notesBody p {
|
||||||
|
margin: 4px;
|
||||||
|
}
|
||||||
|
|
||||||
|
#notesLegend {
|
||||||
|
height: 87%;
|
||||||
|
outline: 0;
|
||||||
|
overflow-y: auto;
|
||||||
|
padding: 0.6em;
|
||||||
|
font-family: Copperplate, monospace;
|
||||||
|
background-color: #fff;
|
||||||
|
border: 1px solid #dedede;
|
||||||
|
color: #000;
|
||||||
|
}
|
||||||
|
|
||||||
svg.button {
|
svg.button {
|
||||||
position: relative;
|
position: relative;
|
||||||
background-color: transparent;
|
background-color: transparent;
|
||||||
|
|
@ -2310,7 +2335,7 @@ svg.button {
|
||||||
|
|
||||||
.epgrid line {
|
.epgrid line {
|
||||||
stroke: lightgrey;
|
stroke: lightgrey;
|
||||||
stroke-opacity: 0.7;
|
stroke-opacity: 0.5;
|
||||||
shape-rendering: crispEdges;
|
shape-rendering: crispEdges;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -2318,45 +2343,6 @@ svg.button {
|
||||||
stroke-width: 0;
|
stroke-width: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
.pell {
|
|
||||||
border: 1px solid hsla(0, 0%, 4%, 0.1);
|
|
||||||
}
|
|
||||||
|
|
||||||
.pell,
|
|
||||||
.pell-content {
|
|
||||||
box-sizing: border-box;
|
|
||||||
}
|
|
||||||
|
|
||||||
.pell-content {
|
|
||||||
height: 14em;
|
|
||||||
outline: 0;
|
|
||||||
overflow-y: auto;
|
|
||||||
padding: 0.6em;
|
|
||||||
font-family: Copperplate, monospace;
|
|
||||||
background-color: #fff;
|
|
||||||
border: 1px solid #dedede;
|
|
||||||
}
|
|
||||||
|
|
||||||
.pell-actionbar {
|
|
||||||
background-color: #fff;
|
|
||||||
border: 1px solid #dedede;
|
|
||||||
border-bottom: 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
.pell-button {
|
|
||||||
background-color: transparent;
|
|
||||||
border: none;
|
|
||||||
cursor: pointer;
|
|
||||||
height: 30px;
|
|
||||||
outline: 0;
|
|
||||||
width: 30px;
|
|
||||||
vertical-align: bottom;
|
|
||||||
}
|
|
||||||
|
|
||||||
.pell-button-selected {
|
|
||||||
background-color: #f0f0f0;
|
|
||||||
}
|
|
||||||
|
|
||||||
#debug {
|
#debug {
|
||||||
font-size: 1px;
|
font-size: 1px;
|
||||||
opacity: 0.8;
|
opacity: 0.8;
|
||||||
|
|
|
||||||
341
index.html
|
|
@ -19,7 +19,7 @@
|
||||||
body {margin: 0; font-size: 10px; overflow: hidden;}
|
body {margin: 0; font-size: 10px; overflow: hidden;}
|
||||||
#map {position: absolute;}
|
#map {position: absolute;}
|
||||||
#initial {fill: none; stroke: black; pointer-events: none;}
|
#initial {fill: none; stroke: black; pointer-events: none;}
|
||||||
#init-rose {animation: 20s infinite spin; opacity: .7; transform-origin: center;}
|
#init-rose {opacity: .7; transform-origin: center; opacity: .7; animation: 20s infinite spin;}
|
||||||
@keyframes spin {0% {transform: rotate(0deg);} 100% {transform: rotate(359deg);}}
|
@keyframes spin {0% {transform: rotate(0deg);} 100% {transform: rotate(359deg);}}
|
||||||
#loading {opacity:1; font-size: 11px; color:#fff5da; text-align:center; text-shadow:0px 1px 4px #4c3a35; width:80%; max-width:600px; position:fixed; top:50%; left:50%; transform:translate(-50%, -50%); pointer-events:none;}
|
#loading {opacity:1; font-size: 11px; color:#fff5da; text-align:center; text-shadow:0px 1px 4px #4c3a35; width:80%; max-width:600px; position:fixed; top:50%; left:50%; transform:translate(-50%, -50%); pointer-events:none;}
|
||||||
#loading-text {font-size: 1.8em; margin: 0.2em 0 0 1em;}
|
#loading-text {font-size: 1.8em; margin: 0.2em 0 0 1em;}
|
||||||
|
|
@ -148,55 +148,6 @@
|
||||||
</filter>
|
</filter>
|
||||||
</g>
|
</g>
|
||||||
|
|
||||||
<g id="hatching">
|
|
||||||
<pattern id="hatch0" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch1" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch2" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:2"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch3" patternTransform="rotate(-45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch4" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:1.5"/>
|
|
||||||
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch5" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:1.5"/>
|
|
||||||
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch6" patternUnits="userSpaceOnUse" width="5" height="5">
|
|
||||||
<circle cx="2.5" cy="2.5" r="1" style="fill: black"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch7" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="3" transform="rotate(-45 0 0)" style="stroke:black; stroke-width:1.5" />
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch8" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:2.5"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch9" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:2.5"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch10" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:2.5"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch11" patternTransform="rotate(-45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:2.5"/>
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch12" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="1" x2="0" y2="3" style="stroke:black; stroke-width:1.5" />
|
|
||||||
<line x1="1" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:1.5" />
|
|
||||||
</pattern>
|
|
||||||
<pattern id="hatch13" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
|
||||||
<line x1="0" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:1.5" />
|
|
||||||
<line x1="0" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:1.5" />
|
|
||||||
</pattern>
|
|
||||||
</g>
|
|
||||||
|
|
||||||
<g id="deftemp">
|
<g id="deftemp">
|
||||||
<mask id="land"></mask>
|
<mask id="land"></mask>
|
||||||
<mask id="water">
|
<mask id="water">
|
||||||
|
|
@ -211,14 +162,14 @@
|
||||||
</g>
|
</g>
|
||||||
|
|
||||||
<pattern id="oceanic" width="100" height="100" patternUnits="userSpaceOnUse">
|
<pattern id="oceanic" width="100" height="100" patternUnits="userSpaceOnUse">
|
||||||
<image id="oceanicPattern" href="./images/pattern1.png"></image>
|
<image id="oceanicPattern" href="./images/pattern1.png" opacity="0.2"></image>
|
||||||
</pattern>
|
</pattern>
|
||||||
</defs>
|
</defs>
|
||||||
<g id="viewbox"></g>
|
<g id="viewbox"></g>
|
||||||
<g id="scaleBar"></g>
|
<g id="scaleBar"></g>
|
||||||
<g id="initial" opacity=1>
|
<g id="initial" opacity=1>
|
||||||
<rect x="-1%" y="-1%" width="102%" height="102%" fill="#466eab"/>
|
<rect x="-1%" y="-1%" width="102%" height="102%" fill="#466eab"/>
|
||||||
<rect x="-1%" y="-1%" width="102%" height="102%" fill="url(#oceanic)" opacity=".2"/>
|
<rect x="-1%" y="-1%" width="102%" height="102%" fill="url(#oceanic)"/>
|
||||||
<use href="#rose" id="init-rose" x="50%" y="50%"/>
|
<use href="#rose" id="init-rose" x="50%" y="50%"/>
|
||||||
</g>
|
</g>
|
||||||
</svg>
|
</svg>
|
||||||
|
|
@ -226,7 +177,7 @@
|
||||||
<div id="loading">
|
<div id="loading">
|
||||||
<div id="titleName"><t data-t="titleName">Azgaar's</t></div>
|
<div id="titleName"><t data-t="titleName">Azgaar's</t></div>
|
||||||
<div id="title"><t data-t="title">Fantasy Map Generator</t></div>
|
<div id="title"><t data-t="title">Fantasy Map Generator</t></div>
|
||||||
<div id="version"><t data-t="version">v. </t>1.71</div>
|
<div id="version"><t data-t="version">v. </t>1.73</div>
|
||||||
<p id="loading-text"><t data-t="loading">LOADING</t><span>.</span><span>.</span><span>.</span></p>
|
<p id="loading-text"><t data-t="loading">LOADING</t><span>.</span><span>.</span><span>.</span></p>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
@ -309,17 +260,9 @@
|
||||||
|
|
||||||
<div id="styleContent" class="tabcontent">
|
<div id="styleContent" class="tabcontent">
|
||||||
<p data-tip="Select a style preset. State labels may required regeneration if font is changed" style="display: inline-block">Style preset:</p>
|
<p data-tip="Select a style preset. State labels may required regeneration if font is changed" style="display: inline-block">Style preset:</p>
|
||||||
<select data-tip="Select a style preset" id="stylePreset" onchange="changeStylePreset(this.value)" style="width:45%">
|
<select data-tip="Select a style preset" id="stylePreset" onchange="requestStylePresetChange(this.value)" style="width:45%; text-transform: capitalize;"></select>
|
||||||
<option value="styleDefault" data-system=1 selected>Default</option>
|
|
||||||
<option value="styleAncient" data-system=1>Ancient</option>
|
|
||||||
<option value="styleGloom" data-system=1>Gloom</option>
|
|
||||||
<option value="styleClean" data-system=1>Clean</option>
|
|
||||||
<option value="styleLight" data-system=1>Light</option>
|
|
||||||
<option value="styleWatercolor" data-system=1>Watercolor</option>
|
|
||||||
<option value="styleMonochrome" data-system=1>Monochrome</option>
|
|
||||||
</select>
|
|
||||||
<button id="addStyleButton" data-tip="Click to save current style as a new preset" class="icon-plus sideButton" style="display: inline-block" onclick="addStylePreset()"></button>
|
<button id="addStyleButton" data-tip="Click to save current style as a new preset" class="icon-plus sideButton" style="display: inline-block" onclick="addStylePreset()"></button>
|
||||||
<button id="removeStyleButton" data-tip="Click to remove current custom style preset" class="icon-minus sideButton" style="display: none" onclick="removeStylePreset()"></button>
|
<button id="removeStyleButton" data-tip="Click to remove current custom style preset" class="icon-minus sideButton" style="display: none" onclick="requestRemoveStylePreset()"></button>
|
||||||
|
|
||||||
<p data-tip="Select an element to edit its style" style="display: inline-block;">Select element:</p>
|
<p data-tip="Select an element to edit its style" style="display: inline-block;">Select element:</p>
|
||||||
<select data-tip="Select an element to edit its style (list is ordered alphabetically)" id="styleElementSelect" style="width:42%">
|
<select data-tip="Select an element to edit its style (list is ordered alphabetically)" id="styleElementSelect" style="width:42%">
|
||||||
|
|
@ -996,13 +939,14 @@
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
|
|
||||||
<tr data-tip="Select template to be used for a Heightmap generation">
|
<tr data-tip="Select heightmap generation template or precreated heightmap">
|
||||||
<td>
|
<td>
|
||||||
<i data-locked=0 id="lock_template" class="icon-lock-open"></i>
|
<i data-locked=0 id="lock_template" class="icon-lock-open"></i>
|
||||||
</td>
|
</td>
|
||||||
<td>Map template</td>
|
<td>Heightmap</td>
|
||||||
<td>
|
<td>
|
||||||
<select id="templateInput" data-stored="template">
|
<select id="templateInput" data-stored="template">
|
||||||
|
<optgroup label="Template">
|
||||||
<option value="volcano">Volcano</option>
|
<option value="volcano">Volcano</option>
|
||||||
<option value="highIsland">High Island</option>
|
<option value="highIsland">High Island</option>
|
||||||
<option value="lowIsland">Low Island</option>
|
<option value="lowIsland">Low Island</option>
|
||||||
|
|
@ -1015,6 +959,32 @@
|
||||||
<option value="isthmus">Isthmus</option>
|
<option value="isthmus">Isthmus</option>
|
||||||
<option value="shattered">Shattered</option>
|
<option value="shattered">Shattered</option>
|
||||||
<option value="taklamakan">Taklamakan</option>
|
<option value="taklamakan">Taklamakan</option>
|
||||||
|
</optgroup>
|
||||||
|
<optgroup label="Specific">
|
||||||
|
<option value="africa-centric">Africa Centric</option>
|
||||||
|
<option value="arabia">Arabia</option>
|
||||||
|
<option value="atlantics">Atlantics</option>
|
||||||
|
<option value="britain">Britain</option>
|
||||||
|
<option value="caribbean">Caribbean</option>
|
||||||
|
<option value="east-asia">East Asia</option>
|
||||||
|
<option value="eurasia">Eurasia</option>
|
||||||
|
<option value="europe">Europe</option>
|
||||||
|
<option value="europe-accented">Europe Accented</option>
|
||||||
|
<option value="europe-and-central-asia">Europe and Central Asia</option>
|
||||||
|
<option value="europe-central">Europe Central</option>
|
||||||
|
<option value="europe-north">Europe North</option>
|
||||||
|
<option value="greenland">Greenland</option>
|
||||||
|
<option value="hellenica">Hellenica</option>
|
||||||
|
<option value="iceland">Iceland</option>
|
||||||
|
<option value="indian-ocean">Indian Ocean</option>
|
||||||
|
<option value="mediterranean-sea">Mediterranean Sea</option>
|
||||||
|
<option value="middle-east">Middle East</option>
|
||||||
|
<option value="north-america">North America</option>
|
||||||
|
<option value="us-centric">US-centric</option>
|
||||||
|
<option value="us-mainland">US Mainland</option>
|
||||||
|
<option value="world">World</option>
|
||||||
|
<option value="world-from-pacific">World from Pacific</option>
|
||||||
|
</optgroup>
|
||||||
</select>
|
</select>
|
||||||
</td>
|
</td>
|
||||||
<td></td>
|
<td></td>
|
||||||
|
|
@ -1489,6 +1459,7 @@
|
||||||
<li><a href="http://www.tumblr.com/share?v=3&u=https%3A%2F%2Fazgaar.github.io%2FFantasy-Map-Generator" target="_blank" data-tip="Post to Tumblr"><img alt="Post to Tumblr" src="images/Tumblr.png" /></a></li>
|
<li><a href="http://www.tumblr.com/share?v=3&u=https%3A%2F%2Fazgaar.github.io%2FFantasy-Map-Generator" target="_blank" data-tip="Post to Tumblr"><img alt="Post to Tumblr" src="images/Tumblr.png" /></a></li>
|
||||||
<li><a href="http://pinterest.com/pin/create/button/?url=https%3A%2F%2Fazgaar.github.io%2FFantasy-Map-Generator" target="_blank" data-tip="Pin it"><img alt="Pin it" src="images/Pinterest.png" /></a></li>
|
<li><a href="http://pinterest.com/pin/create/button/?url=https%3A%2F%2Fazgaar.github.io%2FFantasy-Map-Generator" target="_blank" data-tip="Pin it"><img alt="Pin it" src="images/Pinterest.png" /></a></li>
|
||||||
<li><a href="http://www.reddit.com/submit?url=https%3A%2F%2Fazgaar.github.io%2FFantasy-Map-Generator" target="_blank" data-tip="Submit to Reddit"><img alt="Submit to Reddit" src="images/Reddit.png" /></a></li>
|
<li><a href="http://www.reddit.com/submit?url=https%3A%2F%2Fazgaar.github.io%2FFantasy-Map-Generator" target="_blank" data-tip="Submit to Reddit"><img alt="Submit to Reddit" src="images/Reddit.png" /></a></li>
|
||||||
|
<li><a href="https://discord.gg/X7E84HU" target="_blank" data-tip="Join Discord server"><img alt="Join Discord server" src="images/Discord.png" /></a></li>
|
||||||
</ul>
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|
@ -1649,7 +1620,7 @@
|
||||||
<button id="labelSizeHide" data-tip="Hide the font size section" class="icon-text-height"></button>
|
<button id="labelSizeHide" data-tip="Hide the font size section" class="icon-text-height"></button>
|
||||||
<input id="labelStartOffset" data-tip="Set starting offset for the particular label" type="range" min=20 max=80 style="width:8em">
|
<input id="labelStartOffset" data-tip="Set starting offset for the particular label" type="range" min=20 max=80 style="width:8em">
|
||||||
<i class="icon-text-height"></i>
|
<i class="icon-text-height"></i>
|
||||||
<input id="labelRelativeSize" data-tip="Set relative size for the particular label" type="number" min=30 max=300 step=1 style="width:3.2em">
|
<input id="labelRelativeSize" data-tip="Set relative size for the particular label" type="number" min=30 max=300 step=1 style="width:4.5em">
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<button id="labelAlign" data-tip="Turn text path into a straight line" class="icon-resize-horizontal"></button>
|
<button id="labelAlign" data-tip="Turn text path into a straight line" class="icon-resize-horizontal"></button>
|
||||||
|
|
@ -1995,7 +1966,7 @@
|
||||||
<div id="burgBody" style="padding-bottom: .3em">
|
<div id="burgBody" style="padding-bottom: .3em">
|
||||||
<div style="display: flex; align-items: center">
|
<div style="display: flex; align-items: center">
|
||||||
<svg data-tip="Burg emblem. Click to edit" class="pointer" viewBox="0 0 200 200" width="13em" height="13em"><use id="burgEmblem"></use></svg>
|
<svg data-tip="Burg emblem. Click to edit" class="pointer" viewBox="0 0 200 200" width="13em" height="13em"><use id="burgEmblem"></use></svg>
|
||||||
<div>
|
<div style="display: grid; grid-auto-rows: minmax(1.6em, auto)">
|
||||||
<div id="burgProvinceAndState" style="font-style: italic; max-width: 16em"></div>
|
<div id="burgProvinceAndState" style="font-style: italic; max-width: 16em"></div>
|
||||||
|
|
||||||
<div>
|
<div>
|
||||||
|
|
@ -2044,6 +2015,7 @@
|
||||||
<div class="label">Temperature:</div>
|
<div class="label">Temperature:</div>
|
||||||
<span id="burgTemperature"></span>, like in
|
<span id="burgTemperature"></span>, like in
|
||||||
<span id="burgTemperatureLikeIn"></span>
|
<span id="burgTemperatureLikeIn"></span>
|
||||||
|
<i id="burgTemperatureGraph" data-tip="Show temperature graph for the burg" class="icon-chart-area pointer"></i>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div data-tip="Burg height above mean sea level">
|
<div data-tip="Burg height above mean sea level">
|
||||||
|
|
@ -2932,9 +2904,10 @@
|
||||||
<div id="zonesEditor" class="dialog stable" style="display: none">
|
<div id="zonesEditor" class="dialog stable" style="display: none">
|
||||||
<div id="customHeader" class="header">
|
<div id="customHeader" class="header">
|
||||||
<div style="left:1.8em" data-tip="Zone description">Description </div>
|
<div style="left:1.8em" data-tip="Zone description">Description </div>
|
||||||
<div style="left:13em" data-tip="Zone cells count" class="hide">Cells </div>
|
<div style="left:13em" data-tip="Zone type">Type </div>
|
||||||
<div style="left:19em" data-tip="Zone area" class="hide">Area </div>
|
<div style="left:19em" data-tip="Zone cells count" class="hide">Cells </div>
|
||||||
<div style="left:24em" data-tip="Zone population" class="hide">Population </div>
|
<div style="left:23.6em" data-tip="Zone area" class="hide">Area </div>
|
||||||
|
<div style="left:30.6em" data-tip="Zone population" class="hide">Population </div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="zonesBodySection" class="table" data-type="absolute"></div>
|
<div id="zonesBodySection" class="table" data-type="absolute"></div>
|
||||||
|
|
@ -2955,35 +2928,35 @@
|
||||||
<button id="zonesManually" data-tip="Re-assign zones" class="icon-brush"></button>
|
<button id="zonesManually" data-tip="Re-assign zones" class="icon-brush"></button>
|
||||||
<div id="zonesManuallyButtons" style="display: none">
|
<div id="zonesManuallyButtons" style="display: none">
|
||||||
<label data-tip="Change brush size. Shortcut: + (increase), – (decrease)" class="italic">Brush:
|
<label data-tip="Change brush size. Shortcut: + (increase), – (decrease)" class="italic">Brush:
|
||||||
<input id="zonesBrush" oninput="tip('Brush size: '+this.value); zonesBrushNumber.value = this.value" type="range" min=5 max=25 value=7 style="width:7em">
|
<input id="zonesBrush" oninput="tip('Brush size: '+this.value); zonesBrushNumber.value = this.value" type="range" min=5 max=50 value=7 style="width:9em">
|
||||||
<input id="zonesBrushNumber" oninput="tip('Brush size: '+this.value); zonesBrush.value = this.value" type="number" min=5 max=25 value=7>
|
<input id="zonesBrushNumber" oninput="tip('Brush size: '+this.value); zonesBrush.value = this.value" type="number" min=5 max=50 value=7>
|
||||||
</label><br>
|
</label><br>
|
||||||
<button id="zonesManuallyApply" data-tip="Apply assignment" class="icon-check"></button>
|
<button id="zonesManuallyApply" data-tip="Apply assignment" class="icon-check"></button>
|
||||||
<button id="zonesManuallyCancel" data-tip="Cancel assignment" class="icon-cancel"></button>
|
<button id="zonesManuallyCancel" data-tip="Cancel assignment" class="icon-cancel"></button>
|
||||||
<button id="zonesRemove" data-tip="Click to toggle the removal mode on brush dragging. Shortcut: ctrl" class="icon-eraser"></button>
|
<button id="zonesRemove" data-tip="Click to toggle the removal mode on brush dragging. Shortcut: ctrl" class="icon-eraser"></button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<button id="zonesAdd" data-tip="Add a new zone layer" class="icon-plus"></button>
|
<button id="zonesAdd" data-tip="Add new zone layer" class="icon-plus"></button>
|
||||||
<button id="zonesExport" data-tip="Download zones-related data" class="icon-download"></button>
|
<button id="zonesExport" data-tip="Download zones-related data" class="icon-download"></button>
|
||||||
|
|
||||||
|
<div id="zonesFilters" data-tip="Show only zones of selected type" style="display: inline-block">Type: <select id="zonesFilterType"></select></div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="notesEditor" class="dialog stable textual" style="display: none">
|
<div id="notesEditor" class="dialog stable" style="display: none">
|
||||||
<div>
|
<div style="margin-bottom: 0.3em">
|
||||||
<span>Select object: </span>
|
<strong>Element: </strong>
|
||||||
<select id="notesSelect" data-tip="Select object" style="width: 12em"></select>
|
<select id="notesSelect" data-tip="Select element id" style="width: 12em"></select>
|
||||||
<span>Object name: </span>
|
<strong>Element name: </strong>
|
||||||
<input id="notesName" data-tip="Type to change object name" autocorrect="off" spellcheck="false" style="width: 16em">
|
<input id="notesName" data-tip="Set element name" autocorrect="off" spellcheck="false" style="width: 16em">
|
||||||
<span data-tip="Speak the name. You can change voice and language in options" class="speaker">🔊</span>
|
<span data-tip="Speak the name. You can change voice and language in options" class="speaker">🔊</span>
|
||||||
</div>
|
</div>
|
||||||
<div id="notesText" data-tip="Type and style object description" style="padding: .4em 0"></div>
|
<div id="notesLegend" contenteditable="true"></div>
|
||||||
<div>
|
<div style="margin-top: 0.3em">
|
||||||
<button id="notesSpeak" data-tip="Speak the note. You can change voice and language in options" class="icon-voice"></button>
|
|
||||||
<button id="notesFocus" data-tip="Focus on selected object" class="icon-target"></button>
|
<button id="notesFocus" data-tip="Focus on selected object" class="icon-target"></button>
|
||||||
<button id="notesPin" data-tip="Toggle notes box dispay: hide or do not hide the box on mouse move" class="icon-pin"></button>
|
<button id="notesPin" data-tip="Toggle notes box dispay: hide or do not hide the box on mouse move" class="icon-pin"></button>
|
||||||
<button id="notesDownload" data-tip="Download notes to PC" class="icon-download"></button>
|
<button id="notesDownload" data-tip="Download notes to PC" class="icon-download"></button>
|
||||||
<button id="notesUpload" data-tip="Upload notes from PC" class="icon-upload"></button>
|
<button id="notesUpload" data-tip="Upload notes from PC" class="icon-upload"></button>
|
||||||
<button id="notesClearStyle" data-tip="Remove all styling, get plain text only" class="icon-eraser"></button>
|
|
||||||
<button id="notesRemove" data-tip="Remove this note" class="icon-trash fastDelete"></button>
|
<button id="notesRemove" data-tip="Remove this note" class="icon-trash fastDelete"></button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
@ -3611,8 +3584,20 @@
|
||||||
</div>
|
</div>
|
||||||
<p>GeoJSON format is used in GIS tools such as QGIS. Check out <a href="https://github.com/Azgaar/Fantasy-Map-Generator/wiki/GIS-data-export" target="_blank">wiki-page</a> for guidance.</p>
|
<p>GeoJSON format is used in GIS tools such as QGIS. Check out <a href="https://github.com/Azgaar/Fantasy-Map-Generator/wiki/GIS-data-export" target="_blank">wiki-page</a> for guidance.</p>
|
||||||
<p>Generator uses pop-up window to download files. Please ensure your browser does not block popups.</p>
|
<p>Generator uses pop-up window to download files. Please ensure your browser does not block popups.</p>
|
||||||
|
|
||||||
|
<div style="margin: 1em 0 .3em; font-weight: bold">Export To JSON</div>
|
||||||
|
<div>
|
||||||
|
<button onclick="exportToJson('Full')" data-tip="Download full data as in JSON format">full</button>
|
||||||
|
<button onclick="exportToJson('Minimal')" data-tip="Download minimal data as in JSON format">minimal</button>
|
||||||
|
<button onclick="exportToJson('PackCells')" data-tip="Download map metadata and pack cells data as in JSON format">pack cells</button>
|
||||||
|
<button onclick="exportToJson('GridCells')" data-tip="Download map metadata and grid cells data as in JSON format">grid cells</button>
|
||||||
|
</div>
|
||||||
|
<p>Export in JSON format can be used as an API replacement.</p>
|
||||||
|
|
||||||
|
<div>
|
||||||
<p>It's also possible to export map to <i>Foundry VTT</i>, see <a href="https://github.com/Ethck/azgaar-foundry" target="_blank">the module.</a></p>
|
<p>It's also possible to export map to <i>Foundry VTT</i>, see <a href="https://github.com/Ethck/azgaar-foundry" target="_blank">the module.</a></p>
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div id="saveMapData" style="display: none" class="dialog">
|
<div id="saveMapData" style="display: none" class="dialog">
|
||||||
<div style="margin-top: .3em">
|
<div style="margin-top: .3em">
|
||||||
|
|
@ -3632,12 +3617,15 @@
|
||||||
<button onclick="quickLoad()" data-tip="Load map from browser storage (if saved before)">storage</button>
|
<button onclick="quickLoad()" data-tip="Load map from browser storage (if saved before)">storage</button>
|
||||||
</div>
|
</div>
|
||||||
<div id="loadFromDropbox">
|
<div id="loadFromDropbox">
|
||||||
<p style="margin-bottom: .3em">From your Dropbox account</p>
|
<p style="margin-bottom: .3em">
|
||||||
<select id="loadFromDropboxSelect" style="width: 22em"></select>
|
From your Dropbox account
|
||||||
|
<button id="dropboxConnectButton" onclick="connectToDropbox()" data-tip="Connect your Dropbox account to be able to load maps from it">Connect</button>
|
||||||
|
</p>
|
||||||
|
|
||||||
<div id="loadFromDropboxButtons" style="margin-bottom: .3em">
|
<select id="loadFromDropboxSelect" style="width: 22em"></select>
|
||||||
<button onclick="loadFromDropbox()" data-tip="Load .map file from your Dropbox">Open</button>
|
<div id="loadFromDropboxButtons" style="margin-bottom: .6em">
|
||||||
<button onclick="createSharableDropboxLink()" data-tip="Select file and create a link to share with your friends">Create link</button>
|
<button onclick="loadFromDropbox()" data-tip="Load .map file from your Dropbox">Load</button>
|
||||||
|
<button onclick="createSharableDropboxLink()" data-tip="Select file and create a link to share with your friends">Share</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div style="margin-top: .3em">
|
<div style="margin-top: .3em">
|
||||||
|
|
@ -4394,6 +4382,153 @@
|
||||||
<path d="M 43.4,0 36.2,12.5 43.4,25 M 21.7,12.5 H 36.2 Z M 0,0 H 14.5 L 21.7,12.5 14.5,25 H 0"/>
|
<path d="M 43.4,0 36.2,12.5 43.4,25 M 21.7,12.5 H 36.2 Z M 0,0 H 14.5 L 21.7,12.5 14.5,25 H 0"/>
|
||||||
</pattern>
|
</pattern>
|
||||||
</g>
|
</g>
|
||||||
|
|
||||||
|
<g id="defs-hatching">
|
||||||
|
<pattern id="hatch0" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch1" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch2" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch3" patternTransform="rotate(-45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch4" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch5" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch6" patternUnits="userSpaceOnUse" width="5" height="5">
|
||||||
|
<circle cx="2.5" cy="2.5" r="1" style="fill: black"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch7" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="3" transform="rotate(-45 0 0)" style="stroke:black; stroke-width:1.5" />
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch8" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:2.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch9" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:2.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch10" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:2.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch11" patternTransform="rotate(-45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:2.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch12" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="1" x2="0" y2="3" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="1" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch13" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="0" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch14" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="1" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch15" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="1" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch16" patternTransform="rotate(-45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="1" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch17" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="1" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="1" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch18" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="1" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="1" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch19" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="2" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch20" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="2" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch21" patternTransform="rotate(-45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="2" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch22" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="2" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="2" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch23" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="0" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch24" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="2" y1="0" x2="0" y2="4" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="2" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch25" patternTransform="rotate(-45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="2" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch26" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="2" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch27" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="2" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch28" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="2" y1="0" x2="0" y2="2" style="stroke:black; stroke-width:2"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch29" patternTransform="rotate(30 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="1" x2="0" y2="3" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="1" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch30" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="1" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="1" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch31" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="1" y1="0" x2="0" y2="3" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="1" y1="0" x2="3" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch32" patternUnits="userSpaceOnUse" width="5" height="5">
|
||||||
|
<circle cx="2.5" cy="2.5" r="0.5" style="fill: black"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch33" patternUnits="userSpaceOnUse" width="5" height="5">
|
||||||
|
<circle cx="2.5" cy="2.5" r="1.5" style="fill: black"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch34" patternUnits="userSpaceOnUse" width="5" height="5">
|
||||||
|
<circle cx="3" cy="3" r="1" style="fill: black"/>
|
||||||
|
<circle cx="1" cy="1" r="1" style="fill: black"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch35" patternUnits="userSpaceOnUse" width="5" height="5">
|
||||||
|
<circle cx="3" cy="3" r="1.5" style="fill: black"/>
|
||||||
|
<circle cx="1" cy="1" r="1.5" style="fill: black"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch36" patternTransform="rotate(-45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="3" transform="rotate(-45 0 0)" style="stroke:black; stroke-width:1.5" />
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch37" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="0" y2="3" transform="rotate(-45 0 0)" style="stroke:black; stroke-width:1.5" />
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch38" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="4" y2="4" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch39" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="4" y2="4" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch40" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="3" y2="3" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="hatch41" patternTransform="rotate(45 0 0)" patternUnits="userSpaceOnUse" width="4" height="4">
|
||||||
|
<line x1="0" y1="0" x2="3" y2="3" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
<line x1="0" y1="0" x2="4" y2="0" style="stroke:black; stroke-width:1.5"/>
|
||||||
|
</pattern>
|
||||||
|
</g>
|
||||||
</defs>
|
</defs>
|
||||||
</svg>
|
</svg>
|
||||||
|
|
||||||
|
|
@ -4436,18 +4571,15 @@
|
||||||
<script src="modules/fonts.js"></script>
|
<script src="modules/fonts.js"></script>
|
||||||
<script src="modules/ui/layers.js"></script>
|
<script src="modules/ui/layers.js"></script>
|
||||||
<script src="modules/ui/measurers.js"></script>
|
<script src="modules/ui/measurers.js"></script>
|
||||||
|
<script src="modules/ui/stylePresets.js"></script>
|
||||||
<!-- <script src="libs/umami.js"></script> -->
|
<!-- <script src="libs/umami.js"></script> -->
|
||||||
|
|
||||||
<script defer src="https://unpkg.com/dropbox@10.8.0/dist/Dropbox-sdk.min.js"></script>
|
<script src="modules/ui/general.js"></script>
|
||||||
<script defer src="modules/ui/general.js"></script>
|
<script src="modules/ui/options.js"></script>
|
||||||
<script defer src="modules/ui/options.js"></script>
|
<script src="main.js"></script>
|
||||||
<script defer src="modules/ui/style.js"></script>
|
|
||||||
<script defer src="modules/load.js"></script>
|
|
||||||
<script defer src="modules/cloud.js"></script>
|
|
||||||
<script defer src="main.js"></script>
|
|
||||||
<script defer src="modules/save.js"></script>
|
|
||||||
<script defer src="modules/export.js"></script>
|
|
||||||
<script defer src="modules/relief-icons.js"></script>
|
<script defer src="modules/relief-icons.js"></script>
|
||||||
|
<script defer src="modules/ui/style.js"></script>
|
||||||
<script defer src="modules/ui/tools.js"></script>
|
<script defer src="modules/ui/tools.js"></script>
|
||||||
<script defer src="modules/ui/world-configurator.js"></script>
|
<script defer src="modules/ui/world-configurator.js"></script>
|
||||||
<script defer src="modules/ui/editors.js"></script>
|
<script defer src="modules/ui/editors.js"></script>
|
||||||
|
|
@ -4458,6 +4590,7 @@
|
||||||
<script defer src="modules/ui/cultures-editor.js"></script>
|
<script defer src="modules/ui/cultures-editor.js"></script>
|
||||||
<script defer src="modules/ui/namesbase-editor.js"></script>
|
<script defer src="modules/ui/namesbase-editor.js"></script>
|
||||||
<script defer src="modules/ui/elevation-profile.js"></script>
|
<script defer src="modules/ui/elevation-profile.js"></script>
|
||||||
|
<script defer src="modules/ui/temperature-graph.js"></script>
|
||||||
<script defer src="modules/ui/routes-editor.js"></script>
|
<script defer src="modules/ui/routes-editor.js"></script>
|
||||||
<script defer src="modules/ui/ice-editor.js"></script>
|
<script defer src="modules/ui/ice-editor.js"></script>
|
||||||
<script defer src="modules/ui/lakes-editor.js"></script>
|
<script defer src="modules/ui/lakes-editor.js"></script>
|
||||||
|
|
@ -4467,7 +4600,6 @@
|
||||||
<script defer src="modules/ui/rivers-creator.js"></script>
|
<script defer src="modules/ui/rivers-creator.js"></script>
|
||||||
<script defer src="modules/ui/relief-editor.js"></script>
|
<script defer src="modules/ui/relief-editor.js"></script>
|
||||||
<script defer src="modules/ui/religions-editor.js"></script>
|
<script defer src="modules/ui/religions-editor.js"></script>
|
||||||
<script defer src="modules/ui/markers-editor.js"></script>
|
|
||||||
<script defer src="modules/ui/burg-editor.js"></script>
|
<script defer src="modules/ui/burg-editor.js"></script>
|
||||||
<script defer src="modules/ui/units-editor.js"></script>
|
<script defer src="modules/ui/units-editor.js"></script>
|
||||||
<script defer src="modules/ui/notes-editor.js"></script>
|
<script defer src="modules/ui/notes-editor.js"></script>
|
||||||
|
|
@ -4480,14 +4612,23 @@
|
||||||
<script defer src="modules/ui/markers-overview.js"></script>
|
<script defer src="modules/ui/markers-overview.js"></script>
|
||||||
<script defer src="modules/ui/regiment-editor.js"></script>
|
<script defer src="modules/ui/regiment-editor.js"></script>
|
||||||
<script defer src="modules/ui/battle-screen.js"></script>
|
<script defer src="modules/ui/battle-screen.js"></script>
|
||||||
<script defer src="modules/coa-renderer.js"></script>
|
|
||||||
<script defer src="modules/ui/emblems-editor.js"></script>
|
<script defer src="modules/ui/emblems-editor.js"></script>
|
||||||
|
<script defer src="modules/ui/markers-editor.js"></script>
|
||||||
<script defer src="modules/ui/3d.js"></script>
|
<script defer src="modules/ui/3d.js"></script>
|
||||||
<script defer src="modules/ui/submap.js"></script>
|
<script defer src="modules/ui/submap.js"></script>
|
||||||
<script defer src="modules/ui/hotkeys.js"></script>
|
<script defer src="modules/ui/hotkeys.js"></script>
|
||||||
|
<script defer src="modules/coa-renderer.js"></script>
|
||||||
<script defer src="libs/rgbquant.min.js"></script>
|
<script defer src="libs/rgbquant.min.js"></script>
|
||||||
<script defer src="libs/jquery.ui.touch-punch.min.js"></script>
|
<script defer src="libs/jquery.ui.touch-punch.min.js"></script>
|
||||||
<script defer src="libs/pell.min.js"></script>
|
|
||||||
<script defer src="libs/jszip.min.js"></script>
|
<script defer src="libs/jszip.min.js"></script>
|
||||||
|
|
||||||
|
<script defer src="modules/io/save.js"></script>
|
||||||
|
<script defer src="modules/io/load.js"></script>
|
||||||
|
<script defer src="modules/io/cloud.js"></script>
|
||||||
|
<script defer src="modules/io/export.js"></script>
|
||||||
|
<script defer src="modules/io/export-json.js"></script>
|
||||||
|
|
||||||
|
<!-- Web Components -->
|
||||||
|
<script defer src="components/fill-box.js"></script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|
|
||||||
2
libs/pell.min.js
vendored
|
|
@ -1,2 +0,0 @@
|
||||||
// https://github.com/jaredreich/pell, MIT License
|
|
||||||
!function(e,t){"object"==typeof exports&&"undefined"!=typeof module?module.exports=t():"function"==typeof define&&define.amd?define(t):e.Pell=t()}(this,function(){"use strict";const e=(e,t,n)=>e.addEventListener(t,n),t=(e,t)=>e.appendChild(t),n=e=>document.createElement(e),i=e=>document.queryCommandState(e),o=(e,t=null)=>document.execCommand(e,!1,t),l={bold:{icon:"<b>B</b>",title:"Bold",state:()=>i("bold"),result:()=>o("bold")},italic:{icon:"<i>I</i>",title:"Italic",state:()=>i("italic"),result:()=>o("italic")},underline:{icon:"<u>U</u>",title:"Underline",state:()=>i("underline"),result:()=>o("underline")},strikethrough:{icon:"<strike>S</strike>",title:"Strike-through",state:()=>i("strikeThrough"),result:()=>o("strikeThrough")},heading1:{icon:"<b>H<sub>1</sub></b>",title:"Heading 1",result:()=>o("formatBlock","<h1>")},heading2:{icon:"<b>H<sub>2</sub></b>",title:"Heading 2",result:()=>o("formatBlock","<h2>")},paragraph:{icon:"¶",title:"Paragraph",result:()=>o("formatBlock","<p>")},quote:{icon:"“ ”",title:"Quote",result:()=>o("formatBlock","<blockquote>")},olist:{icon:"#",title:"Ordered List",result:()=>o("insertOrderedList")},ulist:{icon:"•",title:"Unordered List",result:()=>o("insertUnorderedList")},code:{icon:"</>",title:"Code",result:()=>o("formatBlock","<pre>")},line:{icon:"―",title:"Horizontal Line",result:()=>o("insertHorizontalRule")},link:{icon:"🔗",title:"Link",result:()=>navigator.clipboard.readText().then(e=>o("createLink",e))},image:{icon:"📷",title:"Image",result:()=>{navigator.clipboard.readText().then(e=>o("insertImage",e)),o("enableObjectResizing")}}},r={actionbar:"pell-actionbar",button:"pell-button",content:"pell-content",selected:"pell-button-selected"};return{exec:o,init:i=>{const a=i.actions?i.actions.map(e=>"string"==typeof e?l[e]:l[e.name]?{...l[e.name],...e}:e):Object.keys(l).map(e=>l[e]),s={...r,...i.classes},c=i.defaultParagraphSeparator||"div",u=n("div");u.className=s.actionbar,t(i.element,u);const d=i.element.content=n("div");return d.contentEditable=!0,d.className=s.content,d.oninput=(({target:{firstChild:e}})=>{e&&3===e.nodeType?o("formatBlock",`<${c}>`):"<br>"===d.innerHTML&&(d.innerHTML=""),i.onChange(d.innerHTML)}),d.onkeydown=(e=>{"Enter"===e.key&&"blockquote"===(e=>document.queryCommandValue(e))("formatBlock")&&setTimeout(()=>o("formatBlock",`<${c}>`),0)}),t(i.element,d),a.forEach(i=>{const o=n("button");if(o.className=s.button,o.innerHTML=i.icon,o.title=i.title,o.setAttribute("type","button"),o.onclick=(()=>i.result()&&d.focus()),i.state){const t=()=>o.classList[i.state()?"add":"remove"](s.selected);e(d,"keyup",t),e(d,"mouseup",t),e(o,"click",t)}t(u,o)}),i.styleWithCSS&&o("styleWithCSS"),o("defaultParagraphSeparator",c),i.element}}});
|
|
||||||
159
main.js
|
|
@ -1,11 +1,11 @@
|
||||||
// Azgaar (azgaar.fmg@yandex.com). Minsk, 2017-2021. MIT License
|
// Azgaar (azgaar.fmg@yandex.com). Minsk, 2017-2022. MIT License
|
||||||
// https://github.com/Azgaar/Fantasy-Map-Generator
|
// https://github.com/Azgaar/Fantasy-Map-Generator
|
||||||
|
|
||||||
"use strict";
|
"use strict";
|
||||||
const version = "1.71"; // generator version
|
const version = "1.732"; // generator version
|
||||||
document.title += " v" + version;
|
document.title += " v" + version;
|
||||||
|
|
||||||
// Switches to disable/enable logging features
|
// switches to disable/enable logging features
|
||||||
const PRODUCTION = location.hostname && location.hostname !== "localhost" && location.hostname !== "127.0.0.1";
|
const PRODUCTION = location.hostname && location.hostname !== "localhost" && location.hostname !== "127.0.0.1";
|
||||||
const DEBUG = localStorage.getItem("debug");
|
const DEBUG = localStorage.getItem("debug");
|
||||||
const INFO = DEBUG || !PRODUCTION;
|
const INFO = DEBUG || !PRODUCTION;
|
||||||
|
|
@ -173,14 +173,46 @@ landmass.append("rect").attr("x", 0).attr("y", 0).attr("width", graphWidth).attr
|
||||||
oceanPattern.append("rect").attr("fill", "url(#oceanic)").attr("x", 0).attr("y", 0).attr("width", graphWidth).attr("height", graphHeight);
|
oceanPattern.append("rect").attr("fill", "url(#oceanic)").attr("x", 0).attr("y", 0).attr("width", graphWidth).attr("height", graphHeight);
|
||||||
oceanLayers.append("rect").attr("id", "oceanBase").attr("x", 0).attr("y", 0).attr("width", graphWidth).attr("height", graphHeight);
|
oceanLayers.append("rect").attr("id", "oceanBase").attr("x", 0).attr("y", 0).attr("width", graphWidth).attr("height", graphHeight);
|
||||||
|
|
||||||
// remove loading screen
|
if (!location.hostname) {
|
||||||
d3.select("#loading").transition().duration(4000).style("opacity", 0).remove();
|
const wiki = "https://github.com/Azgaar/Fantasy-Map-Generator/wiki/Run-FMG-locally";
|
||||||
d3.select("#initial").transition().duration(4000).attr("opacity", 0).remove();
|
alertMessage.innerHTML = `Fantasy Map Generator cannot run serverless.
|
||||||
|
Follow the <a href="${wiki}" target="_blank">instructions</a> on how you can easily run a local web-server`;
|
||||||
|
|
||||||
|
$("#alert").dialog({
|
||||||
|
resizable: false,
|
||||||
|
title: "Loading error",
|
||||||
|
width: "28em",
|
||||||
|
position: {my: "center center-4em", at: "center", of: "svg"},
|
||||||
|
buttons: {
|
||||||
|
OK: function () {
|
||||||
|
$(this).dialog("close");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
d3.select("#loading-text").transition().duration(1000).style("opacity", 0);
|
||||||
|
d3.select("#init-rose").transition().duration(4000).style("opacity", 0);
|
||||||
|
} else {
|
||||||
|
hideLoading();
|
||||||
|
checkLoadParameters();
|
||||||
|
}
|
||||||
|
|
||||||
|
function hideLoading() {
|
||||||
|
d3.select("#loading").transition().duration(4000).style("opacity", 0);
|
||||||
|
d3.select("#initial").transition().duration(4000).attr("opacity", 0);
|
||||||
d3.select("#optionsContainer").transition().duration(3000).style("opacity", 1);
|
d3.select("#optionsContainer").transition().duration(3000).style("opacity", 1);
|
||||||
d3.select("#tooltip").transition().duration(4000).style("opacity", 1);
|
d3.select("#tooltip").transition().duration(4000).style("opacity", 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
function showLoading() {
|
||||||
|
d3.select("#loading").transition().duration(200).style("opacity", 1);
|
||||||
|
d3.select("#initial").transition().duration(200).attr("opacity", 1);
|
||||||
|
d3.select("#optionsContainer").transition().duration(100).style("opacity", 0);
|
||||||
|
d3.select("#tooltip").transition().duration(200).style("opacity", 0);
|
||||||
|
}
|
||||||
|
|
||||||
// decide which map should be loaded or generated on page load
|
// decide which map should be loaded or generated on page load
|
||||||
void (function checkLoadParameters() {
|
function checkLoadParameters() {
|
||||||
const url = new URL(window.location.href);
|
const url = new URL(window.location.href);
|
||||||
const params = url.searchParams;
|
const params = url.searchParams;
|
||||||
|
|
||||||
|
|
@ -191,7 +223,9 @@ void (function checkLoadParameters() {
|
||||||
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);
|
||||||
if (valid) {
|
if (valid) {
|
||||||
|
setTimeout(() => {
|
||||||
loadMapFromURL(maplink, 1);
|
loadMapFromURL(maplink, 1);
|
||||||
|
}, 1000);
|
||||||
return;
|
return;
|
||||||
} else showUploadErrorMessage("Map link is not a valid URL", maplink);
|
} else showUploadErrorMessage("Map link is not a valid URL", maplink);
|
||||||
}
|
}
|
||||||
|
|
@ -225,11 +259,11 @@ void (function checkLoadParameters() {
|
||||||
|
|
||||||
WARN && console.warn("Generate random map");
|
WARN && console.warn("Generate random map");
|
||||||
generateMapOnLoad();
|
generateMapOnLoad();
|
||||||
})();
|
}
|
||||||
|
|
||||||
function generateMapOnLoad() {
|
async function generateMapOnLoad() {
|
||||||
applyStyleOnLoad(); // apply default or previously selected style
|
await applyStyleOnLoad(); // apply previously selected default or custom style
|
||||||
generate(); // generate map
|
await generate(); // generate map
|
||||||
focusOn(); // based on searchParams focus on point, cell or burg from MFCG
|
focusOn(); // based on searchParams focus on point, cell or burg from MFCG
|
||||||
applyPreset(); // apply saved layers preset
|
applyPreset(); // apply saved layers preset
|
||||||
}
|
}
|
||||||
|
|
@ -410,22 +444,22 @@ function showWelcomeMessage() {
|
||||||
const discord = link("https://discordapp.com/invite/X7E84HU", "Discord server");
|
const discord = link("https://discordapp.com/invite/X7E84HU", "Discord server");
|
||||||
const patreon = link("https://www.patreon.com/azgaar", "Patreon");
|
const patreon = link("https://www.patreon.com/azgaar", "Patreon");
|
||||||
|
|
||||||
alertMessage.innerHTML = `The Fantasy Map Generator is updated up to version <b>${version}</b>.
|
alertMessage.innerHTML = `The Fantasy Map Generator is updated up to version <strong>${version}</strong>.
|
||||||
This version is compatible with ${changelog}, loaded <i>.map</i> files will be auto-updated.
|
This version is compatible with ${changelog}, loaded <i>.map</i> files will be auto-updated.
|
||||||
<ul>Main changes:
|
<ul><strong>Latest changes:</strong>
|
||||||
<li>Ability to limit military units by biome, state, culture and religion</li>
|
<li>Pre-defined heightmaps</li>
|
||||||
<li>New marker types</li>
|
<li>Advanced notes editor</li>
|
||||||
<li>New markers editor</li>
|
<li>Zones editor: filter by type</li>
|
||||||
<li>Markers overview screen</li>
|
<li>Color picker: new hatchings</li>
|
||||||
<li>Markers regeneration menu</li>
|
<li>New style presets: Cyberpunk and Atlas</li>
|
||||||
<li>Burg editor update</li>
|
<li>Burg temperature graph</li>
|
||||||
<li>Editable theme color</li>
|
<li>4 new textures</li>
|
||||||
<li>Add font dialog</li>
|
<li>Province capture logic rework</li>
|
||||||
<li>Save to Dropbox</li>
|
<li>Button to release all provinces</li>
|
||||||
</ul>
|
</ul>
|
||||||
|
|
||||||
<p>Join our ${discord} and ${reddit} to ask questions, share maps, discuss the Generator and Worlbuilding, report bugs and propose new features.</p>
|
<p>Join our ${discord} and ${reddit} to ask questions, share maps, discuss the Generator and Worlbuilding, report bugs and propose new features.</p>
|
||||||
<span>Thanks for all supporters on <a href="https://www.patreon.com/azgaar" target="_blank">Patreon</a>!</i></span>`;
|
<span><i>Thanks for all supporters on ${patreon}!</i></span>`;
|
||||||
|
|
||||||
$("#alert").dialog({
|
$("#alert").dialog({
|
||||||
resizable: false,
|
resizable: false,
|
||||||
|
|
@ -448,7 +482,7 @@ function doWorkOnZoom(isScaleChanged, isPositionChanged) {
|
||||||
|
|
||||||
if (isScaleChanged) {
|
if (isScaleChanged) {
|
||||||
invokeActiveZooming();
|
invokeActiveZooming();
|
||||||
drawScaleBar();
|
drawScaleBar(scale);
|
||||||
}
|
}
|
||||||
|
|
||||||
// zoom image converter overlay
|
// zoom image converter overlay
|
||||||
|
|
@ -609,7 +643,7 @@ void (function addDragToUpload() {
|
||||||
});
|
});
|
||||||
})();
|
})();
|
||||||
|
|
||||||
function generate() {
|
async function generate() {
|
||||||
try {
|
try {
|
||||||
const timeStart = performance.now();
|
const timeStart = performance.now();
|
||||||
invokeActiveZooming();
|
invokeActiveZooming();
|
||||||
|
|
@ -619,8 +653,8 @@ function generate() {
|
||||||
randomizeOptions();
|
randomizeOptions();
|
||||||
placePoints();
|
placePoints();
|
||||||
calculateVoronoi(grid, grid.points);
|
calculateVoronoi(grid, grid.points);
|
||||||
drawScaleBar();
|
drawScaleBar(scale);
|
||||||
HeightmapGenerator.generate();
|
await HeightmapGenerator.generate();
|
||||||
markFeatures();
|
markFeatures();
|
||||||
markupGridOcean();
|
markupGridOcean();
|
||||||
addLakesInDeepDepressions();
|
addLakesInDeepDepressions();
|
||||||
|
|
@ -907,6 +941,31 @@ function defineMapSize() {
|
||||||
|
|
||||||
function getSizeAndLatitude() {
|
function getSizeAndLatitude() {
|
||||||
const template = document.getElementById("templateInput").value; // heightmap template
|
const template = document.getElementById("templateInput").value; // heightmap template
|
||||||
|
|
||||||
|
if (template === "africa-centric") return [45, 53];
|
||||||
|
if (template === "arabia") return [20, 35];
|
||||||
|
if (template === "atlantics") return [42, 23];
|
||||||
|
if (template === "britain") return [7, 20];
|
||||||
|
if (template === "caribbean") return [15, 40];
|
||||||
|
if (template === "east-asia") return [11, 28];
|
||||||
|
if (template === "eurasia") return [38, 19];
|
||||||
|
if (template === "europe") return [20, 16];
|
||||||
|
if (template === "europe-accented") return [14, 22];
|
||||||
|
if (template === "europe-and-central-asia") return [25, 10];
|
||||||
|
if (template === "europe-central") return [11, 22];
|
||||||
|
if (template === "europe-north") return [7, 18];
|
||||||
|
if (template === "greenland") return [22, 7];
|
||||||
|
if (template === "hellenica") return [8, 27];
|
||||||
|
if (template === "iceland") return [2, 15];
|
||||||
|
if (template === "indian-ocean") return [45, 55];
|
||||||
|
if (template === "mediterranean-sea") return [10, 29];
|
||||||
|
if (template === "middle-east") return [8, 31];
|
||||||
|
if (template === "north-america") return [37, 17];
|
||||||
|
if (template === "us-centric") return [66, 27];
|
||||||
|
if (template === "us-mainland") return [16, 30];
|
||||||
|
if (template === "world") return [78, 27];
|
||||||
|
if (template === "world-from-pacific") return [75, 32];
|
||||||
|
|
||||||
const part = grid.features.some(f => f.land && f.border); // if land goes over map borders
|
const part = grid.features.some(f => f.land && f.border); // if land goes over map borders
|
||||||
const max = part ? 80 : 100; // max size
|
const max = part ? 80 : 100; // max size
|
||||||
const lat = () => gauss(P(0.5) ? 40 : 60, 15, 25, 75); // latitude shift
|
const lat = () => gauss(P(0.5) ? 40 : 60, 15, 25, 75); // latitude shift
|
||||||
|
|
@ -1485,14 +1544,12 @@ function rankCells() {
|
||||||
TIME && console.timeEnd("rankCells");
|
TIME && console.timeEnd("rankCells");
|
||||||
}
|
}
|
||||||
|
|
||||||
// regenerate some zones
|
// generate zones
|
||||||
function addZones(number = 1) {
|
function addZones(number = 1) {
|
||||||
TIME && console.time("addZones");
|
TIME && console.time("addZones");
|
||||||
const data = [],
|
const {cells, states, burgs} = pack;
|
||||||
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
|
||||||
|
const zonesData = [];
|
||||||
|
|
||||||
for (let i = 0; i < rn(Math.random() * 1.8 * number); i++) addInvasion(); // invasion of enemy lands
|
for (let i = 0; i < rn(Math.random() * 1.8 * number); i++) addInvasion(); // invasion of enemy lands
|
||||||
for (let i = 0; i < rn(Math.random() * 1.6 * number); i++) addRebels(); // rebels along a state border
|
for (let i = 0; i < rn(Math.random() * 1.6 * number); i++) addRebels(); // rebels along a state border
|
||||||
|
|
@ -1506,6 +1563,8 @@ function addZones(number = 1) {
|
||||||
for (let i = 0; i < rn(Math.random() * 1.4 * number); i++) addFlood(); // flood on river banks
|
for (let i = 0; i < rn(Math.random() * 1.4 * number); i++) addFlood(); // flood on river banks
|
||||||
for (let i = 0; i < rn(Math.random() * 1.2 * number); i++) addTsunami(); // tsunami starting near coast
|
for (let i = 0; i < rn(Math.random() * 1.2 * number); i++) addTsunami(); // tsunami starting near coast
|
||||||
|
|
||||||
|
drawZones();
|
||||||
|
|
||||||
function addInvasion() {
|
function addInvasion() {
|
||||||
const atWar = states.filter(s => s.diplomacy && s.diplomacy.some(d => d === "Enemy"));
|
const atWar = states.filter(s => s.diplomacy && s.diplomacy.some(d => d === "Enemy"));
|
||||||
if (!atWar.length) return;
|
if (!atWar.length) return;
|
||||||
|
|
@ -1546,7 +1605,7 @@ function addZones(number = 1) {
|
||||||
Intervention: 1
|
Intervention: 1
|
||||||
});
|
});
|
||||||
const name = getAdjective(invader.name) + " " + invasion;
|
const name = getAdjective(invader.name) + " " + invasion;
|
||||||
data.push({name, type: "Invasion", cells: cellsArray, fill: "url(#hatch1)"});
|
zonesData.push({name, type: "Invasion", cells: cellsArray, fill: "url(#hatch1)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addRebels() {
|
function addRebels() {
|
||||||
|
|
@ -1582,7 +1641,7 @@ function addZones(number = 1) {
|
||||||
|
|
||||||
const rebels = rw({Rebels: 5, Insurgents: 2, Mutineers: 1, Rioters: 1, Separatists: 1, Secessionists: 1, Insurrection: 2, Rebellion: 1, Conspiracy: 2});
|
const rebels = rw({Rebels: 5, Insurgents: 2, Mutineers: 1, Rioters: 1, Separatists: 1, Secessionists: 1, Insurrection: 2, Rebellion: 1, Conspiracy: 2});
|
||||||
const name = getAdjective(states[neib].name) + " " + rebels;
|
const name = getAdjective(states[neib].name) + " " + rebels;
|
||||||
data.push({name, type: "Rebels", cells: cellsArray, fill: "url(#hatch3)"});
|
zonesData.push({name, type: "Rebels", cells: cellsArray, fill: "url(#hatch3)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addProselytism() {
|
function addProselytism() {
|
||||||
|
|
@ -1612,7 +1671,7 @@ function addZones(number = 1) {
|
||||||
}
|
}
|
||||||
|
|
||||||
const name = getAdjective(organized.name.split(" ")[0]) + " Proselytism";
|
const name = getAdjective(organized.name.split(" ")[0]) + " Proselytism";
|
||||||
data.push({name, type: "Proselytism", cells: cellsArray, fill: "url(#hatch6)"});
|
zonesData.push({name, type: "Proselytism", cells: cellsArray, fill: "url(#hatch6)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addCrusade() {
|
function addCrusade() {
|
||||||
|
|
@ -1624,7 +1683,7 @@ function addZones(number = 1) {
|
||||||
cellsArray.forEach(i => (used[i] = 1));
|
cellsArray.forEach(i => (used[i] = 1));
|
||||||
|
|
||||||
const name = getAdjective(heresy.name.split(" ")[0]) + " Crusade";
|
const name = getAdjective(heresy.name.split(" ")[0]) + " Crusade";
|
||||||
data.push({name, type: "Crusade", cells: cellsArray, fill: "url(#hatch6)"});
|
zonesData.push({name, type: "Crusade", cells: cellsArray, fill: "url(#hatch6)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addDisease() {
|
function addDisease() {
|
||||||
|
|
@ -1661,7 +1720,7 @@ function addZones(number = 1) {
|
||||||
|
|
||||||
const type = rw({Fever: 5, Pestilence: 2, Flu: 2, Pox: 2, Smallpox: 2, Plague: 4, Cholera: 2, Dropsy: 1, Leprosy: 2});
|
const type = rw({Fever: 5, Pestilence: 2, Flu: 2, Pox: 2, Smallpox: 2, Plague: 4, Cholera: 2, Dropsy: 1, Leprosy: 2});
|
||||||
const name = rw({[color()]: 4, [animal()]: 2, [adjective()]: 1}) + " " + type;
|
const name = rw({[color()]: 4, [animal()]: 2, [adjective()]: 1}) + " " + type;
|
||||||
data.push({name, type: "Disease", cells: cellsArray, fill: "url(#hatch12)"});
|
zonesData.push({name, type: "Disease", cells: cellsArray, fill: "url(#hatch12)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addDisaster() {
|
function addDisaster() {
|
||||||
|
|
@ -1693,7 +1752,7 @@ function addZones(number = 1) {
|
||||||
|
|
||||||
const type = rw({Famine: 5, Dearth: 1, Drought: 3, Earthquake: 3, Tornadoes: 1, Wildfires: 1});
|
const type = rw({Famine: 5, Dearth: 1, Drought: 3, Earthquake: 3, Tornadoes: 1, Wildfires: 1});
|
||||||
const name = getAdjective(burg.name) + " " + type;
|
const name = getAdjective(burg.name) + " " + type;
|
||||||
data.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch5)"});
|
zonesData.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch5)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addEruption() {
|
function addEruption() {
|
||||||
|
|
@ -1724,7 +1783,7 @@ function addZones(number = 1) {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
data.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch7)"});
|
zonesData.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch7)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addAvalanche() {
|
function addAvalanche() {
|
||||||
|
|
@ -1749,7 +1808,7 @@ function addZones(number = 1) {
|
||||||
|
|
||||||
const proper = getAdjective(Names.getCultureShort(cells.culture[cell]));
|
const proper = getAdjective(Names.getCultureShort(cells.culture[cell]));
|
||||||
const name = proper + " Avalanche";
|
const name = proper + " Avalanche";
|
||||||
data.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch5)"});
|
zonesData.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch5)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addFault() {
|
function addFault() {
|
||||||
|
|
@ -1774,7 +1833,7 @@ function addZones(number = 1) {
|
||||||
|
|
||||||
const proper = getAdjective(Names.getCultureShort(cells.culture[cell]));
|
const proper = getAdjective(Names.getCultureShort(cells.culture[cell]));
|
||||||
const name = proper + " Fault";
|
const name = proper + " Fault";
|
||||||
data.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch2)"});
|
zonesData.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch2)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addFlood() {
|
function addFlood() {
|
||||||
|
|
@ -1804,7 +1863,7 @@ function addZones(number = 1) {
|
||||||
}
|
}
|
||||||
|
|
||||||
const name = getAdjective(burgs[cells.burg[cell]].name) + " Flood";
|
const name = getAdjective(burgs[cells.burg[cell]].name) + " Flood";
|
||||||
data.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch13)"});
|
zonesData.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch13)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
function addTsunami() {
|
function addTsunami() {
|
||||||
|
|
@ -1832,13 +1891,13 @@ function addZones(number = 1) {
|
||||||
|
|
||||||
const proper = getAdjective(Names.getCultureShort(cells.culture[cell]));
|
const proper = getAdjective(Names.getCultureShort(cells.culture[cell]));
|
||||||
const name = proper + " Tsunami";
|
const name = proper + " Tsunami";
|
||||||
data.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch13)"});
|
zonesData.push({name, type: "Disaster", cells: cellsArray, fill: "url(#hatch13)"});
|
||||||
}
|
}
|
||||||
|
|
||||||
void (function drawZones() {
|
function drawZones() {
|
||||||
zones
|
zones
|
||||||
.selectAll("g")
|
.selectAll("g")
|
||||||
.data(data)
|
.data(zonesData)
|
||||||
.enter()
|
.enter()
|
||||||
.append("g")
|
.append("g")
|
||||||
.attr("id", (d, i) => "zone" + i)
|
.attr("id", (d, i) => "zone" + i)
|
||||||
|
|
@ -1854,7 +1913,7 @@ function addZones(number = 1) {
|
||||||
.attr("id", function (d) {
|
.attr("id", function (d) {
|
||||||
return this.parentNode.id + "_" + d;
|
return this.parentNode.id + "_" + d;
|
||||||
});
|
});
|
||||||
})();
|
}
|
||||||
|
|
||||||
TIME && console.timeEnd("addZones");
|
TIME && console.timeEnd("addZones");
|
||||||
}
|
}
|
||||||
|
|
@ -1881,16 +1940,18 @@ function showStatistics() {
|
||||||
INFO && console.log(stats);
|
INFO && console.log(stats);
|
||||||
}
|
}
|
||||||
|
|
||||||
const regenerateMap = debounce(function () {
|
const regenerateMap = debounce(async function () {
|
||||||
WARN && console.warn("Generate new random map");
|
WARN && console.warn("Generate new random map");
|
||||||
|
showLoading();
|
||||||
closeDialogs("#worldConfigurator, #options3d");
|
closeDialogs("#worldConfigurator, #options3d");
|
||||||
customization = 0;
|
customization = 0;
|
||||||
undraw();
|
|
||||||
resetZoom(1000);
|
resetZoom(1000);
|
||||||
generate();
|
undraw();
|
||||||
|
await generate();
|
||||||
restoreLayers();
|
restoreLayers();
|
||||||
if (ThreeD.options.isOn) ThreeD.redraw();
|
if (ThreeD.options.isOn) ThreeD.redraw();
|
||||||
if ($("#worldConfigurator").is(":visible")) editWorld();
|
if ($("#worldConfigurator").is(":visible")) editWorld();
|
||||||
|
hideLoading();
|
||||||
}, 1000);
|
}, 1000);
|
||||||
|
|
||||||
// clear the map
|
// clear the map
|
||||||
|
|
|
||||||
|
|
@ -595,7 +595,7 @@ window.BurgsAndStates = (function () {
|
||||||
g.select("#stateLabel" + id).remove();
|
g.select("#stateLabel" + id).remove();
|
||||||
}
|
}
|
||||||
|
|
||||||
const path = p[1].length > 1 ? lineGen(p[1]) : `M${p[1][0][0] - 50},${p[1][0][1]}h${100}`;
|
const path = p[1].length > 1 ? round(lineGen(p[1])) : `M${p[1][0][0] - 50},${p[1][0][1]}h${100}`;
|
||||||
const textPath = t
|
const textPath = t
|
||||||
.append("path")
|
.append("path")
|
||||||
.attr("d", path)
|
.attr("d", path)
|
||||||
|
|
@ -621,7 +621,7 @@ window.BurgsAndStates = (function () {
|
||||||
const spans = lines.map((l, d) => {
|
const spans = lines.map((l, d) => {
|
||||||
example.text(l);
|
example.text(l);
|
||||||
const left = example.node().getBBox().width / -2; // x offset
|
const left = example.node().getBBox().width / -2; // x offset
|
||||||
return `<tspan x="${left}px" dy="${d ? 1 : top}em">${l}</tspan>`;
|
return `<tspan x=${rn(left, 1)} dy="${d ? 1 : top}em">${l}</tspan>`;
|
||||||
});
|
});
|
||||||
|
|
||||||
const el = g
|
const el = g
|
||||||
|
|
|
||||||
|
|
@ -976,7 +976,7 @@ window.COA = (function () {
|
||||||
|
|
||||||
if (emblemShape.value === "state" && state && pack.states[state].coa) return pack.states[state].coa.shield;
|
if (emblemShape.value === "state" && state && pack.states[state].coa) return pack.states[state].coa.shield;
|
||||||
if (pack.cultures[culture].shield) return pack.cultures[culture].shield;
|
if (pack.cultures[culture].shield) return pack.cultures[culture].shield;
|
||||||
console.error("Shield shape is not defined on culture level", pack.cultures[culture]);
|
ERROR && console.error("Shield shape is not defined on culture level", pack.cultures[culture]);
|
||||||
return "heater";
|
return "heater";
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1938,7 +1938,9 @@ window.COArenderer = (function () {
|
||||||
g.setAttribute("id", charge + "_" + id);
|
g.setAttribute("id", charge + "_" + id);
|
||||||
return g.outerHTML;
|
return g.outerHTML;
|
||||||
})
|
})
|
||||||
.catch(err => console.error(err));
|
.catch(err => {
|
||||||
|
ERROR && console.error(err);
|
||||||
|
});
|
||||||
return fetched;
|
return fetched;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -14,12 +14,14 @@ const fonts = [
|
||||||
{
|
{
|
||||||
family: "Almendra SC",
|
family: "Almendra SC",
|
||||||
src: "url(https://fonts.gstatic.com/s/almendrasc/v13/Iure6Yx284eebowr7hbyTaZOrLQ.woff2)",
|
src: "url(https://fonts.gstatic.com/s/almendrasc/v13/Iure6Yx284eebowr7hbyTaZOrLQ.woff2)",
|
||||||
unicodeRange: "U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
unicodeRange:
|
||||||
|
"U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
family: "Amatic SC",
|
family: "Amatic SC",
|
||||||
src: "url(https://fonts.gstatic.com/s/amaticsc/v11/TUZ3zwprpvBS1izr_vOMscGKfrUC.woff2)",
|
src: "url(https://fonts.gstatic.com/s/amaticsc/v11/TUZ3zwprpvBS1izr_vOMscGKfrUC.woff2)",
|
||||||
unicodeRange: "U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
unicodeRange:
|
||||||
|
"U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
family: "Architects Daughter",
|
family: "Architects Daughter",
|
||||||
|
|
@ -34,7 +36,8 @@ const fonts = [
|
||||||
{
|
{
|
||||||
family: "Caesar Dressing",
|
family: "Caesar Dressing",
|
||||||
src: "url(https://fonts.gstatic.com/s/caesardressing/v6/yYLx0hLa3vawqtwdswbotmK4vrRHdrz7.woff2)",
|
src: "url(https://fonts.gstatic.com/s/caesardressing/v6/yYLx0hLa3vawqtwdswbotmK4vrRHdrz7.woff2)",
|
||||||
unicodeRange: "U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
unicodeRange:
|
||||||
|
"U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
family: "Cinzel",
|
family: "Cinzel",
|
||||||
|
|
@ -49,7 +52,8 @@ const fonts = [
|
||||||
{
|
{
|
||||||
family: "Fredericka the Great",
|
family: "Fredericka the Great",
|
||||||
src: "url(https://fonts.gstatic.com/s/frederickathegreat/v6/9Bt33CxNwt7aOctW2xjbCstzwVKsIBVV--Sjxbc.woff2)",
|
src: "url(https://fonts.gstatic.com/s/frederickathegreat/v6/9Bt33CxNwt7aOctW2xjbCstzwVKsIBVV--Sjxbc.woff2)",
|
||||||
unicodeRange: "U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
unicodeRange:
|
||||||
|
"U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
family: "Gloria Hallelujah",
|
family: "Gloria Hallelujah",
|
||||||
|
|
@ -74,12 +78,14 @@ const fonts = [
|
||||||
{
|
{
|
||||||
family: "MedievalSharp",
|
family: "MedievalSharp",
|
||||||
src: "url(https://fonts.gstatic.com/s/medievalsharp/v9/EvOJzAlL3oU5AQl2mP5KdgptMqhwMg.woff2)",
|
src: "url(https://fonts.gstatic.com/s/medievalsharp/v9/EvOJzAlL3oU5AQl2mP5KdgptMqhwMg.woff2)",
|
||||||
unicodeRange: "U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
unicodeRange:
|
||||||
|
"U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
family: "Metamorphous",
|
family: "Metamorphous",
|
||||||
src: "url(https://fonts.gstatic.com/s/metamorphous/v7/Wnz8HA03aAXcC39ZEX5y133EOyqs.woff2)",
|
src: "url(https://fonts.gstatic.com/s/metamorphous/v7/Wnz8HA03aAXcC39ZEX5y133EOyqs.woff2)",
|
||||||
unicodeRange: "U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
unicodeRange:
|
||||||
|
"U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
family: "Montez",
|
family: "Montez",
|
||||||
|
|
@ -89,7 +95,8 @@ const fonts = [
|
||||||
{
|
{
|
||||||
family: "Nova Script",
|
family: "Nova Script",
|
||||||
src: "url(https://fonts.gstatic.com/s/novascript/v10/7Au7p_IpkSWSTWaFWkumvlQKGFw.woff2)",
|
src: "url(https://fonts.gstatic.com/s/novascript/v10/7Au7p_IpkSWSTWaFWkumvlQKGFw.woff2)",
|
||||||
unicodeRange: "U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
unicodeRange:
|
||||||
|
"U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
family: "Orbitron",
|
family: "Orbitron",
|
||||||
|
|
@ -109,12 +116,14 @@ const fonts = [
|
||||||
{
|
{
|
||||||
family: "Uncial Antiqua",
|
family: "Uncial Antiqua",
|
||||||
src: "url(https://fonts.gstatic.com/s/uncialantiqua/v5/N0bM2S5WOex4OUbESzoESK-i-MfWQZQ.woff2)",
|
src: "url(https://fonts.gstatic.com/s/uncialantiqua/v5/N0bM2S5WOex4OUbESzoESK-i-MfWQZQ.woff2)",
|
||||||
unicodeRange: "U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
unicodeRange:
|
||||||
|
"U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
family: "Underdog",
|
family: "Underdog",
|
||||||
src: "url(https://fonts.gstatic.com/s/underdog/v6/CHygV-jCElj7diMroWSlWV8.woff2)",
|
src: "url(https://fonts.gstatic.com/s/underdog/v6/CHygV-jCElj7diMroWSlWV8.woff2)",
|
||||||
unicodeRange: "U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
unicodeRange:
|
||||||
|
"U+0000-00FF, U+0131, U+0152-0153, U+02BB-02BC, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2122, U+2191, U+2193, U+2212, U+2215, U+FEFF, U+FFFD"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
family: "Yellowtail",
|
family: "Yellowtail",
|
||||||
|
|
@ -243,7 +252,7 @@ async function addGoogleFont(family) {
|
||||||
})
|
})
|
||||||
.catch(err => {
|
.catch(err => {
|
||||||
tip(`Failed to load Google font ${family}`, true, "error", 4000);
|
tip(`Failed to load Google font ${family}`, true, "error", 4000);
|
||||||
console.error(err);
|
ERROR && console.error(err);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -3,13 +3,44 @@
|
||||||
window.HeightmapGenerator = (function () {
|
window.HeightmapGenerator = (function () {
|
||||||
let cells, p;
|
let cells, p;
|
||||||
|
|
||||||
const generate = function () {
|
const generate = async function () {
|
||||||
TIME && console.time("generateHeightmap");
|
|
||||||
cells = grid.cells;
|
cells = grid.cells;
|
||||||
p = grid.points;
|
p = grid.points;
|
||||||
cells.h = new Uint8Array(grid.points.length);
|
cells.h = new Uint8Array(grid.points.length);
|
||||||
|
|
||||||
const template = document.getElementById("templateInput").value;
|
const input = document.getElementById("templateInput");
|
||||||
|
const selectedId = input.selectedIndex >= 0 ? input.selectedIndex : 0;
|
||||||
|
const type = input.options[selectedId]?.parentElement?.label;
|
||||||
|
|
||||||
|
if (type === "Specific") {
|
||||||
|
// pre-defined heightmap
|
||||||
|
TIME && console.time("defineHeightmap");
|
||||||
|
return new Promise(resolve => {
|
||||||
|
// create canvas where 1px correcponds to a cell
|
||||||
|
const canvas = document.createElement("canvas");
|
||||||
|
const ctx = canvas.getContext("2d");
|
||||||
|
const {cellsX, cellsY} = grid;
|
||||||
|
canvas.width = cellsX;
|
||||||
|
canvas.height = cellsY;
|
||||||
|
|
||||||
|
// load heightmap into image and render to canvas
|
||||||
|
const img = new Image();
|
||||||
|
img.src = `./heightmaps/${input.value}.png`;
|
||||||
|
img.onload = function () {
|
||||||
|
ctx.drawImage(img, 0, 0, cellsX, cellsY);
|
||||||
|
const imageData = ctx.getImageData(0, 0, cellsX, cellsY);
|
||||||
|
assignColorsToHeight(imageData.data);
|
||||||
|
canvas.remove();
|
||||||
|
img.remove();
|
||||||
|
TIME && console.timeEnd("defineHeightmap");
|
||||||
|
resolve();
|
||||||
|
};
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// heightmap template
|
||||||
|
TIME && console.time("generateHeightmap");
|
||||||
|
const template = input.value;
|
||||||
const templateString = HeightmapTemplates[template];
|
const templateString = HeightmapTemplates[template];
|
||||||
const steps = templateString.split("\n");
|
const steps = templateString.split("\n");
|
||||||
|
|
||||||
|
|
@ -79,8 +110,8 @@ window.HeightmapGenerator = (function () {
|
||||||
|
|
||||||
function addOneHill() {
|
function addOneHill() {
|
||||||
const change = new Uint8Array(cells.h.length);
|
const change = new Uint8Array(cells.h.length);
|
||||||
let limit = 0,
|
let limit = 0;
|
||||||
start;
|
let start;
|
||||||
let h = lim(getNumberInRange(height));
|
let h = lim(getNumberInRange(height));
|
||||||
|
|
||||||
do {
|
do {
|
||||||
|
|
@ -410,5 +441,13 @@ window.HeightmapGenerator = (function () {
|
||||||
return rand(min * length, max * length);
|
return rand(min * length, max * length);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function assignColorsToHeight(imageData) {
|
||||||
|
for (let i = 0; i < cells.i.length; i++) {
|
||||||
|
const lightness = imageData[i * 4] / 255;
|
||||||
|
const powered = lightness < 0.2 ? lightness : 0.2 + (lightness - 0.2) ** 0.8;
|
||||||
|
cells.h[i] = minmax(Math.floor(powered * 100), 0, 100);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return {generate, addHill, addRange, addTrough, addStrait, addPit, smooth, modify};
|
return {generate, addHill, addRange, addTrough, addStrait, addPit, smooth, modify};
|
||||||
})();
|
})();
|
||||||
|
|
|
||||||
523
modules/io/auto-update.js
Normal file
|
|
@ -0,0 +1,523 @@
|
||||||
|
"use strict";
|
||||||
|
|
||||||
|
// update old .map version to the current one
|
||||||
|
export function resolveVersionConflicts(version) {
|
||||||
|
if (version < 1) {
|
||||||
|
// v1.0 added a new religions layer
|
||||||
|
relig = viewbox.insert("g", "#terrain").attr("id", "relig");
|
||||||
|
Religions.generate();
|
||||||
|
|
||||||
|
// v1.0 added a legend box
|
||||||
|
legend = svg.append("g").attr("id", "legend");
|
||||||
|
legend
|
||||||
|
.attr("font-family", "Almendra SC")
|
||||||
|
.attr("font-size", 13)
|
||||||
|
.attr("data-size", 13)
|
||||||
|
.attr("data-x", 99)
|
||||||
|
.attr("data-y", 93)
|
||||||
|
.attr("stroke-width", 2.5)
|
||||||
|
.attr("stroke", "#812929")
|
||||||
|
.attr("stroke-dasharray", "0 4 10 4")
|
||||||
|
.attr("stroke-linecap", "round");
|
||||||
|
|
||||||
|
// v1.0 separated drawBorders fron drawStates()
|
||||||
|
stateBorders = borders.append("g").attr("id", "stateBorders");
|
||||||
|
provinceBorders = borders.append("g").attr("id", "provinceBorders");
|
||||||
|
borders
|
||||||
|
.attr("opacity", null)
|
||||||
|
.attr("stroke", null)
|
||||||
|
.attr("stroke-width", null)
|
||||||
|
.attr("stroke-dasharray", null)
|
||||||
|
.attr("stroke-linecap", null)
|
||||||
|
.attr("filter", null);
|
||||||
|
stateBorders.attr("opacity", 0.8).attr("stroke", "#56566d").attr("stroke-width", 1).attr("stroke-dasharray", "2").attr("stroke-linecap", "butt");
|
||||||
|
provinceBorders.attr("opacity", 0.8).attr("stroke", "#56566d").attr("stroke-width", 0.5).attr("stroke-dasharray", "1").attr("stroke-linecap", "butt");
|
||||||
|
|
||||||
|
// v1.0 added state relations, provinces, forms and full names
|
||||||
|
provs = viewbox.insert("g", "#borders").attr("id", "provs").attr("opacity", 0.6);
|
||||||
|
BurgsAndStates.collectStatistics();
|
||||||
|
BurgsAndStates.generateCampaigns();
|
||||||
|
BurgsAndStates.generateDiplomacy();
|
||||||
|
BurgsAndStates.defineStateForms();
|
||||||
|
drawStates();
|
||||||
|
BurgsAndStates.generateProvinces();
|
||||||
|
drawBorders();
|
||||||
|
if (!layerIsOn("toggleBorders")) $("#borders").fadeOut();
|
||||||
|
if (!layerIsOn("toggleStates")) regions.attr("display", "none").selectAll("path").remove();
|
||||||
|
|
||||||
|
// v1.0 added zones layer
|
||||||
|
zones = viewbox.insert("g", "#borders").attr("id", "zones").attr("display", "none");
|
||||||
|
zones.attr("opacity", 0.6).attr("stroke", null).attr("stroke-width", 0).attr("stroke-dasharray", null).attr("stroke-linecap", "butt");
|
||||||
|
addZones();
|
||||||
|
if (!markers.selectAll("*").size()) {
|
||||||
|
Markers.generate();
|
||||||
|
turnButtonOn("toggleMarkers");
|
||||||
|
}
|
||||||
|
|
||||||
|
// v1.0 add fogging layer (state focus)
|
||||||
|
fogging = viewbox.insert("g", "#ruler").attr("id", "fogging-cont").attr("mask", "url(#fog)").append("g").attr("id", "fogging").style("display", "none");
|
||||||
|
fogging.append("rect").attr("x", 0).attr("y", 0).attr("width", "100%").attr("height", "100%");
|
||||||
|
defs.append("mask").attr("id", "fog").append("rect").attr("x", 0).attr("y", 0).attr("width", "100%").attr("height", "100%").attr("fill", "white");
|
||||||
|
|
||||||
|
// v1.0 changes states opacity bask to regions level
|
||||||
|
if (statesBody.attr("opacity")) {
|
||||||
|
regions.attr("opacity", statesBody.attr("opacity"));
|
||||||
|
statesBody.attr("opacity", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
// v1.0 changed labels to multi-lined
|
||||||
|
labels.selectAll("textPath").each(function () {
|
||||||
|
const text = this.textContent;
|
||||||
|
const shift = this.getComputedTextLength() / -1.5;
|
||||||
|
this.innerHTML = `<tspan x="${shift}">${text}</tspan>`;
|
||||||
|
});
|
||||||
|
|
||||||
|
// v1.0 added new biome - Wetland
|
||||||
|
biomesData.name.push("Wetland");
|
||||||
|
biomesData.color.push("#0b9131");
|
||||||
|
biomesData.habitability.push(12);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.1) {
|
||||||
|
// v1.0 initial code had a bug with religion layer id
|
||||||
|
if (!relig.size()) relig = viewbox.insert("g", "#terrain").attr("id", "relig");
|
||||||
|
|
||||||
|
// v1.0 initially has Sympathy status then relaced with Friendly
|
||||||
|
for (const s of pack.states) {
|
||||||
|
if (!s.diplomacy) continue;
|
||||||
|
s.diplomacy = s.diplomacy.map(r => (r === "Sympathy" ? "Friendly" : r));
|
||||||
|
}
|
||||||
|
|
||||||
|
// labels should be toggled via style attribute, so remove display attribute
|
||||||
|
labels.attr("display", null);
|
||||||
|
|
||||||
|
// v1.0 added religions heirarchy tree
|
||||||
|
if (pack.religions[1] && !pack.religions[1].code) {
|
||||||
|
pack.religions
|
||||||
|
.filter(r => r.i)
|
||||||
|
.forEach(r => {
|
||||||
|
r.origin = 0;
|
||||||
|
r.code = r.name.slice(0, 2);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!document.getElementById("freshwater")) {
|
||||||
|
lakes.append("g").attr("id", "freshwater");
|
||||||
|
lakes.select("#freshwater").attr("opacity", 0.5).attr("fill", "#a6c1fd").attr("stroke", "#5f799d").attr("stroke-width", 0.7).attr("filter", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!document.getElementById("salt")) {
|
||||||
|
lakes.append("g").attr("id", "salt");
|
||||||
|
lakes.select("#salt").attr("opacity", 0.5).attr("fill", "#409b8a").attr("stroke", "#388985").attr("stroke-width", 0.7).attr("filter", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
// v1.1 added new lake and coast groups
|
||||||
|
if (!document.getElementById("sinkhole")) {
|
||||||
|
lakes.append("g").attr("id", "sinkhole");
|
||||||
|
lakes.append("g").attr("id", "frozen");
|
||||||
|
lakes.append("g").attr("id", "lava");
|
||||||
|
lakes.select("#sinkhole").attr("opacity", 1).attr("fill", "#5bc9fd").attr("stroke", "#53a3b0").attr("stroke-width", 0.7).attr("filter", null);
|
||||||
|
lakes.select("#frozen").attr("opacity", 0.95).attr("fill", "#cdd4e7").attr("stroke", "#cfe0eb").attr("stroke-width", 0).attr("filter", null);
|
||||||
|
lakes.select("#lava").attr("opacity", 0.7).attr("fill", "#90270d").attr("stroke", "#f93e0c").attr("stroke-width", 2).attr("filter", "url(#crumpled)");
|
||||||
|
|
||||||
|
coastline.append("g").attr("id", "sea_island");
|
||||||
|
coastline.append("g").attr("id", "lake_island");
|
||||||
|
coastline.select("#sea_island").attr("opacity", 0.5).attr("stroke", "#1f3846").attr("stroke-width", 0.7).attr("filter", "url(#dropShadow)");
|
||||||
|
coastline.select("#lake_island").attr("opacity", 1).attr("stroke", "#7c8eaf").attr("stroke-width", 0.35).attr("filter", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
// v1.1 features stores more data
|
||||||
|
defs.select("#land").selectAll("path").remove();
|
||||||
|
defs.select("#water").selectAll("path").remove();
|
||||||
|
coastline.selectAll("path").remove();
|
||||||
|
lakes.selectAll("path").remove();
|
||||||
|
drawCoastline();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.11) {
|
||||||
|
// v1.11 added new attributes
|
||||||
|
terrs.attr("scheme", "bright").attr("terracing", 0).attr("skip", 5).attr("relax", 0).attr("curve", 0);
|
||||||
|
svg.select("#oceanic > *").attr("id", "oceanicPattern");
|
||||||
|
oceanLayers.attr("layers", "-6,-3,-1");
|
||||||
|
gridOverlay.attr("type", "pointyHex").attr("size", 10);
|
||||||
|
|
||||||
|
// v1.11 added cultures heirarchy tree
|
||||||
|
if (pack.cultures[1] && !pack.cultures[1].code) {
|
||||||
|
pack.cultures
|
||||||
|
.filter(c => c.i)
|
||||||
|
.forEach(c => {
|
||||||
|
c.origin = 0;
|
||||||
|
c.code = c.name.slice(0, 2);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
// v1.11 had an issue with fogging being displayed on load
|
||||||
|
unfog();
|
||||||
|
|
||||||
|
// v1.2 added new terrain attributes
|
||||||
|
if (!terrain.attr("set")) terrain.attr("set", "simple");
|
||||||
|
if (!terrain.attr("size")) terrain.attr("size", 1);
|
||||||
|
if (!terrain.attr("density")) terrain.attr("density", 0.4);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.21) {
|
||||||
|
// v1.11 replaced "display" attribute by "display" style
|
||||||
|
viewbox.selectAll("g").each(function () {
|
||||||
|
if (this.hasAttribute("display")) {
|
||||||
|
this.removeAttribute("display");
|
||||||
|
this.style.display = "none";
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
// v1.21 added rivers data to pack
|
||||||
|
pack.rivers = []; // rivers data
|
||||||
|
rivers.selectAll("path").each(function () {
|
||||||
|
const i = +this.id.slice(5);
|
||||||
|
const length = this.getTotalLength() / 2;
|
||||||
|
const s = this.getPointAtLength(length),
|
||||||
|
e = this.getPointAtLength(0);
|
||||||
|
const source = findCell(s.x, s.y),
|
||||||
|
mouth = findCell(e.x, e.y);
|
||||||
|
const name = Rivers.getName(mouth);
|
||||||
|
const type = length < 25 ? rw({Creek: 9, River: 3, Brook: 3, Stream: 1}) : "River";
|
||||||
|
pack.rivers.push({i, parent: 0, length, source, mouth, basin: i, name, type});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.22) {
|
||||||
|
// v1.22 changed state neighbors from Set object to array
|
||||||
|
BurgsAndStates.collectStatistics();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.3) {
|
||||||
|
// v1.3 added global options object
|
||||||
|
const winds = options.slice(); // previostly wind was saved in settings[19]
|
||||||
|
const year = rand(100, 2000);
|
||||||
|
const era = Names.getBaseShort(P(0.7) ? 1 : rand(nameBases.length)) + " Era";
|
||||||
|
const eraShort = era[0] + "E";
|
||||||
|
const military = Military.getDefaultOptions();
|
||||||
|
options = {winds, year, era, eraShort, military};
|
||||||
|
|
||||||
|
// v1.3 added campaings data for all states
|
||||||
|
BurgsAndStates.generateCampaigns();
|
||||||
|
|
||||||
|
// v1.3 added militry layer
|
||||||
|
armies = viewbox.insert("g", "#icons").attr("id", "armies");
|
||||||
|
armies.attr("opacity", 1).attr("fill-opacity", 1).attr("font-size", 6).attr("box-size", 3).attr("stroke", "#000").attr("stroke-width", 0.3);
|
||||||
|
turnButtonOn("toggleMilitary");
|
||||||
|
Military.generate();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.4) {
|
||||||
|
// v1.35 added dry lakes
|
||||||
|
if (!lakes.select("#dry").size()) {
|
||||||
|
lakes.append("g").attr("id", "dry");
|
||||||
|
lakes.select("#dry").attr("opacity", 1).attr("fill", "#c9bfa7").attr("stroke", "#8e816f").attr("stroke-width", 0.7).attr("filter", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
// v1.4 added ice layer
|
||||||
|
ice = viewbox.insert("g", "#coastline").attr("id", "ice").style("display", "none");
|
||||||
|
ice.attr("opacity", null).attr("fill", "#e8f0f6").attr("stroke", "#e8f0f6").attr("stroke-width", 1).attr("filter", "url(#dropShadow05)");
|
||||||
|
drawIce();
|
||||||
|
|
||||||
|
// v1.4 added icon and power attributes for units
|
||||||
|
for (const unit of options.military) {
|
||||||
|
if (!unit.icon) unit.icon = getUnitIcon(unit.type);
|
||||||
|
if (!unit.power) unit.power = unit.crew;
|
||||||
|
}
|
||||||
|
|
||||||
|
function getUnitIcon(type) {
|
||||||
|
if (type === "naval") return "🌊";
|
||||||
|
if (type === "ranged") return "🏹";
|
||||||
|
if (type === "mounted") return "🐴";
|
||||||
|
if (type === "machinery") return "💣";
|
||||||
|
if (type === "armored") return "🐢";
|
||||||
|
if (type === "aviation") return "🦅";
|
||||||
|
if (type === "magical") return "🔮";
|
||||||
|
else return "⚔️";
|
||||||
|
}
|
||||||
|
|
||||||
|
// v1.4 added state reference for regiments
|
||||||
|
pack.states.filter(s => s.military).forEach(s => s.military.forEach(r => (r.state = s.i)));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.5) {
|
||||||
|
// not need to store default styles from v 1.5
|
||||||
|
localStorage.removeItem("styleClean");
|
||||||
|
localStorage.removeItem("styleGloom");
|
||||||
|
localStorage.removeItem("styleAncient");
|
||||||
|
localStorage.removeItem("styleMonochrome");
|
||||||
|
|
||||||
|
// v1.5 cultures has shield attribute
|
||||||
|
pack.cultures.forEach(culture => {
|
||||||
|
if (culture.removed) return;
|
||||||
|
culture.shield = Cultures.getRandomShield();
|
||||||
|
});
|
||||||
|
|
||||||
|
// v1.5 added burg type value
|
||||||
|
pack.burgs.forEach(burg => {
|
||||||
|
if (!burg.i || burg.removed) return;
|
||||||
|
burg.type = BurgsAndStates.getType(burg.cell, burg.port);
|
||||||
|
});
|
||||||
|
|
||||||
|
// v1.5 added emblems
|
||||||
|
defs.append("g").attr("id", "defs-emblems");
|
||||||
|
emblems = viewbox.insert("g", "#population").attr("id", "emblems").style("display", "none");
|
||||||
|
emblems.append("g").attr("id", "burgEmblems");
|
||||||
|
emblems.append("g").attr("id", "provinceEmblems");
|
||||||
|
emblems.append("g").attr("id", "stateEmblems");
|
||||||
|
regenerateEmblems();
|
||||||
|
toggleEmblems();
|
||||||
|
|
||||||
|
// v1.5 changed releif icons data
|
||||||
|
terrain.selectAll("use").each(function () {
|
||||||
|
const type = this.getAttribute("data-type") || this.getAttribute("xlink:href");
|
||||||
|
this.removeAttribute("xlink:href");
|
||||||
|
this.removeAttribute("data-type");
|
||||||
|
this.removeAttribute("data-size");
|
||||||
|
this.setAttribute("href", type);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.6) {
|
||||||
|
// v1.6 changed rivers data
|
||||||
|
for (const river of pack.rivers) {
|
||||||
|
const el = document.getElementById("river" + river.i);
|
||||||
|
if (el) {
|
||||||
|
river.widthFactor = +el.getAttribute("data-width");
|
||||||
|
el.removeAttribute("data-width");
|
||||||
|
el.removeAttribute("data-increment");
|
||||||
|
river.discharge = pack.cells.fl[river.mouth] || 1;
|
||||||
|
river.width = rn(river.length / 100, 2);
|
||||||
|
river.sourceWidth = 0.1;
|
||||||
|
} else {
|
||||||
|
Rivers.remove(river.i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// v1.6 changed lakes data
|
||||||
|
for (const f of pack.features) {
|
||||||
|
if (f.type !== "lake") continue;
|
||||||
|
if (f.evaporation) continue;
|
||||||
|
|
||||||
|
f.flux = f.flux || f.cells * 3;
|
||||||
|
f.temp = grid.cells.temp[pack.cells.g[f.firstCell]];
|
||||||
|
f.height = f.height || d3.min(pack.cells.c[f.firstCell].map(c => pack.cells.h[c]).filter(h => h >= 20));
|
||||||
|
const height = (f.height - 18) ** heightExponentInput.value;
|
||||||
|
const evaporation = ((700 * (f.temp + 0.006 * height)) / 50 + 75) / (80 - f.temp);
|
||||||
|
f.evaporation = rn(evaporation * f.cells);
|
||||||
|
f.name = f.name || Lakes.getName(f);
|
||||||
|
delete f.river;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.61) {
|
||||||
|
// v1.61 changed rulers data
|
||||||
|
ruler.style("display", null);
|
||||||
|
rulers = new Rulers();
|
||||||
|
|
||||||
|
ruler.selectAll(".ruler > .white").each(function () {
|
||||||
|
const x1 = +this.getAttribute("x1");
|
||||||
|
const y1 = +this.getAttribute("y1");
|
||||||
|
const x2 = +this.getAttribute("x2");
|
||||||
|
const y2 = +this.getAttribute("y2");
|
||||||
|
if (isNaN(x1) || isNaN(y1) || isNaN(x2) || isNaN(y2)) return;
|
||||||
|
const points = [
|
||||||
|
[x1, y1],
|
||||||
|
[x2, y2]
|
||||||
|
];
|
||||||
|
rulers.create(Ruler, points);
|
||||||
|
});
|
||||||
|
|
||||||
|
ruler.selectAll("g.opisometer").each(function () {
|
||||||
|
const pointsString = this.dataset.points;
|
||||||
|
if (!pointsString) return;
|
||||||
|
const points = JSON.parse(pointsString);
|
||||||
|
rulers.create(Opisometer, points);
|
||||||
|
});
|
||||||
|
|
||||||
|
ruler.selectAll("path.planimeter").each(function () {
|
||||||
|
const length = this.getTotalLength();
|
||||||
|
if (length < 30) return;
|
||||||
|
|
||||||
|
const step = length > 1000 ? 40 : length > 400 ? 20 : 10;
|
||||||
|
const increment = length / Math.ceil(length / step);
|
||||||
|
const points = [];
|
||||||
|
for (let i = 0; i <= length; i += increment) {
|
||||||
|
const point = this.getPointAtLength(i);
|
||||||
|
points.push([point.x | 0, point.y | 0]);
|
||||||
|
}
|
||||||
|
|
||||||
|
rulers.create(Planimeter, points);
|
||||||
|
});
|
||||||
|
|
||||||
|
ruler.selectAll("*").remove();
|
||||||
|
|
||||||
|
if (rulers.data.length) {
|
||||||
|
turnButtonOn("toggleRulers");
|
||||||
|
rulers.draw();
|
||||||
|
} else turnButtonOff("toggleRulers");
|
||||||
|
|
||||||
|
// 1.61 changed oceanicPattern from rect to image
|
||||||
|
const pattern = document.getElementById("oceanic");
|
||||||
|
const filter = pattern.firstElementChild.getAttribute("filter");
|
||||||
|
const href = filter ? "./images/" + filter.replace("url(#", "").replace(")", "") + ".png" : "";
|
||||||
|
pattern.innerHTML = `<image id="oceanicPattern" href=${href} width="100" height="100" opacity="0.2"></image>`;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.62) {
|
||||||
|
// v1.62 changed grid data
|
||||||
|
gridOverlay.attr("size", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.63) {
|
||||||
|
// v1.63 changed ocean pattern opacity element
|
||||||
|
const oceanPattern = document.getElementById("oceanPattern");
|
||||||
|
if (oceanPattern) oceanPattern.removeAttribute("opacity");
|
||||||
|
const oceanicPattern = document.getElementById("oceanicPattern");
|
||||||
|
if (!oceanicPattern.getAttribute("opacity")) oceanicPattern.setAttribute("opacity", 0.2);
|
||||||
|
|
||||||
|
// v 1.63 moved label text-shadow from css to editable inline style
|
||||||
|
burgLabels.select("#cities").style("text-shadow", "white 0 0 4px");
|
||||||
|
burgLabels.select("#towns").style("text-shadow", "white 0 0 4px");
|
||||||
|
labels.select("#states").style("text-shadow", "white 0 0 4px");
|
||||||
|
labels.select("#addedLabels").style("text-shadow", "white 0 0 4px");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.64) {
|
||||||
|
// v1.64 change states style
|
||||||
|
const opacity = regions.attr("opacity");
|
||||||
|
const filter = regions.attr("filter");
|
||||||
|
statesBody.attr("opacity", opacity).attr("filter", filter);
|
||||||
|
statesHalo.attr("opacity", opacity).attr("filter", "blur(5px)");
|
||||||
|
regions.attr("opacity", null).attr("filter", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.65) {
|
||||||
|
// v1.65 changed rivers data
|
||||||
|
d3.select("#rivers").attr("style", null); // remove style to unhide layer
|
||||||
|
const {cells, rivers} = pack;
|
||||||
|
const defaultWidthFactor = rn(1 / (pointsInput.dataset.cells / 10000) ** 0.25, 2);
|
||||||
|
|
||||||
|
for (const river of rivers) {
|
||||||
|
const node = document.getElementById("river" + river.i);
|
||||||
|
if (node && !river.cells) {
|
||||||
|
const riverCells = [];
|
||||||
|
const riverPoints = [];
|
||||||
|
|
||||||
|
const length = node.getTotalLength() / 2;
|
||||||
|
if (!length) continue;
|
||||||
|
const segments = Math.ceil(length / 6);
|
||||||
|
const increment = length / segments;
|
||||||
|
|
||||||
|
for (let i = 0; i <= segments; i++) {
|
||||||
|
const shift = increment * i;
|
||||||
|
const {x: x1, y: y1} = node.getPointAtLength(length + shift);
|
||||||
|
const {x: x2, y: y2} = node.getPointAtLength(length - shift);
|
||||||
|
const x = rn((x1 + x2) / 2, 1);
|
||||||
|
const y = rn((y1 + y2) / 2, 1);
|
||||||
|
|
||||||
|
const cell = findCell(x, y);
|
||||||
|
riverPoints.push([x, y]);
|
||||||
|
riverCells.push(cell);
|
||||||
|
}
|
||||||
|
|
||||||
|
river.cells = riverCells;
|
||||||
|
river.points = riverPoints;
|
||||||
|
}
|
||||||
|
|
||||||
|
river.widthFactor = defaultWidthFactor;
|
||||||
|
|
||||||
|
cells.i.forEach(i => {
|
||||||
|
const riverInWater = cells.r[i] && cells.h[i] < 20;
|
||||||
|
if (riverInWater) cells.r[i] = 0;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.652) {
|
||||||
|
// remove style to unhide layers
|
||||||
|
rivers.attr("style", null);
|
||||||
|
borders.attr("style", null);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.7) {
|
||||||
|
// v1.7 changed markers data
|
||||||
|
const defs = document.getElementById("defs-markers");
|
||||||
|
const markersGroup = document.getElementById("markers");
|
||||||
|
|
||||||
|
if (defs && markersGroup) {
|
||||||
|
const markerElements = markersGroup.querySelectorAll("use");
|
||||||
|
const rescale = +markersGroup.getAttribute("rescale");
|
||||||
|
|
||||||
|
pack.markers = Array.from(markerElements).map((el, i) => {
|
||||||
|
const id = el.getAttribute("id");
|
||||||
|
const note = notes.find(note => note.id === id);
|
||||||
|
if (note) note.id = `marker${i}`;
|
||||||
|
|
||||||
|
let x = +el.dataset.x;
|
||||||
|
let y = +el.dataset.y;
|
||||||
|
|
||||||
|
const transform = el.getAttribute("transform");
|
||||||
|
if (transform) {
|
||||||
|
const [dx, dy] = parseTransform(transform);
|
||||||
|
if (dx) x += +dx;
|
||||||
|
if (dy) y += +dy;
|
||||||
|
}
|
||||||
|
const cell = findCell(x, y);
|
||||||
|
const size = rn(rescale ? el.dataset.size * 30 : el.getAttribute("width"), 1);
|
||||||
|
|
||||||
|
const href = el.href.baseVal;
|
||||||
|
const type = href.replace("#marker_", "");
|
||||||
|
const symbol = defs?.querySelector(`symbol${href}`);
|
||||||
|
const text = symbol?.querySelector("text");
|
||||||
|
const circle = symbol?.querySelector("circle");
|
||||||
|
|
||||||
|
const icon = text?.innerHTML;
|
||||||
|
const px = text && Number(text.getAttribute("font-size")?.replace("px", ""));
|
||||||
|
const dx = text && Number(text.getAttribute("x")?.replace("%", ""));
|
||||||
|
const dy = text && Number(text.getAttribute("y")?.replace("%", ""));
|
||||||
|
const fill = circle && circle.getAttribute("fill");
|
||||||
|
const stroke = circle && circle.getAttribute("stroke");
|
||||||
|
|
||||||
|
const marker = {i, icon, type, x, y, size, cell};
|
||||||
|
if (size && size !== 30) marker.size = size;
|
||||||
|
if (!isNaN(px) && px !== 12) marker.px = px;
|
||||||
|
if (!isNaN(dx) && dx !== 50) marker.dx = dx;
|
||||||
|
if (!isNaN(dy) && dy !== 50) marker.dy = dy;
|
||||||
|
if (fill && fill !== "#ffffff") marker.fill = fill;
|
||||||
|
if (stroke && stroke !== "#000000") marker.stroke = stroke;
|
||||||
|
if (circle?.getAttribute("opacity") === "0") marker.pin = "no";
|
||||||
|
|
||||||
|
return marker;
|
||||||
|
});
|
||||||
|
|
||||||
|
markersGroup.style.display = null;
|
||||||
|
defs?.remove();
|
||||||
|
markerElements.forEach(el => el.remove());
|
||||||
|
if (layerIsOn("markers")) drawMarkers();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.72) {
|
||||||
|
// v1.72 renamed custom style presets
|
||||||
|
const storedStyles = Object.keys(localStorage).filter(key => key.startsWith("style"));
|
||||||
|
storedStyles.forEach(styleName => {
|
||||||
|
const style = localStorage.getItem(styleName);
|
||||||
|
const newStyleName = styleName.replace(/^style/, customPresetPrefix);
|
||||||
|
localStorage.setItem(newStyleName, style);
|
||||||
|
localStorage.removeItem(styleName);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
if (version < 1.73) {
|
||||||
|
// v1.73 moved the hatching patterns out of the user's SVG
|
||||||
|
document.getElementById("hatching")?.remove();
|
||||||
|
|
||||||
|
// v1.73 added zone type to UI, ensure type is populated
|
||||||
|
const zones = Array.from(document.querySelectorAll("#zones > g"));
|
||||||
|
zones.forEach(zone => {
|
||||||
|
if (!zone.dataset.type) zone.dataset.type = "Unknown";
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -12,7 +12,6 @@ async load(filename): load filename from provider
|
||||||
async list(): list available filenames at provider
|
async list(): list available filenames at provider
|
||||||
async getLink(filePath): get shareable link for file
|
async getLink(filePath): get shareable link for file
|
||||||
restore(): restore access tokens from storage if possible
|
restore(): restore access tokens from storage if possible
|
||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
window.Cloud = (function () {
|
window.Cloud = (function () {
|
||||||
|
|
@ -32,38 +31,40 @@ window.Cloud = (function () {
|
||||||
token: null, // Access token
|
token: null, // Access token
|
||||||
api: null,
|
api: null,
|
||||||
|
|
||||||
restore() {
|
|
||||||
this.token = getToken(this.name);
|
|
||||||
if (this.token) this.connect(this.token);
|
|
||||||
},
|
|
||||||
|
|
||||||
async call(name, param) {
|
async call(name, param) {
|
||||||
try {
|
try {
|
||||||
|
if (!this.api) await this.initialize();
|
||||||
return await this.api[name](param);
|
return await this.api[name](param);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
if (e.name !== "DropboxResponseError") throw e;
|
if (e.name !== "DropboxResponseError") throw e;
|
||||||
// retry with auth
|
await this.auth(); // retry with auth
|
||||||
await this.auth();
|
|
||||||
return await this.api[name](param);
|
return await this.api[name](param);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
connect(token) {
|
initialize() {
|
||||||
const clientId = this.clientId;
|
const token = getToken(this.name);
|
||||||
const auth = new Dropbox.DropboxAuth({clientId});
|
if (token) {
|
||||||
|
return this.connect(token);
|
||||||
|
} else {
|
||||||
|
return this.auth();
|
||||||
|
}
|
||||||
|
},
|
||||||
|
|
||||||
|
async connect(token) {
|
||||||
|
await import("https://unpkg.com/dropbox@10.8.0/dist/Dropbox-sdk.min.js");
|
||||||
|
const auth = new Dropbox.DropboxAuth({clientId: this.clientId});
|
||||||
auth.setAccessToken(token);
|
auth.setAccessToken(token);
|
||||||
this.api = new Dropbox.Dropbox({auth});
|
this.api = new Dropbox.Dropbox({auth});
|
||||||
},
|
},
|
||||||
|
|
||||||
async save(fileName, contents) {
|
async save(fileName, contents) {
|
||||||
if (!this.api) await this.auth();
|
const resp = await this.call("filesUpload", {path: "/" + fileName, contents});
|
||||||
const resp = this.call("filesUpload", {path: "/" + fileName, contents});
|
|
||||||
DEBUG && console.log("Dropbox response:", resp);
|
DEBUG && console.log("Dropbox response:", resp);
|
||||||
return true;
|
return true;
|
||||||
},
|
},
|
||||||
|
|
||||||
async load(path) {
|
async load(path) {
|
||||||
if (!this.api) await this.auth();
|
|
||||||
const resp = await this.call("filesDownload", {path});
|
const resp = await this.call("filesDownload", {path});
|
||||||
const blob = resp.result.fileBlob;
|
const blob = resp.result.fileBlob;
|
||||||
if (!blob) throw new Error("Invalid response from dropbox.");
|
if (!blob) throw new Error("Invalid response from dropbox.");
|
||||||
|
|
@ -71,22 +72,23 @@ window.Cloud = (function () {
|
||||||
},
|
},
|
||||||
|
|
||||||
async list() {
|
async list() {
|
||||||
if (!this.api) return null;
|
|
||||||
const resp = await this.call("filesListFolder", {path: ""});
|
const resp = await this.call("filesListFolder", {path: ""});
|
||||||
return resp.result.entries.map(e => ({name: e.name, path: e.path_lower}));
|
return resp.result.entries.map(e => ({name: e.name, path: e.path_lower}));
|
||||||
},
|
},
|
||||||
|
|
||||||
auth() {
|
auth() {
|
||||||
const url = window.location.origin + window.location.pathname + "dropbox.html";
|
const width = 640;
|
||||||
this.authWindow = window.open(url, "auth", "width=640,height=480");
|
const height = 480;
|
||||||
// child window expected to call
|
const left = window.innerWidth / 2 - width / 2;
|
||||||
// window.opener.Cloud.providers.dropbox.setDropBoxToken (see below)
|
const top = window.innerHeight / 2 - height / 2.5;
|
||||||
|
this.authWindow = window.open("./dropbox.html", "auth", `width=640, height=${height}, top=${top}, left=${left}}`);
|
||||||
|
|
||||||
return new Promise((resolve, reject) => {
|
return new Promise((resolve, reject) => {
|
||||||
const watchDog = () => {
|
const watchDog = setTimeout(() => {
|
||||||
this.authWindow.close();
|
this.authWindow.close();
|
||||||
reject(new Error("Timeout. No auth for dropbox."));
|
reject(new Error("Timeout. No auth for Dropbox"));
|
||||||
};
|
}, 120 * 1000);
|
||||||
setTimeout(watchDog, 120 * 1000);
|
|
||||||
window.addEventListener("dropboxauth", e => {
|
window.addEventListener("dropboxauth", e => {
|
||||||
clearTimeout(watchDog);
|
clearTimeout(watchDog);
|
||||||
resolve();
|
resolve();
|
||||||
|
|
@ -94,46 +96,34 @@ window.Cloud = (function () {
|
||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
// Callback function for auth window.
|
// Callback function for auth window
|
||||||
setDropBoxToken(token) {
|
async setDropBoxToken(token) {
|
||||||
DEBUG && console.log("Access token:", token);
|
DEBUG && console.log("Access token:", token);
|
||||||
setToken(this.name, token);
|
setToken(this.name, token);
|
||||||
this.connect(token);
|
await this.connect(token);
|
||||||
this.authWindow.close();
|
this.authWindow.close();
|
||||||
window.dispatchEvent(new Event("dropboxauth"));
|
window.dispatchEvent(new Event("dropboxauth"));
|
||||||
},
|
},
|
||||||
|
|
||||||
|
returnError(errorDescription) {
|
||||||
|
console.error(errorDescription);
|
||||||
|
tip(errorDescription.replaceAll("+", " "), true, "error", 4000);
|
||||||
|
this.authWindow.close();
|
||||||
|
},
|
||||||
|
|
||||||
async getLink(path) {
|
async getLink(path) {
|
||||||
if (!this.api) await this.auth();
|
// return existitng shared link
|
||||||
let resp;
|
const sharedLinks = await this.call("sharingListSharedLinks", {path});
|
||||||
|
if (sharedLinks.result.links.length) return resp.result.links[0].url;
|
||||||
|
|
||||||
// already exists?
|
// create new shared link
|
||||||
resp = await this.call("sharingListSharedLinks", {path});
|
const settings = {require_password: false, audience: "public", access: "viewer", requested_visibility: "public", allow_download: true};
|
||||||
if (resp.result.links.length) return resp.result.links[0].url;
|
const resp = await this.call("sharingCreateSharedLinkWithSettings", {path, settings});
|
||||||
|
|
||||||
// create new
|
|
||||||
resp = await this.call("sharingCreateSharedLinkWithSettings", {
|
|
||||||
path,
|
|
||||||
settings: {
|
|
||||||
require_password: false,
|
|
||||||
audience: "public",
|
|
||||||
access: "viewer",
|
|
||||||
requested_visibility: "public",
|
|
||||||
allow_download: true
|
|
||||||
}
|
|
||||||
});
|
|
||||||
DEBUG && console.log("Dropbox link object:", resp.result);
|
DEBUG && console.log("Dropbox link object:", resp.result);
|
||||||
return resp.result.url;
|
return resp.result.url;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// register providers here:
|
const providers = {dropbox: DBP};
|
||||||
const providers = {
|
|
||||||
dropbox: DBP
|
|
||||||
};
|
|
||||||
|
|
||||||
// restore all providers at startup
|
|
||||||
for (const p of Object.values(providers)) p.restore();
|
|
||||||
|
|
||||||
return {providers};
|
return {providers};
|
||||||
})();
|
})();
|
||||||
209
modules/io/export-json.js
Normal file
|
|
@ -0,0 +1,209 @@
|
||||||
|
function exportToJson(type) {
|
||||||
|
if (customization) return tip("Map cannot be saved when edit mode is active, please exit the mode and retry", false, "error");
|
||||||
|
closeDialogs("#alert");
|
||||||
|
|
||||||
|
const typeMap = {
|
||||||
|
Full: getFullDataJson,
|
||||||
|
Minimal: getMinimalDataJson,
|
||||||
|
PackCells: getPackCellsDataJson,
|
||||||
|
GridCells: getGridCellsDataJson,
|
||||||
|
};
|
||||||
|
|
||||||
|
const mapData = typeMap[type]();
|
||||||
|
const blob = new Blob([mapData], {type: "application/json"});
|
||||||
|
const URL = window.URL.createObjectURL(blob);
|
||||||
|
const link = document.createElement("a");
|
||||||
|
link.download = getFileName(type) + ".json";
|
||||||
|
link.href = URL;
|
||||||
|
link.click();
|
||||||
|
tip(`${link.download} is saved. Open "Downloads" screen (CTRL + J) to check`, true, "success", 7000);
|
||||||
|
window.URL.revokeObjectURL(URL);
|
||||||
|
}
|
||||||
|
|
||||||
|
function getMapInfo() {
|
||||||
|
const info = {
|
||||||
|
version,
|
||||||
|
description: "Azgaar's Fantasy Map Generator output: azgaar.github.io/Fantasy-map-generator",
|
||||||
|
exportedAt: new Date().toISOString(),
|
||||||
|
mapName: mapName.value,
|
||||||
|
seed,
|
||||||
|
mapId
|
||||||
|
};
|
||||||
|
|
||||||
|
return info;
|
||||||
|
}
|
||||||
|
|
||||||
|
function getSettings() {
|
||||||
|
const settings = {
|
||||||
|
distanceUnit: distanceUnitInput.value,
|
||||||
|
distanceScale: distanceScaleInput.value,
|
||||||
|
areaUnit: areaUnit.value,
|
||||||
|
heightUnit: heightUnit.value,
|
||||||
|
heightExponent: heightExponentInput.value,
|
||||||
|
temperatureScale: temperatureScale.value,
|
||||||
|
barSize: barSizeInput.value,
|
||||||
|
barLabel: barLabel.value,
|
||||||
|
barBackOpacity: barBackOpacity.value,
|
||||||
|
barBackColor: barBackColor.value,
|
||||||
|
barPosX: barPosX.value,
|
||||||
|
barPosY: barPosY.value,
|
||||||
|
populationRate: populationRate,
|
||||||
|
urbanization: urbanization,
|
||||||
|
mapSize: mapSizeOutput.value,
|
||||||
|
latitudeO: latitudeOutput.value,
|
||||||
|
temperatureEquator: temperatureEquatorOutput.value,
|
||||||
|
temperaturePole: temperaturePoleOutput.value,
|
||||||
|
prec: precOutput.value,
|
||||||
|
options: options,
|
||||||
|
mapName: mapName.value,
|
||||||
|
hideLabels: hideLabels.checked,
|
||||||
|
stylePreset: stylePreset.value,
|
||||||
|
rescaleLabels: rescaleLabels.checked,
|
||||||
|
urbanDensity: urbanDensity
|
||||||
|
};
|
||||||
|
|
||||||
|
return settings;
|
||||||
|
}
|
||||||
|
|
||||||
|
function getPackCellsData() {
|
||||||
|
const cellConverted = {
|
||||||
|
i: Array.from(pack.cells.i),
|
||||||
|
v: pack.cells.v,
|
||||||
|
c: pack.cells.c,
|
||||||
|
p: pack.cells.p,
|
||||||
|
g: Array.from(pack.cells.g),
|
||||||
|
h: Array.from(pack.cells.h),
|
||||||
|
area: Array.from(pack.cells.area),
|
||||||
|
f: Array.from(pack.cells.f),
|
||||||
|
t: Array.from(pack.cells.t),
|
||||||
|
haven: Array.from(pack.cells.haven),
|
||||||
|
harbor: Array.from(pack.cells.harbor),
|
||||||
|
fl: Array.from(pack.cells.fl),
|
||||||
|
r: Array.from(pack.cells.r),
|
||||||
|
conf: Array.from(pack.cells.conf),
|
||||||
|
biome: Array.from(pack.cells.biome),
|
||||||
|
s: Array.from(pack.cells.s),
|
||||||
|
pop: Array.from(pack.cells.pop),
|
||||||
|
culture: Array.from(pack.cells.culture),
|
||||||
|
burg: Array.from(pack.cells.burg),
|
||||||
|
road: Array.from(pack.cells.road),
|
||||||
|
crossroad: Array.from(pack.cells.crossroad),
|
||||||
|
state: Array.from(pack.cells.state),
|
||||||
|
religion: Array.from(pack.cells.religion),
|
||||||
|
province: Array.from(pack.cells.province)
|
||||||
|
};
|
||||||
|
const cellObjArr = [];
|
||||||
|
{
|
||||||
|
cellConverted.i.forEach(value => {
|
||||||
|
const cellobj = {
|
||||||
|
i: value,
|
||||||
|
v: cellConverted.v[value],
|
||||||
|
c: cellConverted.c[value],
|
||||||
|
p: cellConverted.p[value],
|
||||||
|
g: cellConverted.g[value],
|
||||||
|
h: cellConverted.h[value],
|
||||||
|
area: cellConverted.area[value],
|
||||||
|
f: cellConverted.f[value],
|
||||||
|
t: cellConverted.t[value],
|
||||||
|
haven: cellConverted.haven[value],
|
||||||
|
harbor: cellConverted.harbor[value],
|
||||||
|
fl: cellConverted.fl[value],
|
||||||
|
r: cellConverted.r[value],
|
||||||
|
conf: cellConverted.conf[value],
|
||||||
|
biome: cellConverted.biome[value],
|
||||||
|
s: cellConverted.s[value],
|
||||||
|
pop: cellConverted.pop[value],
|
||||||
|
culture: cellConverted.culture[value],
|
||||||
|
burg: cellConverted.burg[value],
|
||||||
|
road: cellConverted.road[value],
|
||||||
|
crossroad: cellConverted.crossroad[value],
|
||||||
|
state: cellConverted.state[value],
|
||||||
|
religion: cellConverted.religion[value],
|
||||||
|
province: cellConverted.province[value]
|
||||||
|
};
|
||||||
|
cellObjArr.push(cellobj);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
const cellsData = {
|
||||||
|
cells: cellObjArr,
|
||||||
|
features: pack.features,
|
||||||
|
cultures: pack.cultures,
|
||||||
|
burgs: pack.burgs,
|
||||||
|
states: pack.states,
|
||||||
|
provinces: pack.provinces,
|
||||||
|
religions: pack.religions,
|
||||||
|
rivers: pack.rivers,
|
||||||
|
markers: pack.markers
|
||||||
|
};
|
||||||
|
|
||||||
|
return cellsData;
|
||||||
|
}
|
||||||
|
|
||||||
|
//data only containing graphical appearance
|
||||||
|
function getGridCellsData(){
|
||||||
|
const gridData = {
|
||||||
|
spacing: grid.spacing,
|
||||||
|
cellsY: grid.cellsY,
|
||||||
|
cellsX: grid.cellsX,
|
||||||
|
points: grid.points,
|
||||||
|
boundary: grid.boundary
|
||||||
|
}
|
||||||
|
return gridData
|
||||||
|
}
|
||||||
|
|
||||||
|
function getFullDataJson() {
|
||||||
|
TIME && console.time("getFullDataJson");
|
||||||
|
|
||||||
|
const info = getMapInfo();
|
||||||
|
const settings = getSettings();
|
||||||
|
const cells = getPackCellsData();
|
||||||
|
const exportData = {info, settings, coords: mapCoordinates, cells, biomes: biomesData, notes, nameBases};
|
||||||
|
|
||||||
|
TIME && console.timeEnd("getFullDataJson");
|
||||||
|
return JSON.stringify(exportData);
|
||||||
|
}
|
||||||
|
|
||||||
|
// data excluding cells
|
||||||
|
function getMinimalDataJson() {
|
||||||
|
TIME && console.time("getMinimalDataJson");
|
||||||
|
|
||||||
|
const info = getMapInfo();
|
||||||
|
const settings = getSettings();
|
||||||
|
const packData = {
|
||||||
|
features: pack.features,
|
||||||
|
cultures: pack.cultures,
|
||||||
|
burgs: pack.burgs,
|
||||||
|
states: pack.states,
|
||||||
|
provinces: pack.provinces,
|
||||||
|
religions: pack.religions,
|
||||||
|
rivers: pack.rivers,
|
||||||
|
markers: pack.markers
|
||||||
|
};
|
||||||
|
const exportData = {info, settings, coords: mapCoordinates, pack: packData, biomes: biomesData, notes, nameBases};
|
||||||
|
|
||||||
|
TIME && console.timeEnd("getMinimalDataJson");
|
||||||
|
return JSON.stringify(exportData);
|
||||||
|
}
|
||||||
|
|
||||||
|
function getPackCellsDataJson() {
|
||||||
|
TIME && console.time("getCellsDataJson");
|
||||||
|
|
||||||
|
const info = getMapInfo();
|
||||||
|
const cells = getPackCellsData();
|
||||||
|
const exportData = {info, cells};
|
||||||
|
|
||||||
|
TIME && console.timeEnd("getCellsDataJson");
|
||||||
|
return JSON.stringify(exportData);
|
||||||
|
}
|
||||||
|
|
||||||
|
function getGridCellsDataJson() {
|
||||||
|
TIME && console.time("getGridCellsDataJson");
|
||||||
|
|
||||||
|
const info = getMapInfo();
|
||||||
|
const gridCells = getGridCellsData()
|
||||||
|
const exportData = {info,gridCells};
|
||||||
|
|
||||||
|
TIME && console.log("getGridCellsDataJson");
|
||||||
|
return JSON.stringify(exportData);
|
||||||
|
}
|
||||||
|
|
@ -262,17 +262,17 @@ async function getMapURL(type, options = {}) {
|
||||||
if (pattern) cloneDefs.appendChild(pattern.cloneNode(true));
|
if (pattern) cloneDefs.appendChild(pattern.cloneNode(true));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!cloneEl.getElementById("hatching").children.length) cloneEl.getElementById("hatching")?.remove(); // remove unused hatching group
|
|
||||||
if (!cloneEl.getElementById("fogging-cont")) cloneEl.getElementById("fog")?.remove(); // remove unused fog
|
if (!cloneEl.getElementById("fogging-cont")) cloneEl.getElementById("fog")?.remove(); // remove unused fog
|
||||||
if (!cloneEl.getElementById("regions")) cloneEl.getElementById("statePaths")?.remove(); // removed unused statePaths
|
if (!cloneEl.getElementById("regions")) cloneEl.getElementById("statePaths")?.remove(); // removed unused statePaths
|
||||||
if (!cloneEl.getElementById("labels")) cloneEl.getElementById("textPaths")?.remove(); // removed unused textPaths
|
if (!cloneEl.getElementById("labels")) cloneEl.getElementById("textPaths")?.remove(); // removed unused textPaths
|
||||||
|
|
||||||
// add armies style
|
// add armies style
|
||||||
if (cloneEl.getElementById("armies"))
|
if (cloneEl.getElementById("armies")) {
|
||||||
cloneEl.insertAdjacentHTML(
|
cloneEl.insertAdjacentHTML(
|
||||||
"afterbegin",
|
"afterbegin",
|
||||||
"<style>#armies text {stroke: none; fill: #fff; text-shadow: 0 0 4px #000; dominant-baseline: central; text-anchor: middle; font-family: Helvetica; fill-opacity: 1;}#armies text.regimentIcon {font-size: .8em;}</style>"
|
"<style>#armies text {stroke: none; fill: #fff; text-shadow: 0 0 4px #000; dominant-baseline: central; text-anchor: middle; font-family: Helvetica; fill-opacity: 1;}#armies text.regimentIcon {font-size: .8em;}</style>"
|
||||||
);
|
);
|
||||||
|
}
|
||||||
|
|
||||||
// add xlink: for href to support svg 1.1
|
// add xlink: for href to support svg 1.1
|
||||||
if (type === "svg") {
|
if (type === "svg") {
|
||||||
|
|
@ -283,6 +283,16 @@ async function getMapURL(type, options = {}) {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// add hatchings
|
||||||
|
const hatchingUsers = cloneEl.querySelectorAll(`[fill^='url(#hatch']`);
|
||||||
|
const hatchingFills = unique(Array.from(hatchingUsers).map(el => el.getAttribute("fill")));
|
||||||
|
const hatchingIds = hatchingFills.map(fill => fill.slice(5, -1));
|
||||||
|
for (const hatchingId of hatchingIds) {
|
||||||
|
const hatching = svgDefs.getElementById(hatchingId);
|
||||||
|
if (hatching) cloneDefs.appendChild(hatching.cloneNode(true));
|
||||||
|
}
|
||||||
|
|
||||||
|
// load fonts
|
||||||
const usedFonts = getUsedFonts(cloneEl);
|
const usedFonts = getUsedFonts(cloneEl);
|
||||||
const fontsToLoad = usedFonts.filter(font => font.src);
|
const fontsToLoad = usedFonts.filter(font => font.src);
|
||||||
if (fontsToLoad.length) {
|
if (fontsToLoad.length) {
|
||||||
|
|
@ -145,7 +145,7 @@ function parseLoadedResult(result) {
|
||||||
const mapVersion = parseFloat(mapData[0].split("|")[0] || mapData[0]);
|
const mapVersion = parseFloat(mapData[0].split("|")[0] || mapData[0]);
|
||||||
return [mapData, mapVersion];
|
return [mapData, mapVersion];
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error(error);
|
ERROR && console.error(error);
|
||||||
return [null, null];
|
return [null, null];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -182,18 +182,15 @@ function showUploadMessage(type, mapData, mapVersion) {
|
||||||
$("#alert").dialog({title, buttons});
|
$("#alert").dialog({title, buttons});
|
||||||
}
|
}
|
||||||
|
|
||||||
function parseLoadedData(data) {
|
async function parseLoadedData(data) {
|
||||||
try {
|
try {
|
||||||
// exit customization
|
// exit customization
|
||||||
if (window.closeDialogs) closeDialogs();
|
if (window.closeDialogs) closeDialogs();
|
||||||
customization = 0;
|
customization = 0;
|
||||||
if (customizationMenu.offsetParent) styleTab.click();
|
if (customizationMenu.offsetParent) styleTab.click();
|
||||||
|
|
||||||
const reliefIcons = document.getElementById("defs-relief").innerHTML; // save relief icons
|
|
||||||
const hatching = document.getElementById("hatching").cloneNode(true); // save hatching
|
|
||||||
|
|
||||||
void (function parseParameters() {
|
|
||||||
const params = data[0].split("|");
|
const params = data[0].split("|");
|
||||||
|
void (function parseParameters() {
|
||||||
if (params[3]) {
|
if (params[3]) {
|
||||||
seed = params[3];
|
seed = params[3];
|
||||||
optionsSeed.value = seed;
|
optionsSeed.value = seed;
|
||||||
|
|
@ -423,514 +420,13 @@ function parseLoadedData(data) {
|
||||||
legend.on("mousemove", () => tip("Drag to change the position. Click to hide the legend")).on("click", () => clearLegend());
|
legend.on("mousemove", () => tip("Drag to change the position. Click to hide the legend")).on("click", () => clearLegend());
|
||||||
})();
|
})();
|
||||||
|
|
||||||
void (function resolveVersionConflicts() {
|
{
|
||||||
const version = parseFloat(data[0].split("|")[0]);
|
// dynamically import and run auto-udpdate script
|
||||||
if (version < 0.9) {
|
const version = parseFloat(params[0]);
|
||||||
// 0.9 has additional relief icons to be included into older maps
|
const {resolveVersionConflicts} = await import("./auto-update.js");
|
||||||
document.getElementById("defs-relief").innerHTML = reliefIcons;
|
resolveVersionConflicts(version);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (version < 1) {
|
|
||||||
// 1.0 adds a new religions layer
|
|
||||||
relig = viewbox.insert("g", "#terrain").attr("id", "relig");
|
|
||||||
Religions.generate();
|
|
||||||
|
|
||||||
// 1.0 adds a legend box
|
|
||||||
legend = svg.append("g").attr("id", "legend");
|
|
||||||
legend
|
|
||||||
.attr("font-family", "Almendra SC")
|
|
||||||
.attr("font-size", 13)
|
|
||||||
.attr("data-size", 13)
|
|
||||||
.attr("data-x", 99)
|
|
||||||
.attr("data-y", 93)
|
|
||||||
.attr("stroke-width", 2.5)
|
|
||||||
.attr("stroke", "#812929")
|
|
||||||
.attr("stroke-dasharray", "0 4 10 4")
|
|
||||||
.attr("stroke-linecap", "round");
|
|
||||||
|
|
||||||
// 1.0 separated drawBorders fron drawStates()
|
|
||||||
stateBorders = borders.append("g").attr("id", "stateBorders");
|
|
||||||
provinceBorders = borders.append("g").attr("id", "provinceBorders");
|
|
||||||
borders
|
|
||||||
.attr("opacity", null)
|
|
||||||
.attr("stroke", null)
|
|
||||||
.attr("stroke-width", null)
|
|
||||||
.attr("stroke-dasharray", null)
|
|
||||||
.attr("stroke-linecap", null)
|
|
||||||
.attr("filter", null);
|
|
||||||
stateBorders.attr("opacity", 0.8).attr("stroke", "#56566d").attr("stroke-width", 1).attr("stroke-dasharray", "2").attr("stroke-linecap", "butt");
|
|
||||||
provinceBorders.attr("opacity", 0.8).attr("stroke", "#56566d").attr("stroke-width", 0.5).attr("stroke-dasharray", "1").attr("stroke-linecap", "butt");
|
|
||||||
|
|
||||||
// 1.0 adds state relations, provinces, forms and full names
|
|
||||||
provs = viewbox.insert("g", "#borders").attr("id", "provs").attr("opacity", 0.6);
|
|
||||||
BurgsAndStates.collectStatistics();
|
|
||||||
BurgsAndStates.generateCampaigns();
|
|
||||||
BurgsAndStates.generateDiplomacy();
|
|
||||||
BurgsAndStates.defineStateForms();
|
|
||||||
drawStates();
|
|
||||||
BurgsAndStates.generateProvinces();
|
|
||||||
drawBorders();
|
|
||||||
if (!layerIsOn("toggleBorders")) $("#borders").fadeOut();
|
|
||||||
if (!layerIsOn("toggleStates")) regions.attr("display", "none").selectAll("path").remove();
|
|
||||||
|
|
||||||
// 1.0 adds hatching
|
|
||||||
document.getElementsByTagName("defs")[0].appendChild(hatching);
|
|
||||||
|
|
||||||
// 1.0 adds zones layer
|
|
||||||
zones = viewbox.insert("g", "#borders").attr("id", "zones").attr("display", "none");
|
|
||||||
zones.attr("opacity", 0.6).attr("stroke", null).attr("stroke-width", 0).attr("stroke-dasharray", null).attr("stroke-linecap", "butt");
|
|
||||||
addZones();
|
|
||||||
if (!markers.selectAll("*").size()) {
|
|
||||||
Markers.generate();
|
|
||||||
turnButtonOn("toggleMarkers");
|
|
||||||
}
|
|
||||||
|
|
||||||
// 1.0 add fogging layer (state focus)
|
|
||||||
fogging = viewbox.insert("g", "#ruler").attr("id", "fogging-cont").attr("mask", "url(#fog)").append("g").attr("id", "fogging").style("display", "none");
|
|
||||||
fogging.append("rect").attr("x", 0).attr("y", 0).attr("width", "100%").attr("height", "100%");
|
|
||||||
defs.append("mask").attr("id", "fog").append("rect").attr("x", 0).attr("y", 0).attr("width", "100%").attr("height", "100%").attr("fill", "white");
|
|
||||||
|
|
||||||
// 1.0 changes states opacity bask to regions level
|
|
||||||
if (statesBody.attr("opacity")) {
|
|
||||||
regions.attr("opacity", statesBody.attr("opacity"));
|
|
||||||
statesBody.attr("opacity", null);
|
|
||||||
}
|
|
||||||
|
|
||||||
// 1.0 changed labels to multi-lined
|
|
||||||
labels.selectAll("textPath").each(function () {
|
|
||||||
const text = this.textContent;
|
|
||||||
const shift = this.getComputedTextLength() / -1.5;
|
|
||||||
this.innerHTML = `<tspan x="${shift}">${text}</tspan>`;
|
|
||||||
});
|
|
||||||
|
|
||||||
// 1.0 added new biome - Wetland
|
|
||||||
biomesData.name.push("Wetland");
|
|
||||||
biomesData.color.push("#0b9131");
|
|
||||||
biomesData.habitability.push(12);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.1) {
|
|
||||||
// v 1.0 initial code had a bug with religion layer id
|
|
||||||
if (!relig.size()) relig = viewbox.insert("g", "#terrain").attr("id", "relig");
|
|
||||||
|
|
||||||
// v 1.0 initially has Sympathy status then relaced with Friendly
|
|
||||||
for (const s of pack.states) {
|
|
||||||
if (!s.diplomacy) continue;
|
|
||||||
s.diplomacy = s.diplomacy.map(r => (r === "Sympathy" ? "Friendly" : r));
|
|
||||||
}
|
|
||||||
|
|
||||||
// labels should be toggled via style attribute, so remove display attribute
|
|
||||||
labels.attr("display", null);
|
|
||||||
|
|
||||||
// v 1.0 added religions heirarchy tree
|
|
||||||
if (pack.religions[1] && !pack.religions[1].code) {
|
|
||||||
pack.religions
|
|
||||||
.filter(r => r.i)
|
|
||||||
.forEach(r => {
|
|
||||||
r.origin = 0;
|
|
||||||
r.code = r.name.slice(0, 2);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!document.getElementById("freshwater")) {
|
|
||||||
lakes.append("g").attr("id", "freshwater");
|
|
||||||
lakes.select("#freshwater").attr("opacity", 0.5).attr("fill", "#a6c1fd").attr("stroke", "#5f799d").attr("stroke-width", 0.7).attr("filter", null);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!document.getElementById("salt")) {
|
|
||||||
lakes.append("g").attr("id", "salt");
|
|
||||||
lakes.select("#salt").attr("opacity", 0.5).attr("fill", "#409b8a").attr("stroke", "#388985").attr("stroke-width", 0.7).attr("filter", null);
|
|
||||||
}
|
|
||||||
|
|
||||||
// v 1.1 added new lake and coast groups
|
|
||||||
if (!document.getElementById("sinkhole")) {
|
|
||||||
lakes.append("g").attr("id", "sinkhole");
|
|
||||||
lakes.append("g").attr("id", "frozen");
|
|
||||||
lakes.append("g").attr("id", "lava");
|
|
||||||
lakes.select("#sinkhole").attr("opacity", 1).attr("fill", "#5bc9fd").attr("stroke", "#53a3b0").attr("stroke-width", 0.7).attr("filter", null);
|
|
||||||
lakes.select("#frozen").attr("opacity", 0.95).attr("fill", "#cdd4e7").attr("stroke", "#cfe0eb").attr("stroke-width", 0).attr("filter", null);
|
|
||||||
lakes.select("#lava").attr("opacity", 0.7).attr("fill", "#90270d").attr("stroke", "#f93e0c").attr("stroke-width", 2).attr("filter", "url(#crumpled)");
|
|
||||||
|
|
||||||
coastline.append("g").attr("id", "sea_island");
|
|
||||||
coastline.append("g").attr("id", "lake_island");
|
|
||||||
coastline.select("#sea_island").attr("opacity", 0.5).attr("stroke", "#1f3846").attr("stroke-width", 0.7).attr("filter", "url(#dropShadow)");
|
|
||||||
coastline.select("#lake_island").attr("opacity", 1).attr("stroke", "#7c8eaf").attr("stroke-width", 0.35).attr("filter", null);
|
|
||||||
}
|
|
||||||
|
|
||||||
// v 1.1 features stores more data
|
|
||||||
defs.select("#land").selectAll("path").remove();
|
|
||||||
defs.select("#water").selectAll("path").remove();
|
|
||||||
coastline.selectAll("path").remove();
|
|
||||||
lakes.selectAll("path").remove();
|
|
||||||
drawCoastline();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.11) {
|
|
||||||
// v 1.11 added new attributes
|
|
||||||
terrs.attr("scheme", "bright").attr("terracing", 0).attr("skip", 5).attr("relax", 0).attr("curve", 0);
|
|
||||||
svg.select("#oceanic > *").attr("id", "oceanicPattern");
|
|
||||||
oceanLayers.attr("layers", "-6,-3,-1");
|
|
||||||
gridOverlay.attr("type", "pointyHex").attr("size", 10);
|
|
||||||
|
|
||||||
// v 1.11 added cultures heirarchy tree
|
|
||||||
if (pack.cultures[1] && !pack.cultures[1].code) {
|
|
||||||
pack.cultures
|
|
||||||
.filter(c => c.i)
|
|
||||||
.forEach(c => {
|
|
||||||
c.origin = 0;
|
|
||||||
c.code = c.name.slice(0, 2);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
// v 1.11 had an issue with fogging being displayed on load
|
|
||||||
unfog();
|
|
||||||
|
|
||||||
// v 1.2 added new terrain attributes
|
|
||||||
if (!terrain.attr("set")) terrain.attr("set", "simple");
|
|
||||||
if (!terrain.attr("size")) terrain.attr("size", 1);
|
|
||||||
if (!terrain.attr("density")) terrain.attr("density", 0.4);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.21) {
|
|
||||||
// v 1.11 replaced "display" attribute by "display" style
|
|
||||||
viewbox.selectAll("g").each(function () {
|
|
||||||
if (this.hasAttribute("display")) {
|
|
||||||
this.removeAttribute("display");
|
|
||||||
this.style.display = "none";
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// v 1.21 added rivers data to pack
|
|
||||||
pack.rivers = []; // rivers data
|
|
||||||
rivers.selectAll("path").each(function () {
|
|
||||||
const i = +this.id.slice(5);
|
|
||||||
const length = this.getTotalLength() / 2;
|
|
||||||
const s = this.getPointAtLength(length),
|
|
||||||
e = this.getPointAtLength(0);
|
|
||||||
const source = findCell(s.x, s.y),
|
|
||||||
mouth = findCell(e.x, e.y);
|
|
||||||
const name = Rivers.getName(mouth);
|
|
||||||
const type = length < 25 ? rw({Creek: 9, River: 3, Brook: 3, Stream: 1}) : "River";
|
|
||||||
pack.rivers.push({i, parent: 0, length, source, mouth, basin: i, name, type});
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.22) {
|
|
||||||
// v 1.22 changed state neighbors from Set object to array
|
|
||||||
BurgsAndStates.collectStatistics();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.3) {
|
|
||||||
// v 1.3 added global options object
|
|
||||||
const winds = options.slice(); // previostly wind was saved in settings[19]
|
|
||||||
const year = rand(100, 2000);
|
|
||||||
const era = Names.getBaseShort(P(0.7) ? 1 : rand(nameBases.length)) + " Era";
|
|
||||||
const eraShort = era[0] + "E";
|
|
||||||
const military = Military.getDefaultOptions();
|
|
||||||
options = {winds, year, era, eraShort, military};
|
|
||||||
|
|
||||||
// v 1.3 added campaings data for all states
|
|
||||||
BurgsAndStates.generateCampaigns();
|
|
||||||
|
|
||||||
// v 1.3 added militry layer
|
|
||||||
armies = viewbox.insert("g", "#icons").attr("id", "armies");
|
|
||||||
armies.attr("opacity", 1).attr("fill-opacity", 1).attr("font-size", 6).attr("box-size", 3).attr("stroke", "#000").attr("stroke-width", 0.3);
|
|
||||||
turnButtonOn("toggleMilitary");
|
|
||||||
Military.generate();
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.4) {
|
|
||||||
// v 1.35 added dry lakes
|
|
||||||
if (!lakes.select("#dry").size()) {
|
|
||||||
lakes.append("g").attr("id", "dry");
|
|
||||||
lakes.select("#dry").attr("opacity", 1).attr("fill", "#c9bfa7").attr("stroke", "#8e816f").attr("stroke-width", 0.7).attr("filter", null);
|
|
||||||
}
|
|
||||||
|
|
||||||
// v 1.4 added ice layer
|
|
||||||
ice = viewbox.insert("g", "#coastline").attr("id", "ice").style("display", "none");
|
|
||||||
ice.attr("opacity", null).attr("fill", "#e8f0f6").attr("stroke", "#e8f0f6").attr("stroke-width", 1).attr("filter", "url(#dropShadow05)");
|
|
||||||
drawIce();
|
|
||||||
|
|
||||||
// v 1.4 added icon and power attributes for units
|
|
||||||
for (const unit of options.military) {
|
|
||||||
if (!unit.icon) unit.icon = getUnitIcon(unit.type);
|
|
||||||
if (!unit.power) unit.power = unit.crew;
|
|
||||||
}
|
|
||||||
|
|
||||||
function getUnitIcon(type) {
|
|
||||||
if (type === "naval") return "🌊";
|
|
||||||
if (type === "ranged") return "🏹";
|
|
||||||
if (type === "mounted") return "🐴";
|
|
||||||
if (type === "machinery") return "💣";
|
|
||||||
if (type === "armored") return "🐢";
|
|
||||||
if (type === "aviation") return "🦅";
|
|
||||||
if (type === "magical") return "🔮";
|
|
||||||
else return "⚔️";
|
|
||||||
}
|
|
||||||
|
|
||||||
// 1.4 added state reference for regiments
|
|
||||||
pack.states.filter(s => s.military).forEach(s => s.military.forEach(r => (r.state = s.i)));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.5) {
|
|
||||||
// not need to store default styles from v 1.5
|
|
||||||
localStorage.removeItem("styleClean");
|
|
||||||
localStorage.removeItem("styleGloom");
|
|
||||||
localStorage.removeItem("styleAncient");
|
|
||||||
localStorage.removeItem("styleMonochrome");
|
|
||||||
|
|
||||||
// v 1.5 cultures has shield attribute
|
|
||||||
pack.cultures.forEach(culture => {
|
|
||||||
if (culture.removed) return;
|
|
||||||
culture.shield = Cultures.getRandomShield();
|
|
||||||
});
|
|
||||||
|
|
||||||
// v 1.5 added burg type value
|
|
||||||
pack.burgs.forEach(burg => {
|
|
||||||
if (!burg.i || burg.removed) return;
|
|
||||||
burg.type = BurgsAndStates.getType(burg.cell, burg.port);
|
|
||||||
});
|
|
||||||
|
|
||||||
// v 1.5 added emblems
|
|
||||||
defs.append("g").attr("id", "defs-emblems");
|
|
||||||
emblems = viewbox.insert("g", "#population").attr("id", "emblems").style("display", "none");
|
|
||||||
emblems.append("g").attr("id", "burgEmblems");
|
|
||||||
emblems.append("g").attr("id", "provinceEmblems");
|
|
||||||
emblems.append("g").attr("id", "stateEmblems");
|
|
||||||
regenerateEmblems();
|
|
||||||
toggleEmblems();
|
|
||||||
|
|
||||||
// v 1.5 changed releif icons data
|
|
||||||
terrain.selectAll("use").each(function () {
|
|
||||||
const type = this.getAttribute("data-type") || this.getAttribute("xlink:href");
|
|
||||||
this.removeAttribute("xlink:href");
|
|
||||||
this.removeAttribute("data-type");
|
|
||||||
this.removeAttribute("data-size");
|
|
||||||
this.setAttribute("href", type);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.6) {
|
|
||||||
// v 1.6 changed rivers data
|
|
||||||
for (const river of pack.rivers) {
|
|
||||||
const el = document.getElementById("river" + river.i);
|
|
||||||
if (el) {
|
|
||||||
river.widthFactor = +el.getAttribute("data-width");
|
|
||||||
el.removeAttribute("data-width");
|
|
||||||
el.removeAttribute("data-increment");
|
|
||||||
river.discharge = pack.cells.fl[river.mouth] || 1;
|
|
||||||
river.width = rn(river.length / 100, 2);
|
|
||||||
river.sourceWidth = 0.1;
|
|
||||||
} else {
|
|
||||||
Rivers.remove(river.i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// v 1.6 changed lakes data
|
|
||||||
for (const f of pack.features) {
|
|
||||||
if (f.type !== "lake") continue;
|
|
||||||
if (f.evaporation) continue;
|
|
||||||
|
|
||||||
f.flux = f.flux || f.cells * 3;
|
|
||||||
f.temp = grid.cells.temp[pack.cells.g[f.firstCell]];
|
|
||||||
f.height = f.height || d3.min(pack.cells.c[f.firstCell].map(c => pack.cells.h[c]).filter(h => h >= 20));
|
|
||||||
const height = (f.height - 18) ** heightExponentInput.value;
|
|
||||||
const evaporation = ((700 * (f.temp + 0.006 * height)) / 50 + 75) / (80 - f.temp);
|
|
||||||
f.evaporation = rn(evaporation * f.cells);
|
|
||||||
f.name = f.name || Lakes.getName(f);
|
|
||||||
delete f.river;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.61) {
|
|
||||||
// v 1.61 changed rulers data
|
|
||||||
ruler.style("display", null);
|
|
||||||
rulers = new Rulers();
|
|
||||||
|
|
||||||
ruler.selectAll(".ruler > .white").each(function () {
|
|
||||||
const x1 = +this.getAttribute("x1");
|
|
||||||
const y1 = +this.getAttribute("y1");
|
|
||||||
const x2 = +this.getAttribute("x2");
|
|
||||||
const y2 = +this.getAttribute("y2");
|
|
||||||
if (isNaN(x1) || isNaN(y1) || isNaN(x2) || isNaN(y2)) return;
|
|
||||||
const points = [
|
|
||||||
[x1, y1],
|
|
||||||
[x2, y2]
|
|
||||||
];
|
|
||||||
rulers.create(Ruler, points);
|
|
||||||
});
|
|
||||||
|
|
||||||
ruler.selectAll("g.opisometer").each(function () {
|
|
||||||
const pointsString = this.dataset.points;
|
|
||||||
if (!pointsString) return;
|
|
||||||
const points = JSON.parse(pointsString);
|
|
||||||
rulers.create(Opisometer, points);
|
|
||||||
});
|
|
||||||
|
|
||||||
ruler.selectAll("path.planimeter").each(function () {
|
|
||||||
const length = this.getTotalLength();
|
|
||||||
if (length < 30) return;
|
|
||||||
|
|
||||||
const step = length > 1000 ? 40 : length > 400 ? 20 : 10;
|
|
||||||
const increment = length / Math.ceil(length / step);
|
|
||||||
const points = [];
|
|
||||||
for (let i = 0; i <= length; i += increment) {
|
|
||||||
const point = this.getPointAtLength(i);
|
|
||||||
points.push([point.x | 0, point.y | 0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
rulers.create(Planimeter, points);
|
|
||||||
});
|
|
||||||
|
|
||||||
ruler.selectAll("*").remove();
|
|
||||||
|
|
||||||
if (rulers.data.length) {
|
|
||||||
turnButtonOn("toggleRulers");
|
|
||||||
rulers.draw();
|
|
||||||
} else turnButtonOff("toggleRulers");
|
|
||||||
|
|
||||||
// 1.61 changed oceanicPattern from rect to image
|
|
||||||
const pattern = document.getElementById("oceanic");
|
|
||||||
const filter = pattern.firstElementChild.getAttribute("filter");
|
|
||||||
const href = filter ? "./images/" + filter.replace("url(#", "").replace(")", "") + ".png" : "";
|
|
||||||
pattern.innerHTML = `<image id="oceanicPattern" href=${href} width="100" height="100" opacity="0.2"></image>`;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.62) {
|
|
||||||
// v 1.62 changed grid data
|
|
||||||
gridOverlay.attr("size", null);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.63) {
|
|
||||||
// v.1.63 changed ocean pattern opacity element
|
|
||||||
const oceanPattern = document.getElementById("oceanPattern");
|
|
||||||
if (oceanPattern) oceanPattern.removeAttribute("opacity");
|
|
||||||
const oceanicPattern = document.getElementById("oceanicPattern");
|
|
||||||
if (!oceanicPattern.getAttribute("opacity")) oceanicPattern.setAttribute("opacity", 0.2);
|
|
||||||
|
|
||||||
// v 1.63 moved label text-shadow from css to editable inline style
|
|
||||||
burgLabels.select("#cities").style("text-shadow", "white 0 0 4px");
|
|
||||||
burgLabels.select("#towns").style("text-shadow", "white 0 0 4px");
|
|
||||||
labels.select("#states").style("text-shadow", "white 0 0 4px");
|
|
||||||
labels.select("#addedLabels").style("text-shadow", "white 0 0 4px");
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.64) {
|
|
||||||
// v.1.64 change states style
|
|
||||||
const opacity = regions.attr("opacity");
|
|
||||||
const filter = regions.attr("filter");
|
|
||||||
statesBody.attr("opacity", opacity).attr("filter", filter);
|
|
||||||
statesHalo.attr("opacity", opacity).attr("filter", "blur(5px)");
|
|
||||||
regions.attr("opacity", null).attr("filter", null);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.65) {
|
|
||||||
// v 1.65 changed rivers data
|
|
||||||
d3.select("#rivers").attr("style", null); // remove style to unhide layer
|
|
||||||
const {cells, rivers} = pack;
|
|
||||||
const defaultWidthFactor = rn(1 / (pointsInput.dataset.cells / 10000) ** 0.25, 2);
|
|
||||||
|
|
||||||
for (const river of rivers) {
|
|
||||||
const node = document.getElementById("river" + river.i);
|
|
||||||
if (node && !river.cells) {
|
|
||||||
const riverCells = [];
|
|
||||||
const riverPoints = [];
|
|
||||||
|
|
||||||
const length = node.getTotalLength() / 2;
|
|
||||||
if (!length) continue;
|
|
||||||
const segments = Math.ceil(length / 6);
|
|
||||||
const increment = length / segments;
|
|
||||||
|
|
||||||
for (let i = 0; i <= segments; i++) {
|
|
||||||
const shift = increment * i;
|
|
||||||
const {x: x1, y: y1} = node.getPointAtLength(length + shift);
|
|
||||||
const {x: x2, y: y2} = node.getPointAtLength(length - shift);
|
|
||||||
const x = rn((x1 + x2) / 2, 1);
|
|
||||||
const y = rn((y1 + y2) / 2, 1);
|
|
||||||
|
|
||||||
const cell = findCell(x, y);
|
|
||||||
riverPoints.push([x, y]);
|
|
||||||
riverCells.push(cell);
|
|
||||||
}
|
|
||||||
|
|
||||||
river.cells = riverCells;
|
|
||||||
river.points = riverPoints;
|
|
||||||
}
|
|
||||||
|
|
||||||
river.widthFactor = defaultWidthFactor;
|
|
||||||
|
|
||||||
cells.i.forEach(i => {
|
|
||||||
const riverInWater = cells.r[i] && cells.h[i] < 20;
|
|
||||||
if (riverInWater) cells.r[i] = 0;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.652) {
|
|
||||||
// remove style to unhide layers
|
|
||||||
rivers.attr("style", null);
|
|
||||||
borders.attr("style", null);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (version < 1.7) {
|
|
||||||
// v 1.7 changed markers data
|
|
||||||
const defs = document.getElementById("defs-markers");
|
|
||||||
const markersGroup = document.getElementById("markers");
|
|
||||||
|
|
||||||
if (defs && markersGroup) {
|
|
||||||
const markerElements = markersGroup.querySelectorAll("use");
|
|
||||||
const rescale = +markersGroup.getAttribute("rescale");
|
|
||||||
|
|
||||||
pack.markers = Array.from(markerElements).map((el, i) => {
|
|
||||||
const id = el.getAttribute("id");
|
|
||||||
const note = notes.find(note => note.id === id);
|
|
||||||
if (note) note.id = `marker${i}`;
|
|
||||||
|
|
||||||
let x = +el.dataset.x;
|
|
||||||
let y = +el.dataset.y;
|
|
||||||
|
|
||||||
const transform = el.getAttribute("transform");
|
|
||||||
if (transform) {
|
|
||||||
const [dx, dy] = parseTransform(transform);
|
|
||||||
if (dx) x += +dx;
|
|
||||||
if (dy) y += +dy;
|
|
||||||
}
|
|
||||||
const cell = findCell(x, y);
|
|
||||||
const size = rn(rescale ? el.dataset.size * 30 : el.getAttribute("width"), 1);
|
|
||||||
|
|
||||||
const href = el.href.baseVal;
|
|
||||||
const type = href.replace("#marker_", "");
|
|
||||||
const symbol = defs?.querySelector(`symbol${href}`);
|
|
||||||
const text = symbol?.querySelector("text");
|
|
||||||
const circle = symbol?.querySelector("circle");
|
|
||||||
|
|
||||||
const icon = text?.innerHTML;
|
|
||||||
const px = text && Number(text.getAttribute("font-size")?.replace("px", ""));
|
|
||||||
const dx = text && Number(text.getAttribute("x")?.replace("%", ""));
|
|
||||||
const dy = text && Number(text.getAttribute("y")?.replace("%", ""));
|
|
||||||
const fill = circle && circle.getAttribute("fill");
|
|
||||||
const stroke = circle && circle.getAttribute("stroke");
|
|
||||||
|
|
||||||
const marker = {i, icon, type, x, y, size, cell};
|
|
||||||
if (size && size !== 30) marker.size = size;
|
|
||||||
if (!isNaN(px) && px !== 12) marker.px = px;
|
|
||||||
if (!isNaN(dx) && dx !== 50) marker.dx = dx;
|
|
||||||
if (!isNaN(dy) && dy !== 50) marker.dy = dy;
|
|
||||||
if (fill && fill !== "#ffffff") marker.fill = fill;
|
|
||||||
if (stroke && stroke !== "#000000") marker.stroke = stroke;
|
|
||||||
if (circle?.getAttribute("opacity") === "0") marker.pin = "no";
|
|
||||||
|
|
||||||
return marker;
|
|
||||||
});
|
|
||||||
|
|
||||||
markersGroup.style.display = null;
|
|
||||||
defs?.remove();
|
|
||||||
markerElements.forEach(el => el.remove());
|
|
||||||
if (layerIsOn("markers")) drawMarkers();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
})();
|
|
||||||
|
|
||||||
void (function checkDataIntegrity() {
|
void (function checkDataIntegrity() {
|
||||||
const cells = pack.cells;
|
const cells = pack.cells;
|
||||||
|
|
||||||
|
|
@ -1070,6 +566,7 @@ function parseLoadedData(data) {
|
||||||
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,
|
||||||
<br>generate a new random map or cancel the loading
|
<br>generate a new random map or cancel the loading
|
||||||
<p id="errorBox">${parseError(error)}</p>`;
|
<p id="errorBox">${parseError(error)}</p>`;
|
||||||
|
|
||||||
$("#alert").dialog({
|
$("#alert").dialog({
|
||||||
resizable: false,
|
resizable: false,
|
||||||
title: "Loading error",
|
title: "Loading error",
|
||||||
|
|
@ -145,7 +145,7 @@ async function saveToDropbox() {
|
||||||
await Cloud.providers.dropbox.save(filename, mapData);
|
await Cloud.providers.dropbox.save(filename, mapData);
|
||||||
tip("Map is saved to your Dropbox", true, "success", 8000);
|
tip("Map is saved to your Dropbox", true, "success", 8000);
|
||||||
} catch (msg) {
|
} catch (msg) {
|
||||||
console.error(msg);
|
ERROR && console.error(msg);
|
||||||
tip("Cannot save .map to your Dropbox", true, "error", 8000);
|
tip("Cannot save .map to your Dropbox", true, "error", 8000);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -519,7 +519,7 @@ window.Markers = (function () {
|
||||||
|
|
||||||
const dungeonSeed = `${seed}${cell}`;
|
const dungeonSeed = `${seed}${cell}`;
|
||||||
const name = "Dungeon";
|
const name = "Dungeon";
|
||||||
const legend = `<div>Undiscovered dungeon. See <a href="https://watabou.github.io/one-page-dungeon/?seed=${dungeonSeed}" target="_blank">One page dungeon</a></div><iframe style="height: 33vh" src="https://watabou.github.io/one-page-dungeon/?seed=${dungeonSeed}" sandbox="allow-scripts allow-same-origin"></iframe>`;
|
const legend = `<div>Undiscovered dungeon. See <a href="https://watabou.github.io/one-page-dungeon/?seed=${dungeonSeed}" target="_blank">One page dungeon</a></div><iframe src="https://watabou.github.io/one-page-dungeon/?seed=${dungeonSeed}" sandbox="allow-scripts allow-same-origin"></iframe>`;
|
||||||
notes.push({id, name, legend});
|
notes.push({id, name, legend});
|
||||||
quantity--;
|
quantity--;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -141,8 +141,8 @@ class Battle {
|
||||||
const state = pack.states[regiment.state];
|
const state = pack.states[regiment.state];
|
||||||
const distance = (Math.hypot(this.y - regiment.by, this.x - regiment.bx) * distanceScaleInput.value) | 0; // distance between regiment and its base
|
const distance = (Math.hypot(this.y - regiment.by, this.x - regiment.bx) * distanceScaleInput.value) | 0; // distance between regiment and its base
|
||||||
const color = state.color[0] === "#" ? state.color : "#999";
|
const color = state.color[0] === "#" ? state.color : "#999";
|
||||||
const icon = `<svg width="1.4em" height="1.4em" style="margin-bottom: -.6em">
|
const icon = `<svg width="1.4em" height="1.4em" style="margin-bottom: -.6em; stroke: #333">
|
||||||
<rect x="0" y="0" width="100%" height="100%" fill="${color}" class="fillRect"></rect>
|
<rect x="0" y="0" width="100%" height="100%" fill="${color}"></rect>
|
||||||
<text x="0" y="1.04em" style="">${regiment.icon}</text></svg>`;
|
<text x="0" y="1.04em" style="">${regiment.icon}</text></svg>`;
|
||||||
const body = `<tbody id="battle${state.i}-${regiment.i}">`;
|
const body = `<tbody id="battle${state.i}-${regiment.i}">`;
|
||||||
|
|
||||||
|
|
@ -183,7 +183,7 @@ class Battle {
|
||||||
dist = added ? "0 " + distanceUnitInput.value : distance(r);
|
dist = added ? "0 " + distanceUnitInput.value : distance(r);
|
||||||
return `<div ${added ? "class='inactive'" : ""} data-s=${s.i} data-i=${r.i} data-state=${s.name} data-regiment=${r.name}
|
return `<div ${added ? "class='inactive'" : ""} data-s=${s.i} data-i=${r.i} data-state=${s.name} data-regiment=${r.name}
|
||||||
data-total=${r.a} data-distance=${dist} data-tip="Click to select regiment">
|
data-total=${r.a} data-distance=${dist} data-tip="Click to select regiment">
|
||||||
<svg width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${s.color}" class="fillRect"></svg>
|
<svg width=".9em" height=".9em" style="margin-bottom:-1px; stroke: #333"><rect x="0" y="0" width="100%" height="100%" fill="${s.color}" ></svg>
|
||||||
<div style="width:6em">${s.name.slice(0, 11)}</div>
|
<div style="width:6em">${s.name.slice(0, 11)}</div>
|
||||||
<div style="width:1.2em">${r.icon}</div>
|
<div style="width:1.2em">${r.icon}</div>
|
||||||
<div style="width:13em">${r.name.slice(0, 24)}</div>
|
<div style="width:13em">${r.name.slice(0, 24)}</div>
|
||||||
|
|
|
||||||
|
|
@ -37,9 +37,9 @@ function editBiomes() {
|
||||||
document.getElementById("biomesExport").addEventListener("click", downloadBiomesData);
|
document.getElementById("biomesExport").addEventListener("click", downloadBiomesData);
|
||||||
|
|
||||||
body.addEventListener("click", function (ev) {
|
body.addEventListener("click", function (ev) {
|
||||||
const el = ev.target,
|
const el = ev.target;
|
||||||
cl = el.classList;
|
const cl = el.classList;
|
||||||
if (cl.contains("fillRect")) biomeChangeColor(el);
|
if (el.tagName === "FILL-BOX") 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);
|
else if (cl.contains("icon-trash-empty")) removeCustomBiome(el);
|
||||||
if (customization === 6) selectBiomeOnLineClick(el);
|
if (customization === 6) selectBiomeOnLineClick(el);
|
||||||
|
|
@ -94,9 +94,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="${
|
<fill-box fill="${b.color[i]}"></fill-box>
|
||||||
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=${
|
<input data-tip="Biome habitability percent. Click and set new value to change" type="number" min=0 max=9999 class="biomeHabitability hide" value=${
|
||||||
|
|
@ -158,15 +156,15 @@ function editBiomes() {
|
||||||
|
|
||||||
function biomeChangeColor(el) {
|
function biomeChangeColor(el) {
|
||||||
const currentFill = el.getAttribute("fill");
|
const currentFill = el.getAttribute("fill");
|
||||||
const biome = +el.parentNode.parentNode.dataset.id;
|
const biome = +el.parentNode.dataset.id;
|
||||||
|
|
||||||
const callback = function (fill) {
|
const callback = newFill => {
|
||||||
el.setAttribute("fill", fill);
|
el.fill = newFill;
|
||||||
biomesData.color[biome] = fill;
|
biomesData.color[biome] = newFill;
|
||||||
biomes
|
biomes
|
||||||
.select("#biome" + biome)
|
.select("#biome" + biome)
|
||||||
.attr("fill", fill)
|
.attr("fill", newFill)
|
||||||
.attr("stroke", fill);
|
.attr("stroke", newFill);
|
||||||
};
|
};
|
||||||
|
|
||||||
openPicker(currentFill, callback);
|
openPicker(currentFill, callback);
|
||||||
|
|
@ -270,7 +268,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="fillRect pointer"></svg>
|
<fill-box fill="${b.color[i]}"></fill-box>
|
||||||
<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]}>
|
||||||
|
|
|
||||||
|
|
@ -52,6 +52,7 @@ function editBurg(id) {
|
||||||
document.getElementById("burglLegend").addEventListener("click", editBurgLegend);
|
document.getElementById("burglLegend").addEventListener("click", editBurgLegend);
|
||||||
document.getElementById("burgLock").addEventListener("click", toggleBurgLockButton);
|
document.getElementById("burgLock").addEventListener("click", toggleBurgLockButton);
|
||||||
document.getElementById("burgRemove").addEventListener("click", removeSelectedBurg);
|
document.getElementById("burgRemove").addEventListener("click", removeSelectedBurg);
|
||||||
|
document.getElementById("burgTemperatureGraph").addEventListener("click", showTemperatureGraph);
|
||||||
|
|
||||||
function updateBurgValues() {
|
function updateBurgValues() {
|
||||||
const id = +elSelected.attr("data-id");
|
const id = +elSelected.attr("data-id");
|
||||||
|
|
@ -543,6 +544,11 @@ function editBurg(id) {
|
||||||
editNotes("burg" + id, name);
|
editNotes("burg" + id, name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function showTemperatureGraph() {
|
||||||
|
const id = elSelected.attr("data-id");
|
||||||
|
showBurgTemperatureGraph(id);
|
||||||
|
}
|
||||||
|
|
||||||
function removeSelectedBurg() {
|
function removeSelectedBurg() {
|
||||||
const id = +elSelected.attr("data-id");
|
const id = +elSelected.attr("data-id");
|
||||||
if (pack.burgs[id].capital) {
|
if (pack.burgs[id].capital) {
|
||||||
|
|
|
||||||
|
|
@ -108,9 +108,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-emblems="${c.shield}">
|
data-area=${area} data-population=${population} data-base=${c.base} data-type=${c.type} data-expansionism=${c.expansionism} data-emblems="${c.shield}">
|
||||||
<svg data-tip="Culture fill style. Click to change" width=".9em" height=".9em" style="margin-bottom:-1px">
|
<fill-box fill="${c.color}"></fill-box>
|
||||||
<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="Regenerate culture name" class="icon-cw hiddenIcon" style="visibility: hidden"></span>
|
<span data-tip="Regenerate culture name" class="icon-cw hiddenIcon" style="visibility: hidden"></span>
|
||||||
<span data-tip="Cells count" class="icon-check-empty hide"></span>
|
<span data-tip="Cells count" class="icon-check-empty hide"></span>
|
||||||
|
|
@ -148,7 +146,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.fillRect").forEach(el => el.addEventListener("click", cultureChangeColor));
|
body.querySelectorAll("fill-box").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 > span.icon-cw").forEach(el => el.addEventListener("click", cultureRegenerateName));
|
body.querySelectorAll("div > span.icon-cw").forEach(el => el.addEventListener("click", cultureRegenerateName));
|
||||||
body.querySelectorAll("div > input.statePower").forEach(el => el.addEventListener("input", cultureChangeExpansionism));
|
body.querySelectorAll("div > input.statePower").forEach(el => el.addEventListener("input", cultureChangeExpansionism));
|
||||||
|
|
@ -248,16 +246,16 @@ function editCultures() {
|
||||||
function cultureChangeColor() {
|
function cultureChangeColor() {
|
||||||
const el = this;
|
const el = this;
|
||||||
const currentFill = el.getAttribute("fill");
|
const currentFill = el.getAttribute("fill");
|
||||||
const culture = +el.parentNode.parentNode.dataset.id;
|
const culture = +el.parentNode.dataset.id;
|
||||||
|
|
||||||
const callback = function (fill) {
|
const callback = newFill => {
|
||||||
el.setAttribute("fill", fill);
|
el.fill = newFill;
|
||||||
pack.cultures[culture].color = fill;
|
pack.cultures[culture].color = newFill;
|
||||||
cults
|
cults
|
||||||
.select("#culture" + culture)
|
.select("#culture" + culture)
|
||||||
.attr("fill", fill)
|
.attr("fill", newFill)
|
||||||
.attr("stroke", fill);
|
.attr("stroke", newFill);
|
||||||
debug.select("#cultureCenter" + culture).attr("fill", fill);
|
debug.select("#cultureCenter" + culture).attr("fill", newFill);
|
||||||
};
|
};
|
||||||
|
|
||||||
openPicker(currentFill, callback);
|
openPicker(currentFill, callback);
|
||||||
|
|
|
||||||
|
|
@ -101,10 +101,8 @@ function editDiplomacy() {
|
||||||
lines += `<div class="states" data-id=${state.i} data-name="${name}" data-relations="${relation}">
|
lines += `<div class="states" data-id=${state.i} data-name="${name}" data-relations="${relation}">
|
||||||
<svg data-tip="${tipSelect}" class="coaIcon" viewBox="0 0 200 200"><use href="#stateCOA${state.i}"></use></svg>
|
<svg data-tip="${tipSelect}" class="coaIcon" viewBox="0 0 200 200"><use href="#stateCOA${state.i}"></use></svg>
|
||||||
<div data-tip="${tipSelect}" style="width: 12em">${name}</div>
|
<div data-tip="${tipSelect}" style="width: 12em">${name}</div>
|
||||||
<div data-tip="${tipChange}" class="changeRelations pointer" style="width: 6em">
|
<div data-tip="${tipChange}" class="changeRelations" style="width: 6em">
|
||||||
<svg width=".9em" height=".9em" style="margin-bottom:-1px">
|
<fill-box fill="${color}" size=".9em"></fill-box>
|
||||||
<rect x="0" y="0" width="100%" height="100%" fill="${color}" class="fillRect"></rect>
|
|
||||||
</svg>
|
|
||||||
${relation}
|
${relation}
|
||||||
</div>
|
</div>
|
||||||
</div>`;
|
</div>`;
|
||||||
|
|
@ -195,9 +193,7 @@ function editDiplomacy() {
|
||||||
([relation, {color, inText, tip}]) =>
|
([relation, {color, inText, tip}]) =>
|
||||||
`<div style="margin-block: 0.2em" data-tip="${tip}"><label class="pointer">
|
`<div style="margin-block: 0.2em" data-tip="${tip}"><label class="pointer">
|
||||||
<input type="radio" name="relationSelect" value="${relation}" ${currentRelation === relation && "checked"} >
|
<input type="radio" name="relationSelect" value="${relation}" ${currentRelation === relation && "checked"} >
|
||||||
<svg width=".9em" height=".9em" style="margin-bottom:-1px">
|
<fill-box fill="${color}" size=".8em"></fill-box>
|
||||||
<rect x="0" y="0" width="100%" height="100%" fill="${color}" class="fillRect" />
|
|
||||||
</svg>
|
|
||||||
${inText}
|
${inText}
|
||||||
</label></div>`
|
</label></div>`
|
||||||
)
|
)
|
||||||
|
|
|
||||||
|
|
@ -425,10 +425,10 @@ function clearLegend() {
|
||||||
function createPicker() {
|
function createPicker() {
|
||||||
const pos = () => tip("Drag to change the picker position");
|
const pos = () => tip("Drag to change the picker position");
|
||||||
const cl = () => tip("Click to close the picker");
|
const cl = () => tip("Click to close the picker");
|
||||||
const closePicker = () => contaiter.style("display", "none");
|
const closePicker = () => container.style("display", "none");
|
||||||
|
|
||||||
const contaiter = d3.select("body").append("svg").attr("id", "pickerContainer").attr("width", "100%").attr("height", "100%");
|
const container = d3.select("body").append("svg").attr("id", "pickerContainer").attr("width", "100%").attr("height", "100%");
|
||||||
contaiter
|
container
|
||||||
.append("rect")
|
.append("rect")
|
||||||
.attr("x", 0)
|
.attr("x", 0)
|
||||||
.attr("y", 0)
|
.attr("y", 0)
|
||||||
|
|
@ -437,7 +437,7 @@ function createPicker() {
|
||||||
.attr("opacity", 0.2)
|
.attr("opacity", 0.2)
|
||||||
.on("mousemove", cl)
|
.on("mousemove", cl)
|
||||||
.on("click", closePicker);
|
.on("click", closePicker);
|
||||||
const picker = contaiter
|
const picker = container
|
||||||
.append("g")
|
.append("g")
|
||||||
.attr("id", "picker")
|
.attr("id", "picker")
|
||||||
.call(
|
.call(
|
||||||
|
|
@ -494,7 +494,7 @@ function createPicker() {
|
||||||
|
|
||||||
const colors = picker.append("g").attr("id", "pickerColors").attr("stroke", "#333333");
|
const colors = picker.append("g").attr("id", "pickerColors").attr("stroke", "#333333");
|
||||||
const hatches = picker.append("g").attr("id", "pickerHatches").attr("stroke", "#333333");
|
const hatches = picker.append("g").attr("id", "pickerHatches").attr("stroke", "#333333");
|
||||||
const hatching = d3.selectAll("g#hatching > pattern");
|
const hatching = d3.selectAll("g#defs-hatching > pattern");
|
||||||
const number = hatching.size();
|
const number = hatching.size();
|
||||||
|
|
||||||
const clr = d3.range(number).map(i => d3.hsl((i / number) * 360, 0.7, 0.7).hex());
|
const clr = d3.range(number).map(i => d3.hsl((i / number) * 360, 0.7, 0.7).hex());
|
||||||
|
|
@ -504,8 +504,8 @@ function createPicker() {
|
||||||
.attr("id", "picker_" + d)
|
.attr("id", "picker_" + d)
|
||||||
.attr("fill", d)
|
.attr("fill", d)
|
||||||
.attr("class", i ? "" : "selected")
|
.attr("class", i ? "" : "selected")
|
||||||
.attr("x", i * 22 + 4)
|
.attr("x", (i % 14) * 22 + 4)
|
||||||
.attr("y", 40)
|
.attr("y", 40 + Math.floor(i / 14)*20)
|
||||||
.attr("width", 16)
|
.attr("width", 16)
|
||||||
.attr("height", 16);
|
.attr("height", 16);
|
||||||
});
|
});
|
||||||
|
|
@ -515,20 +515,20 @@ function createPicker() {
|
||||||
.append("rect")
|
.append("rect")
|
||||||
.attr("id", "picker_" + this.id)
|
.attr("id", "picker_" + this.id)
|
||||||
.attr("fill", "url(#" + this.id + ")")
|
.attr("fill", "url(#" + this.id + ")")
|
||||||
.attr("x", i * 22 + 4)
|
.attr("x", (i % 14) * 22 + 4)
|
||||||
.attr("y", 61)
|
.attr("y", Math.floor(i / 14)*20 + 20 + (number * 2))
|
||||||
.attr("width", 16)
|
.attr("width", 16)
|
||||||
.attr("height", 16);
|
.attr("height", 16)
|
||||||
});
|
});
|
||||||
|
|
||||||
colors
|
colors
|
||||||
.selectAll("rect")
|
.selectAll("rect")
|
||||||
.on("click", pickerFillClicked)
|
.on("click", pickerFillClicked)
|
||||||
.on("mousemove", () => tip("Click to fill with the color"));
|
.on("mouseover", () => tip("Click to fill with the color"));
|
||||||
hatches
|
hatches
|
||||||
.selectAll("rect")
|
.selectAll("rect")
|
||||||
.on("click", pickerFillClicked)
|
.on("click", pickerFillClicked)
|
||||||
.on("mousemove", () => tip("Click to fill with the hatching"));
|
.on("mouseover", function() { tip("Click to fill with the hatching " + this.id) });
|
||||||
|
|
||||||
// append box
|
// append box
|
||||||
const bbox = picker.node().getBBox();
|
const bbox = picker.node().getBBox();
|
||||||
|
|
@ -544,10 +544,10 @@ function createPicker() {
|
||||||
.attr("fill", "#ffffff")
|
.attr("fill", "#ffffff")
|
||||||
.attr("stroke", "#5d4651")
|
.attr("stroke", "#5d4651")
|
||||||
.on("mousemove", pos);
|
.on("mousemove", pos);
|
||||||
picker.insert("text", ":first-child").attr("x", 291).attr("y", -10).attr("id", "pickerCloseText").text("✕");
|
picker.insert("text", ":first-child").attr("x", width-20).attr("y", -10).attr("id", "pickerCloseText").text("✕");
|
||||||
picker
|
picker
|
||||||
.insert("rect", ":first-child")
|
.insert("rect", ":first-child")
|
||||||
.attr("x", 288)
|
.attr("x", width-23)
|
||||||
.attr("y", -21)
|
.attr("y", -21)
|
||||||
.attr("id", "pickerCloseRect")
|
.attr("id", "pickerCloseRect")
|
||||||
.attr("width", 14)
|
.attr("width", 14)
|
||||||
|
|
|
||||||
|
|
@ -70,7 +70,8 @@ function mouseMove() {
|
||||||
const point = d3.mouse(this);
|
const point = d3.mouse(this);
|
||||||
const i = findCell(point[0], point[1]); // pack cell id
|
const i = findCell(point[0], point[1]); // pack cell id
|
||||||
if (i === undefined) return;
|
if (i === undefined) return;
|
||||||
showNotes(d3.event, i);
|
|
||||||
|
showNotes(d3.event);
|
||||||
const g = findGridCell(point[0], point[1]); // grid cell id
|
const g = findGridCell(point[0], point[1]); // grid cell id
|
||||||
if (tooltip.dataset.main) showMainTip();
|
if (tooltip.dataset.main) showMainTip();
|
||||||
else showMapTooltip(point, d3.event, i, g);
|
else showMapTooltip(point, d3.event, i, g);
|
||||||
|
|
@ -78,7 +79,7 @@ function mouseMove() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// show note box on hover (if any)
|
// show note box on hover (if any)
|
||||||
function showNotes(e, i) {
|
function showNotes(e) {
|
||||||
if (notesEditor.offsetParent) return;
|
if (notesEditor.offsetParent) return;
|
||||||
let id = e.target.id || e.target.parentNode.id || e.target.parentNode.parentNode.id;
|
let id = e.target.id || e.target.parentNode.id || e.target.parentNode.parentNode.id;
|
||||||
if (e.target.parentNode.parentNode.id === "burgLabels") id = "burg" + e.target.dataset.id;
|
if (e.target.parentNode.parentNode.id === "burgLabels") id = "burg" + e.target.dataset.id;
|
||||||
|
|
|
||||||
|
|
@ -913,11 +913,9 @@ function editHeightmap() {
|
||||||
|
|
||||||
function uploadTemplate(dataLoaded) {
|
function uploadTemplate(dataLoaded) {
|
||||||
const steps = dataLoaded.split("\r\n");
|
const steps = dataLoaded.split("\r\n");
|
||||||
if (!steps.length) {
|
if (!steps.length) return tip("Cannot parse the template, please check the file", false, "error");
|
||||||
tip("Cannot parse the template, please check the file", false, "error");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
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) {
|
if (step.length !== 5) {
|
||||||
|
|
@ -1318,10 +1316,10 @@ function editHeightmap() {
|
||||||
img.onload = function () {
|
img.onload = function () {
|
||||||
const canvas = document.createElement("canvas");
|
const canvas = document.createElement("canvas");
|
||||||
const ctx = canvas.getContext("2d");
|
const ctx = canvas.getContext("2d");
|
||||||
canvas.width = svgWidth;
|
canvas.width = graphWidth;
|
||||||
canvas.height = svgHeight;
|
canvas.height = graphHeight;
|
||||||
document.body.insertBefore(canvas, optionsContainer);
|
document.body.insertBefore(canvas, optionsContainer);
|
||||||
ctx.drawImage(img, 0, 0, svgWidth, svgHeight);
|
ctx.drawImage(img, 0, 0, graphWidth, graphHeight);
|
||||||
const imgBig = canvas.toDataURL("image/png");
|
const imgBig = canvas.toDataURL("image/png");
|
||||||
const link = document.createElement("a");
|
const link = document.createElement("a");
|
||||||
link.download = getFileName("Heightmap") + ".png";
|
link.download = getFileName("Heightmap") + ".png";
|
||||||
|
|
|
||||||
|
|
@ -536,12 +536,11 @@ class Planimeter extends Measurer {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Scale bar
|
// Scale bar
|
||||||
function drawScaleBar(requestedScale) {
|
function drawScaleBar(scaleLevel) {
|
||||||
if (scaleBar.style("display") === "none") return; // no need to re-draw hidden element
|
if (scaleBar.style("display") === "none") return; // no need to re-draw hidden element
|
||||||
scaleBar.selectAll("*").remove(); // fully redraw every time
|
scaleBar.selectAll("*").remove(); // fully redraw every time
|
||||||
const scaleLevel = requestedScale || scale;
|
|
||||||
|
|
||||||
const distanceScale = distanceScaleInput.value;
|
const distanceScale = +distanceScaleInput.value;
|
||||||
const unit = distanceUnitInput.value;
|
const unit = distanceUnitInput.value;
|
||||||
const size = +barSizeInput.value;
|
const size = +barSizeInput.value;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -75,12 +75,9 @@ function overviewMilitary() {
|
||||||
const sortData = options.military.map(u => `data-${u.name}="${getForces(u)}"`).join(" ");
|
const sortData = options.military.map(u => `data-${u.name}="${getForces(u)}"`).join(" ");
|
||||||
const lineData = options.military.map(u => `<div data-type="${u.name}" data-tip="State ${u.name} units number">${getForces(u)}</div>`).join(" ");
|
const lineData = options.military.map(u => `<div data-type="${u.name}" data-tip="State ${u.name} units number">${getForces(u)}</div>`).join(" ");
|
||||||
|
|
||||||
lines += `<div class="states" data-id=${s.i} data-state="${
|
lines += `<div class="states" data-id=${s.i} data-state="${s.name}" ${sortData} data-total="${total}"
|
||||||
s.name
|
data-population="${population}" data-rate="${rate}" data-alert="${s.alert}">
|
||||||
}" ${sortData} data-total="${total}" data-population="${population}" data-rate="${rate}" data-alert="${s.alert}">
|
<fill-box data-tip="${s.fullName}" fill="${s.color}" disabled></fill-box>
|
||||||
<svg data-tip="${s.fullName}" 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="${s.fullName}" style="width:6em" value="${s.name}" readonly>
|
<input data-tip="${s.fullName}" style="width:6em" value="${s.name}" readonly>
|
||||||
${lineData}
|
${lineData}
|
||||||
<div data-type="total" data-tip="Total state military personnel (considering crew)" style="font-weight: bold">${si(total)}</div>
|
<div data-type="total" data-tip="Total state military personnel (considering crew)" style="font-weight: bold">${si(total)}</div>
|
||||||
|
|
|
||||||
|
|
@ -1,25 +1,22 @@
|
||||||
"use strict";
|
"use strict";
|
||||||
|
|
||||||
function editNotes(id, name) {
|
function editNotes(id, name) {
|
||||||
|
// elements
|
||||||
|
const notesLegend = document.getElementById("notesLegend");
|
||||||
|
const notesName = document.getElementById("notesName");
|
||||||
|
const notesSelect = document.getElementById("notesSelect");
|
||||||
|
const notesPin = document.getElementById("notesPin");
|
||||||
|
|
||||||
// update list of objects
|
// update list of objects
|
||||||
const select = document.getElementById("notesSelect");
|
notesSelect.options.length = 0;
|
||||||
select.options.length = 0;
|
|
||||||
for (const note of notes) {
|
for (const note of notes) {
|
||||||
select.options.add(new Option(note.id, note.id));
|
notesSelect.options.add(new Option(note.id, note.id));
|
||||||
}
|
}
|
||||||
|
|
||||||
// initiate pell (html editor)
|
// update pin notes icon
|
||||||
const notesText = document.getElementById("notesText");
|
const notesArePinned = options.pinNotes;
|
||||||
notesText.innerHTML = "";
|
if (notesArePinned) notesPin.classList.add("pressed");
|
||||||
const editor = Pell.init({
|
else notesPin.classList.remove("pressed");
|
||||||
element: notesText,
|
|
||||||
onChange: html => {
|
|
||||||
const note = notes.find(note => note.id === select.value);
|
|
||||||
if (!note) return;
|
|
||||||
note.legend = html;
|
|
||||||
showNote(note);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
// select an object
|
// select an object
|
||||||
if (notes.length || id) {
|
if (notes.length || id) {
|
||||||
|
|
@ -29,136 +26,161 @@ function editNotes(id, name) {
|
||||||
if (!name) name = id;
|
if (!name) name = id;
|
||||||
note = {id, name, legend: ""};
|
note = {id, name, legend: ""};
|
||||||
notes.push(note);
|
notes.push(note);
|
||||||
select.options.add(new Option(id, id));
|
notesSelect.options.add(new Option(id, id));
|
||||||
}
|
}
|
||||||
select.value = id;
|
|
||||||
notesName.value = note.name;
|
notesSelect.value = id;
|
||||||
editor.content.innerHTML = note.legend;
|
notesName.value = note.name;
|
||||||
showNote(note);
|
notesLegend.innerHTML = note.legend;
|
||||||
} else {
|
initEditor();
|
||||||
editor.content.innerHTML = "There are no added notes. Click on element (e.g. label) and add a free text note";
|
updateNotesBox(note);
|
||||||
document.getElementById("notesName").value = "";
|
} else {
|
||||||
|
// if notes array is empty
|
||||||
|
notesName.value = "";
|
||||||
|
notesLegend.innerHTML = "No notes added. Click on an element (e.g. label or marker) and add a free text note";
|
||||||
}
|
}
|
||||||
|
|
||||||
// open a dialog
|
|
||||||
$("#notesEditor").dialog({
|
$("#notesEditor").dialog({
|
||||||
title: "Notes Editor",
|
title: "Notes Editor",
|
||||||
minWidth: "40em",
|
width: "70vw",
|
||||||
width: "50vw",
|
height: window.innerHeight * 0.75,
|
||||||
position: {my: "center", at: "center", of: "svg"}
|
position: {my: "center", at: "center", of: "svg"},
|
||||||
|
close: removeEditor
|
||||||
});
|
});
|
||||||
|
$("[aria-describedby='notesEditor']").css("top", "10vh");
|
||||||
|
|
||||||
if (modules.editNotes) return;
|
if (modules.editNotes) return;
|
||||||
modules.editNotes = true;
|
modules.editNotes = true;
|
||||||
|
|
||||||
// add listeners
|
// add listeners
|
||||||
document.getElementById("notesSelect").addEventListener("change", changeObject);
|
document.getElementById("notesSelect").addEventListener("change", changeElement);
|
||||||
document.getElementById("notesName").addEventListener("input", changeName);
|
document.getElementById("notesName").addEventListener("input", changeName);
|
||||||
document.getElementById("notesPin").addEventListener("click", () => (options.pinNotes = !options.pinNotes));
|
document.getElementById("notesLegend").addEventListener("blur", updateLegend);
|
||||||
document.getElementById("notesSpeak").addEventListener("click", () => speak(editor.content.innerHTML));
|
document.getElementById("notesPin").addEventListener("click", toggleNotesPin);
|
||||||
document.getElementById("notesFocus").addEventListener("click", validateHighlightElement);
|
document.getElementById("notesFocus").addEventListener("click", validateHighlightElement);
|
||||||
document.getElementById("notesDownload").addEventListener("click", downloadLegends);
|
document.getElementById("notesDownload").addEventListener("click", downloadLegends);
|
||||||
document.getElementById("notesUpload").addEventListener("click", () => legendsToLoad.click());
|
document.getElementById("notesUpload").addEventListener("click", () => legendsToLoad.click());
|
||||||
document.getElementById("legendsToLoad").addEventListener("change", function () {
|
document.getElementById("legendsToLoad").addEventListener("change", function () {
|
||||||
uploadFile(this, uploadLegends);
|
uploadFile(this, uploadLegends);
|
||||||
});
|
});
|
||||||
document.getElementById("notesClearStyle").addEventListener("click", clearStyle);
|
|
||||||
document.getElementById("notesRemove").addEventListener("click", triggerNotesRemove);
|
document.getElementById("notesRemove").addEventListener("click", triggerNotesRemove);
|
||||||
|
|
||||||
function showNote(note) {
|
async function initEditor() {
|
||||||
document.getElementById("notes").style.display = "block";
|
if (!window.tinymce) {
|
||||||
|
const url = "https://cdn.tiny.cloud/1/4i6a79ymt2y0cagke174jp3meoi28vyecrch12e5puyw3p9a/tinymce/5/tinymce.min.js";
|
||||||
|
try {
|
||||||
|
await import(url);
|
||||||
|
} catch (error) {
|
||||||
|
// error may be caused by failed request being cached, try again with random hash
|
||||||
|
try {
|
||||||
|
const hash = Math.random().toString(36).substring(2, 15);
|
||||||
|
await import(`${url}#${hash}`);
|
||||||
|
} catch (error) {
|
||||||
|
console.error(error);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (window.tinymce) {
|
||||||
|
tinymce.init({
|
||||||
|
selector: "#notesLegend",
|
||||||
|
height: "90%",
|
||||||
|
menubar: false,
|
||||||
|
plugins: `autolink lists link charmap print formatpainter casechange code fullscreen image link media table paste hr checklist wordcount`,
|
||||||
|
toolbar: `code | undo redo | bold italic strikethrough | forecolor backcolor | formatpainter removeformat | alignleft aligncenter alignright alignjustify | bullist numlist outdent indent | link image media table | fontselect fontsizeselect | blockquote hr casechange checklist charmap | print fullscreen`,
|
||||||
|
media_alt_source: false,
|
||||||
|
media_poster: false,
|
||||||
|
setup: editor => {
|
||||||
|
editor.on("Change", updateLegend);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function updateLegend() {
|
||||||
|
const note = notes.find(note => note.id === notesSelect.value);
|
||||||
|
if (!note) return tip("Note element is not found", true, "error", 4000);
|
||||||
|
|
||||||
|
const isTinyEditorActive = window.tinymce?.activeEditor;
|
||||||
|
note.legend = isTinyEditorActive ? tinymce.activeEditor.getContent() : notesLegend.innerHTML;
|
||||||
|
updateNotesBox(note);
|
||||||
|
}
|
||||||
|
|
||||||
|
function updateNotesBox(note) {
|
||||||
document.getElementById("notesHeader").innerHTML = note.name;
|
document.getElementById("notesHeader").innerHTML = note.name;
|
||||||
document.getElementById("notesBody").innerHTML = note.legend;
|
document.getElementById("notesBody").innerHTML = note.legend;
|
||||||
}
|
}
|
||||||
|
|
||||||
function changeObject() {
|
function changeElement() {
|
||||||
const note = notes.find(note => note.id === this.value);
|
const note = notes.find(note => note.id === this.value);
|
||||||
if (!note) return;
|
if (!note) return tip("Note element is not found", true, "error", 4000);
|
||||||
|
|
||||||
notesName.value = note.name;
|
notesName.value = note.name;
|
||||||
editor.content.innerHTML = note.legend;
|
notesLegend.innerHTML = note.legend;
|
||||||
|
updateNotesBox(note);
|
||||||
|
|
||||||
|
if (window.tinymce) tinymce.activeEditor.setContent(note.legend);
|
||||||
}
|
}
|
||||||
|
|
||||||
function changeName() {
|
function changeName() {
|
||||||
const id = document.getElementById("notesSelect").value;
|
const note = notes.find(note => note.id === notesSelect.value);
|
||||||
const note = notes.find(note => note.id === id);
|
if (!note) return tip("Note element is not found", true, "error", 4000);
|
||||||
if (!note) return;
|
|
||||||
note.name = this.value;
|
note.name = this.value;
|
||||||
showNote(note);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function validateHighlightElement() {
|
function validateHighlightElement() {
|
||||||
const select = document.getElementById("notesSelect");
|
const element = document.getElementById(notesSelect.value);
|
||||||
const element = document.getElementById(select.value);
|
if (element) return highlightElement(element, 3);
|
||||||
|
|
||||||
// if element is not found
|
confirmationDialog({
|
||||||
if (element === null) {
|
|
||||||
alertMessage.innerHTML = "Related element is not found. Would you like to remove the note?";
|
|
||||||
$("#alert").dialog({
|
|
||||||
resizable: false,
|
|
||||||
title: "Element not found",
|
title: "Element not found",
|
||||||
buttons: {
|
message: "Note element is not found. Would you like to remove the note?",
|
||||||
Remove: function () {
|
confirm: "Remove",
|
||||||
$(this).dialog("close");
|
cancel: "Keep",
|
||||||
removeLegend();
|
onConfirm: removeLegend
|
||||||
},
|
|
||||||
Keep: function () {
|
|
||||||
$(this).dialog("close");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
highlightElement(element, 3); // if element is found
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function downloadLegends() {
|
function downloadLegends() {
|
||||||
const data = JSON.stringify(notes);
|
const notesData = JSON.stringify(notes);
|
||||||
const name = getFileName("Notes") + ".txt";
|
const name = getFileName("Notes") + ".txt";
|
||||||
downloadFile(data, name);
|
downloadFile(notesData, name);
|
||||||
}
|
}
|
||||||
|
|
||||||
function uploadLegends(dataLoaded) {
|
function uploadLegends(dataLoaded) {
|
||||||
if (!dataLoaded) {
|
if (!dataLoaded) return tip("Cannot load the file. Please check the data format", false, "error");
|
||||||
tip("Cannot load the file. Please check the data format", false, "error");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
notes = JSON.parse(dataLoaded);
|
notes = JSON.parse(dataLoaded);
|
||||||
document.getElementById("notesSelect").options.length = 0;
|
notesSelect.options.length = 0;
|
||||||
editNotes(notes[0].id, notes[0].name);
|
editNotes(notes[0].id, notes[0].name);
|
||||||
}
|
}
|
||||||
|
|
||||||
function clearStyle() {
|
|
||||||
editor.content.innerHTML = editor.content.textContent;
|
|
||||||
}
|
|
||||||
|
|
||||||
function triggerNotesRemove() {
|
function triggerNotesRemove() {
|
||||||
alertMessage.innerHTML = "Are you sure you want to remove the selected note?";
|
confirmationDialog({
|
||||||
$("#alert").dialog({
|
|
||||||
resizable: false,
|
|
||||||
title: "Remove note",
|
title: "Remove note",
|
||||||
buttons: {
|
message: "Are you sure you want to remove the selected note? There is no way to undo this action",
|
||||||
Remove: function () {
|
confirm: "Remove",
|
||||||
$(this).dialog("close");
|
onConfirm: removeLegend
|
||||||
removeLegend();
|
|
||||||
},
|
|
||||||
Keep: function () {
|
|
||||||
$(this).dialog("close");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
function removeLegend() {
|
function removeLegend() {
|
||||||
const select = document.getElementById("notesSelect");
|
const index = notes.findIndex(n => n.id === notesSelect.value);
|
||||||
const index = notes.findIndex(n => n.id === select.value);
|
|
||||||
notes.splice(index, 1);
|
notes.splice(index, 1);
|
||||||
select.options.length = 0;
|
notesSelect.options.length = 0;
|
||||||
if (!notes.length) {
|
if (!notes.length) {
|
||||||
$("#notesEditor").dialog("close");
|
$("#notesEditor").dialog("close");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
notesText.innerHTML = "";
|
|
||||||
editNotes(notes[0].id, notes[0].name);
|
editNotes(notes[0].id, notes[0].name);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function toggleNotesPin() {
|
||||||
|
options.pinNotes = !options.pinNotes;
|
||||||
|
this.classList.toggle("pressed");
|
||||||
|
}
|
||||||
|
|
||||||
|
function removeEditor() {
|
||||||
|
if (window.tinymce) tinymce.remove();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -103,7 +103,9 @@ function showSupporters() {
|
||||||
Mike Conley,Xavier privé,Hope You're Well,Mark Sprietsma,Robert Landry,Nick Mowry,steve hall,Markell,Josh Wren,Neutrix,BLRageQuit,Rocky,
|
Mike Conley,Xavier privé,Hope You're Well,Mark Sprietsma,Robert Landry,Nick Mowry,steve hall,Markell,Josh Wren,Neutrix,BLRageQuit,Rocky,
|
||||||
Dario Spadavecchia,Bas Kroot,John Patrick Callahan Jr,Alexandra Vesey,D,Exp1nt,james,Braxton Istace,w,Rurikid,AntiBlock,Redsauz,BigE0021,
|
Dario Spadavecchia,Bas Kroot,John Patrick Callahan Jr,Alexandra Vesey,D,Exp1nt,james,Braxton Istace,w,Rurikid,AntiBlock,Redsauz,BigE0021,
|
||||||
Jonathan Williams,ojacid .,Brian Wilson,A Patreon of the Ahts,Shubham Jakhotiya,www15o,Jan Bundesmann,Angelique Badger,Joshua Xiong,Moist mongol,
|
Jonathan Williams,ojacid .,Brian Wilson,A Patreon of the Ahts,Shubham Jakhotiya,www15o,Jan Bundesmann,Angelique Badger,Joshua Xiong,Moist mongol,
|
||||||
Frank Fewkes,jason baldrick,Game Master Pro,Andrew Kircher,Preston Mitchell,Chris Kohut`;
|
Frank Fewkes,jason baldrick,Game Master Pro,Andrew Kircher,Preston Mitchell,Chris Kohut,Emarandzeb,Trentin Bergeron,Damon Gallaty,Pleaseworkforonce,
|
||||||
|
Jordan,William Markus,Sidr Dim,Alexander Whittaker,The Next Level,Patrick Valverde,Markus Peham,Daniel Cooper,the Beagles of Neorbus,Marley Moule,
|
||||||
|
Maximilian Schielke,Johnathan Xavier Hutchinson,Ele,Rita`;
|
||||||
|
|
||||||
const array = supporters
|
const array = supporters
|
||||||
.replace(/(?:\r\n|\r|\n)/g, "")
|
.replace(/(?:\r\n|\r|\n)/g, "")
|
||||||
|
|
@ -304,10 +306,8 @@ function showSeedHistoryDialog() {
|
||||||
|
|
||||||
// generate map with historical seed
|
// generate map with historical seed
|
||||||
function restoreSeed(id) {
|
function restoreSeed(id) {
|
||||||
if (mapHistory[id].seed == seed) {
|
if (mapHistory[id].seed == seed) return tip("The current map is already generated with this seed", null, "error");
|
||||||
tip("The current map is already generated with this seed", null, "error");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
optionsSeed.value = mapHistory[id].seed;
|
optionsSeed.value = mapHistory[id].seed;
|
||||||
mapWidthInput.value = mapHistory[id].width;
|
mapWidthInput.value = mapHistory[id].width;
|
||||||
mapHeightInput.value = mapHistory[id].height;
|
mapHeightInput.value = mapHistory[id].height;
|
||||||
|
|
@ -545,7 +545,7 @@ function randomizeOptions() {
|
||||||
|
|
||||||
// 'Options' settings
|
// 'Options' settings
|
||||||
if (randomize || !locked("template")) randomizeHeightmapTemplate();
|
if (randomize || !locked("template")) randomizeHeightmapTemplate();
|
||||||
if (randomize || !locked("regions")) regionsInput.value = regionsOutput.value = gauss(15, 3, 2, 30);
|
if (randomize || !locked("regions")) regionsInput.value = regionsOutput.value = gauss(18, 5, 2, 30);
|
||||||
if (randomize || !locked("provinces")) provincesInput.value = provincesOutput.value = gauss(20, 10, 20, 100);
|
if (randomize || !locked("provinces")) provincesInput.value = provincesOutput.value = gauss(20, 10, 20, 100);
|
||||||
if (randomize || !locked("manors")) {
|
if (randomize || !locked("manors")) {
|
||||||
manorsInput.value = 1000;
|
manorsInput.value = 1000;
|
||||||
|
|
@ -736,8 +736,14 @@ async function showLoadPane() {
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// already connected to Dropbox: list saved maps
|
||||||
|
if (Cloud.providers.dropbox.api) {
|
||||||
|
document.getElementById("dropboxConnectButton").style.display = "none";
|
||||||
|
document.getElementById("loadFromDropboxSelect").style.display = "block";
|
||||||
const loadFromDropboxButtons = document.getElementById("loadFromDropboxButtons");
|
const loadFromDropboxButtons = document.getElementById("loadFromDropboxButtons");
|
||||||
const fileSelect = document.getElementById("loadFromDropboxSelect");
|
const fileSelect = document.getElementById("loadFromDropboxSelect");
|
||||||
|
fileSelect.innerHTML = `<option value="" disabled selected>Loading...</option>`;
|
||||||
|
|
||||||
const files = await Cloud.providers.dropbox.list();
|
const files = await Cloud.providers.dropbox.list();
|
||||||
|
|
||||||
if (!files) {
|
if (!files) {
|
||||||
|
|
@ -754,6 +760,19 @@ async function showLoadPane() {
|
||||||
opt.value = file.path;
|
opt.value = file.path;
|
||||||
fileSelect.appendChild(opt);
|
fileSelect.appendChild(opt);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// not connected to Dropbox: show connect button
|
||||||
|
document.getElementById("dropboxConnectButton").style.display = "inline-block";
|
||||||
|
document.getElementById("loadFromDropboxButtons").style.display = "none";
|
||||||
|
document.getElementById("loadFromDropboxSelect").style.display = "none";
|
||||||
|
}
|
||||||
|
|
||||||
|
async function connectToDropbox() {
|
||||||
|
await Cloud.providers.dropbox.initialize();
|
||||||
|
if (Cloud.providers.dropbox.api) showLoadPane();
|
||||||
}
|
}
|
||||||
|
|
||||||
function loadURL() {
|
function loadURL() {
|
||||||
|
|
|
||||||
|
|
@ -44,7 +44,8 @@ function editProvinces() {
|
||||||
cl = el.classList,
|
cl = el.classList,
|
||||||
line = el.parentNode,
|
line = el.parentNode,
|
||||||
p = +line.dataset.id;
|
p = +line.dataset.id;
|
||||||
if (cl.contains("fillRect")) changeFill(el);
|
|
||||||
|
if (el.tagName === "FILL-BOX") changeFill(el);
|
||||||
else if (cl.contains("name")) editProvinceName(p);
|
else if (cl.contains("name")) editProvinceName(p);
|
||||||
else if (cl.contains("coaIcon")) editEmblem("province", "provinceCOA" + p, pack.provinces[p]);
|
else if (cl.contains("coaIcon")) editEmblem("province", "provinceCOA" + p, pack.provinces[p]);
|
||||||
else if (cl.contains("icon-star-empty")) capitalZoomIn(p);
|
else if (cl.contains("icon-star-empty")) capitalZoomIn(p);
|
||||||
|
|
@ -133,9 +134,7 @@ function editProvinces() {
|
||||||
lines += `<div class="states" data-id=${p.i} data-name="${p.name}" data-form="${p.formName}" data-color="${
|
lines += `<div class="states" data-id=${p.i} data-name="${p.name}" data-form="${p.formName}" data-color="${
|
||||||
p.color
|
p.color
|
||||||
}" data-capital="${capital}" data-state="${stateName}" data-area=${area} data-population=${population}>
|
}" 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="${
|
<fill-box fill="${p.color}"></fill-box>
|
||||||
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>
|
||||||
<svg data-tip="Click to show and edit province emblem" class="coaIcon pointer hide" viewBox="0 0 200 200"><use href="#provinceCOA${p.i}"></use></svg>
|
<svg data-tip="Click to show and edit province emblem" class="coaIcon pointer hide" viewBox="0 0 200 200"><use href="#provinceCOA${p.i}"></use></svg>
|
||||||
<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>
|
||||||
|
|
@ -215,14 +214,14 @@ function editProvinces() {
|
||||||
|
|
||||||
function changeFill(el) {
|
function changeFill(el) {
|
||||||
const currentFill = el.getAttribute("fill");
|
const currentFill = el.getAttribute("fill");
|
||||||
const p = +el.parentNode.parentNode.dataset.id;
|
const p = +el.parentNode.dataset.id;
|
||||||
|
|
||||||
const callback = function (fill) {
|
const callback = newFill => {
|
||||||
el.setAttribute("fill", fill);
|
el.fill = newFill;
|
||||||
pack.provinces[p].color = fill;
|
pack.provinces[p].color = newFill;
|
||||||
const g = provs.select("#provincesBody");
|
const g = provs.select("#provincesBody");
|
||||||
g.select("#province" + p).attr("fill", fill);
|
g.select("#province" + p).attr("fill", newFill);
|
||||||
g.select("#province-gap" + p).attr("stroke", fill);
|
g.select("#province-gap" + p).attr("stroke", newFill);
|
||||||
};
|
};
|
||||||
|
|
||||||
openPicker(currentFill, callback);
|
openPicker(currentFill, callback);
|
||||||
|
|
|
||||||
|
|
@ -14,7 +14,9 @@ function overviewRegiments(state) {
|
||||||
updateHeaders();
|
updateHeaders();
|
||||||
|
|
||||||
$("#regimentsOverview").dialog({
|
$("#regimentsOverview").dialog({
|
||||||
title: "Regiments Overview", resizable: false, width: fitContent(),
|
title: "Regiments Overview",
|
||||||
|
resizable: false,
|
||||||
|
width: fitContent(),
|
||||||
position: {my: "right top", at: "right-10 top+10", of: "svg", collision: "fit"}
|
position: {my: "right top", at: "right-10 top+10", of: "svg", collision: "fit"}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
@ -31,11 +33,13 @@ function overviewRegiments(state) {
|
||||||
header.querySelectorAll(".removable").forEach(el => el.remove());
|
header.querySelectorAll(".removable").forEach(el => el.remove());
|
||||||
const insert = html => document.getElementById("regimentsTotal").insertAdjacentHTML("beforebegin", html);
|
const insert = html => document.getElementById("regimentsTotal").insertAdjacentHTML("beforebegin", html);
|
||||||
for (const u of options.military) {
|
for (const u of options.military) {
|
||||||
const label = capitalize(u.name.replace(/_/g, ' '));
|
const label = capitalize(u.name.replace(/_/g, " "));
|
||||||
insert(`<div data-tip="Regiment ${u.name} units number. Click to sort" class="sortable removable" data-sortby="${u.name}">${label} </div>`);
|
insert(`<div data-tip="Regiment ${u.name} units number. Click to sort" class="sortable removable" data-sortby="${u.name}">${label} </div>`);
|
||||||
}
|
}
|
||||||
header.querySelectorAll(".removable").forEach(function (e) {
|
header.querySelectorAll(".removable").forEach(function (e) {
|
||||||
e.addEventListener("click", function() {sortLines(this);});
|
e.addEventListener("click", function () {
|
||||||
|
sortLines(this);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -52,10 +56,12 @@ function overviewRegiments(state) {
|
||||||
|
|
||||||
for (const r of s.military) {
|
for (const r of s.military) {
|
||||||
const sortData = options.military.map(u => `data-${u.name}=${r.u[u.name] || 0}`).join(" ");
|
const sortData = options.military.map(u => `data-${u.name}=${r.u[u.name] || 0}`).join(" ");
|
||||||
const lineData = options.military.map(u => `<div data-type="${u.name}" data-tip="${capitalize(u.name)} units number">${r.u[u.name]||0}</div>`).join(" ");
|
const lineData = options.military
|
||||||
|
.map(u => `<div data-type="${u.name}" data-tip="${capitalize(u.name)} units number">${r.u[u.name] || 0}</div>`)
|
||||||
|
.join(" ");
|
||||||
|
|
||||||
lines += `<div class="states" data-id=${r.i} data-s="${s.i}" data-state="${s.name}" data-name="${r.name}" ${sortData} data-total="${r.a}">
|
lines += `<div class="states" data-id=${r.i} data-s="${s.i}" data-state="${s.name}" data-name="${r.name}" ${sortData} data-total="${r.a}">
|
||||||
<svg data-tip="${s.fullName}" width=".9em" height=".9em" style="margin-bottom:-1px"><rect x="0" y="0" width="100%" height="100%" fill="${s.color}" class="fillRect"></svg>
|
<fill-box data-tip="${s.fullName}" fill="${s.color}" disabled></fill-box>
|
||||||
<input data-tip="${s.fullName}" style="width:6em" value="${s.name}" readonly>
|
<input data-tip="${s.fullName}" style="width:6em" value="${s.name}" readonly>
|
||||||
<span data-tip="Regiment's emblem" style="width:1em">${r.icon}</span>
|
<span data-tip="Regiment's emblem" style="width:1em">${r.icon}</span>
|
||||||
<input data-tip="Regiment's name" style="width:13em" value="${r.name}" readonly>
|
<input data-tip="Regiment's name" style="width:13em" value="${r.name}" readonly>
|
||||||
|
|
@ -75,7 +81,10 @@ function overviewRegiments(state) {
|
||||||
</div>`;
|
</div>`;
|
||||||
|
|
||||||
body.insertAdjacentHTML("beforeend", lines);
|
body.insertAdjacentHTML("beforeend", lines);
|
||||||
if (body.dataset.type === "percentage") {body.dataset.type = "absolute"; togglePercentageMode();}
|
if (body.dataset.type === "percentage") {
|
||||||
|
body.dataset.type = "absolute";
|
||||||
|
togglePercentageMode();
|
||||||
|
}
|
||||||
applySorting(regimentsHeader);
|
applySorting(regimentsHeader);
|
||||||
|
|
||||||
// add listeners
|
// add listeners
|
||||||
|
|
@ -87,7 +96,7 @@ function overviewRegiments(state) {
|
||||||
const filter = document.getElementById("regimentsFilter");
|
const filter = document.getElementById("regimentsFilter");
|
||||||
filter.options.length = 0; // remove all options
|
filter.options.length = 0; // remove all options
|
||||||
filter.options.add(new Option(`all`, -1, false, state === -1));
|
filter.options.add(new Option(`all`, -1, false, state === -1));
|
||||||
const statesSorted = pack.states.filter(s => s.i && !s.removed).sort((a, b) => (a.name > b.name) ? 1 : -1);
|
const statesSorted = pack.states.filter(s => s.i && !s.removed).sort((a, b) => (a.name > b.name ? 1 : -1));
|
||||||
statesSorted.forEach(s => filter.options.add(new Option(s.name, s.i, false, s.i == state)));
|
statesSorted.forEach(s => filter.options.add(new Option(s.name, s.i, false, s.i == state)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -108,19 +117,20 @@ function overviewRegiments(state) {
|
||||||
if (body.dataset.type === "absolute") {
|
if (body.dataset.type === "absolute") {
|
||||||
body.dataset.type = "percentage";
|
body.dataset.type = "percentage";
|
||||||
const lines = body.querySelectorAll(":scope > div:not(.totalLine)");
|
const lines = body.querySelectorAll(":scope > div:not(.totalLine)");
|
||||||
const array = Array.from(lines), cache = [];
|
const array = Array.from(lines),
|
||||||
|
cache = [];
|
||||||
|
|
||||||
const total = function (type) {
|
const total = function (type) {
|
||||||
if (cache[type]) cache[type];
|
if (cache[type]) cache[type];
|
||||||
cache[type] = d3.sum(array.map(el => +el.dataset[type]));
|
cache[type] = d3.sum(array.map(el => +el.dataset[type]));
|
||||||
return cache[type];
|
return cache[type];
|
||||||
}
|
};
|
||||||
|
|
||||||
lines.forEach(function (el) {
|
lines.forEach(function (el) {
|
||||||
el.querySelectorAll("div").forEach(function (div) {
|
el.querySelectorAll("div").forEach(function (div) {
|
||||||
const type = div.dataset.type;
|
const type = div.dataset.type;
|
||||||
if (type === "rate") return;
|
if (type === "rate") return;
|
||||||
div.textContent = total(type) ? rn(+el.dataset[type] / total(type) * 100) + "%" : "0%";
|
div.textContent = total(type) ? rn((+el.dataset[type] / total(type)) * 100) + "%" : "0%";
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
|
|
@ -145,11 +155,15 @@ function overviewRegiments(state) {
|
||||||
|
|
||||||
function addRegimentOnClick() {
|
function addRegimentOnClick() {
|
||||||
const state = +regimentsFilter.value;
|
const state = +regimentsFilter.value;
|
||||||
if (state === -1) {tip("Please select state from the list", false, "error"); return;}
|
if (state === -1) {
|
||||||
|
tip("Please select state from the list", false, "error");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
const point = d3.mouse(this);
|
const point = d3.mouse(this);
|
||||||
const cell = findCell(point[0], point[1]);
|
const cell = findCell(point[0], point[1]);
|
||||||
const x = pack.cells.p[cell][0], y = pack.cells.p[cell][1];
|
const x = pack.cells.p[cell][0],
|
||||||
|
y = pack.cells.p[cell][1];
|
||||||
const military = pack.states[state].military;
|
const military = pack.states[state].military;
|
||||||
const i = military.length ? last(military).i + 1 : 0;
|
const i = military.length ? last(military).i + 1 : 0;
|
||||||
const n = +(pack.cells.h[cell] < 20); // naval or land
|
const n = +(pack.cells.h[cell] < 20); // naval or land
|
||||||
|
|
@ -176,5 +190,4 @@ function overviewRegiments(state) {
|
||||||
const name = getFileName("Regiments") + ".csv";
|
const name = getFileName("Regiments") + ".csv";
|
||||||
downloadFile(data, name);
|
downloadFile(data, name);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
@ -79,7 +79,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="fillRect pointer"></svg>
|
<fill-box fill="${r.color}"></fill-box>
|
||||||
<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">
|
||||||
|
|
@ -93,7 +93,9 @@ function editReligions() {
|
||||||
</div>`;
|
</div>`;
|
||||||
} else {
|
} else {
|
||||||
// No religion (neutral) line
|
// No religion (neutral) line
|
||||||
lines += `<div class="states" data-id=${r.i} data-name="${r.name}" data-color="" data-area=${area} data-population=${population} data-type="" data-form="" data-deity="" data-expansionism="">
|
lines += `<div class="states" data-id=${r.i} data-name="${
|
||||||
|
r.name
|
||||||
|
}" data-color="" data-area=${area} data-population=${population} data-type="" data-form="" data-deity="" data-expansionism="">
|
||||||
<svg width="9" height="9" class="placeholder"></svg>
|
<svg width="9" height="9" class="placeholder"></svg>
|
||||||
<input data-tip="Religion name. Click and type to change" class="religionName italic" value="${r.name}" autocorrect="off" spellcheck="false">
|
<input data-tip="Religion name. Click and type to change" class="religionName italic" value="${r.name}" autocorrect="off" spellcheck="false">
|
||||||
<select data-tip="Religion type" class="religionType placeholder">${getTypeOptions(r.type)}</select>
|
<select data-tip="Religion type" class="religionType placeholder">${getTypeOptions(r.type)}</select>
|
||||||
|
|
@ -124,7 +126,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.fillRect").forEach(el => el.addEventListener("click", religionChangeColor));
|
body.querySelectorAll("fill-box").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));
|
||||||
|
|
@ -215,13 +217,13 @@ function editReligions() {
|
||||||
function religionChangeColor() {
|
function religionChangeColor() {
|
||||||
const el = this;
|
const el = this;
|
||||||
const currentFill = el.getAttribute("fill");
|
const currentFill = el.getAttribute("fill");
|
||||||
const religion = +el.parentNode.parentNode.dataset.id;
|
const religion = +el.parentNode.dataset.id;
|
||||||
|
|
||||||
const callback = function (fill) {
|
const callback = newFill => {
|
||||||
el.setAttribute("fill", fill);
|
el.fill = newFill;
|
||||||
pack.religions[religion].color = fill;
|
pack.religions[religion].color = newFill;
|
||||||
relig.select("#religion" + religion).attr("fill", fill);
|
relig.select("#religion" + religion).attr("fill", newFill);
|
||||||
debug.select("#religionsCenter" + religion).attr("fill", fill);
|
debug.select("#religionsCenter" + religion).attr("fill", newFill);
|
||||||
};
|
};
|
||||||
|
|
||||||
openPicker(currentFill, callback);
|
openPicker(currentFill, callback);
|
||||||
|
|
@ -459,7 +461,13 @@ function editReligions() {
|
||||||
|
|
||||||
// prepare svg
|
// prepare svg
|
||||||
alertMessage.innerHTML = "<div id='religionInfo' class='chartInfo'>‍</div>";
|
alertMessage.innerHTML = "<div id='religionInfo' class='chartInfo'>‍</div>";
|
||||||
const svg = d3.select("#alertMessage").insert("svg", "#religionInfo").attr("id", "hierarchy").attr("width", width).attr("height", height).style("text-anchor", "middle");
|
const svg = d3
|
||||||
|
.select("#alertMessage")
|
||||||
|
.insert("svg", "#religionInfo")
|
||||||
|
.attr("id", "hierarchy")
|
||||||
|
.attr("width", width)
|
||||||
|
.attr("height", height)
|
||||||
|
.style("text-anchor", "middle");
|
||||||
const graph = svg.append("g").attr("transform", `translate(10, -45)`);
|
const graph = svg.append("g").attr("transform", `translate(10, -45)`);
|
||||||
const links = graph.append("g").attr("fill", "none").attr("stroke", "#aaaaaa");
|
const links = graph.append("g").attr("fill", "none").attr("stroke", "#aaaaaa");
|
||||||
const nodes = graph.append("g");
|
const nodes = graph.append("g");
|
||||||
|
|
@ -473,7 +481,24 @@ function editReligions() {
|
||||||
.enter()
|
.enter()
|
||||||
.append("path")
|
.append("path")
|
||||||
.attr("d", d => {
|
.attr("d", d => {
|
||||||
return "M" + d.source.x + "," + d.source.y + "C" + d.source.x + "," + (d.source.y * 3 + d.target.y) / 4 + " " + d.target.x + "," + (d.source.y * 2 + d.target.y) / 3 + " " + d.target.x + "," + d.target.y;
|
return (
|
||||||
|
"M" +
|
||||||
|
d.source.x +
|
||||||
|
"," +
|
||||||
|
d.source.y +
|
||||||
|
"C" +
|
||||||
|
d.source.x +
|
||||||
|
"," +
|
||||||
|
(d.source.y * 3 + d.target.y) / 4 +
|
||||||
|
" " +
|
||||||
|
d.target.x +
|
||||||
|
"," +
|
||||||
|
(d.source.y * 2 + d.target.y) / 3 +
|
||||||
|
" " +
|
||||||
|
d.target.x +
|
||||||
|
"," +
|
||||||
|
d.target.y
|
||||||
|
);
|
||||||
});
|
});
|
||||||
|
|
||||||
const node = nodes
|
const node = nodes
|
||||||
|
|
@ -578,7 +603,11 @@ function editReligions() {
|
||||||
$("#religionsEditor").dialog({position: {my: "right top", at: "right-10 top+10", of: "svg"}});
|
$("#religionsEditor").dialog({position: {my: "right top", at: "right-10 top+10", of: "svg"}});
|
||||||
|
|
||||||
tip("Click on religion to select, drag the circle to change religion", true);
|
tip("Click on religion to select, drag the circle to change religion", true);
|
||||||
viewbox.style("cursor", "crosshair").on("click", selectReligionOnMapClick).call(d3.drag().on("start", dragReligionBrush)).on("touchmove mousemove", moveReligionBrush);
|
viewbox
|
||||||
|
.style("cursor", "crosshair")
|
||||||
|
.on("click", selectReligionOnMapClick)
|
||||||
|
.call(d3.drag().on("start", dragReligionBrush))
|
||||||
|
.on("touchmove mousemove", moveReligionBrush);
|
||||||
|
|
||||||
body.querySelector("div").classList.add("selected");
|
body.querySelector("div").classList.add("selected");
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -45,7 +45,7 @@ function editStates() {
|
||||||
cl = el.classList,
|
cl = el.classList,
|
||||||
line = el.parentNode,
|
line = el.parentNode,
|
||||||
state = +line.dataset.id;
|
state = +line.dataset.id;
|
||||||
if (cl.contains("fillRect")) stateChangeFill(el);
|
if (el.tagName === "FILL-BOX") stateChangeFill(el);
|
||||||
else if (cl.contains("name")) editStateName(state);
|
else if (cl.contains("name")) editStateName(state);
|
||||||
else if (cl.contains("coaIcon")) editEmblem("state", "stateCOA" + state, pack.states[state]);
|
else if (cl.contains("coaIcon")) editEmblem("state", "stateCOA" + state, pack.states[state]);
|
||||||
else if (cl.contains("icon-star-empty")) stateCapitalZoomIn(state);
|
else if (cl.contains("icon-star-empty")) stateCapitalZoomIn(state);
|
||||||
|
|
@ -102,7 +102,7 @@ function editStates() {
|
||||||
// Neutral line
|
// Neutral line
|
||||||
lines += `<div class="states" data-id=${s.i} data-name="${s.name}" data-cells=${s.cells} data-area=${area}
|
lines += `<div class="states" data-id=${s.i} data-name="${s.name}" data-cells=${s.cells} data-area=${area}
|
||||||
data-population=${population} data-burgs=${s.burgs} data-color="" data-form="" data-capital="" data-culture="" data-type="" data-expansionism="">
|
data-population=${population} data-burgs=${s.burgs} data-color="" data-form="" data-capital="" data-culture="" data-type="" data-expansionism="">
|
||||||
<svg width="9" height="9" class="placeholder"></svg>
|
<svg width="1em" height="1em" class="placeholder"></svg>
|
||||||
<input data-tip="Neutral lands name. Click to change" class="stateName name pointer italic" value="${s.name}" readonly>
|
<input data-tip="Neutral lands name. Click to change" class="stateName name pointer italic" value="${s.name}" readonly>
|
||||||
<svg class="coaIcon placeholder hide"></svg>
|
<svg class="coaIcon placeholder hide"></svg>
|
||||||
<input class="stateForm placeholder" value="none">
|
<input class="stateForm placeholder" value="none">
|
||||||
|
|
@ -126,15 +126,10 @@ function editStates() {
|
||||||
|
|
||||||
const capital = pack.burgs[s.capital].name;
|
const capital = pack.burgs[s.capital].name;
|
||||||
COArenderer.trigger("stateCOA" + s.i, s.coa);
|
COArenderer.trigger("stateCOA" + s.i, s.coa);
|
||||||
lines += `<div class="states" data-id=${s.i} data-name="${s.name}" data-form="${s.formName}" data-capital="${capital}" data-color="${
|
lines += `<div class="states" data-id=${s.i} data-name="${s.name}" data-form="${s.formName}" data-capital="${capital}"
|
||||||
s.color
|
data-color="${s.color}" data-cells=${s.cells} data-area=${area} data-population=${population} data-burgs=${s.burgs}
|
||||||
}" data-cells=${s.cells}
|
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=${
|
<fill-box fill="${s.color}"></fill-box>
|
||||||
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="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>
|
||||||
<svg data-tip="Click to show and edit state emblem" class="coaIcon pointer hide" viewBox="0 0 200 200"><use href="#stateCOA${s.i}"></use></svg>
|
<svg data-tip="Click to show and edit state emblem" class="coaIcon pointer hide" viewBox="0 0 200 200"><use href="#stateCOA${s.i}"></use></svg>
|
||||||
<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>
|
||||||
|
|
@ -149,9 +144,8 @@ function editStates() {
|
||||||
<div data-tip="${populationTip}" class="culturePopulation hide">${si(population)}</div>
|
<div data-tip="${populationTip}" class="culturePopulation hide">${si(population)}</div>
|
||||||
<select data-tip="State type. Defines growth model. Click to change" class="cultureType ${hidden} show hide">${getTypeOptions(s.type)}</select>
|
<select data-tip="State type. Defines growth model. Click to change" class="cultureType ${hidden} show hide">${getTypeOptions(s.type)}</select>
|
||||||
<span data-tip="State expansionism" class="icon-resize-full ${hidden} show hide"></span>
|
<span data-tip="State expansionism" class="icon-resize-full ${hidden} show hide"></span>
|
||||||
<input data-tip="Expansionism (defines competitive size). Change to re-calculate states based on new value" class="statePower ${hidden} show hide" type="number" min=0 max=99 step=.1 value=${
|
<input data-tip="Expansionism (defines competitive size). Change to re-calculate states based on new value"
|
||||||
s.expansionism
|
class="statePower ${hidden} show hide" type="number" min=0 max=99 step=.1 value=${s.expansionism}>
|
||||||
}>
|
|
||||||
<span data-tip="Cells count" class="icon-check-empty ${hidden} show hide"></span>
|
<span data-tip="Cells count" class="icon-check-empty ${hidden} show hide"></span>
|
||||||
<div data-tip="Cells count" class="stateCells ${hidden} show hide">${s.cells}</div>
|
<div data-tip="Cells count" class="stateCells ${hidden} show hide">${s.cells}</div>
|
||||||
<span data-tip="Toggle state focus" class="icon-pin ${focused ? "" : " inactive"} hide"></span>
|
<span data-tip="Toggle state focus" class="icon-pin ${focused ? "" : " inactive"} hide"></span>
|
||||||
|
|
@ -237,18 +231,18 @@ function editStates() {
|
||||||
|
|
||||||
function stateChangeFill(el) {
|
function stateChangeFill(el) {
|
||||||
const currentFill = el.getAttribute("fill");
|
const currentFill = el.getAttribute("fill");
|
||||||
const state = +el.parentNode.parentNode.dataset.id;
|
const state = +el.parentNode.dataset.id;
|
||||||
|
|
||||||
const callback = function (fill) {
|
const callback = function (newFill) {
|
||||||
el.setAttribute("fill", fill);
|
el.fill = newFill;
|
||||||
pack.states[state].color = fill;
|
pack.states[state].color = newFill;
|
||||||
statesBody.select("#state" + state).attr("fill", fill);
|
statesBody.select("#state" + state).attr("fill", newFill);
|
||||||
statesBody.select("#state-gap" + state).attr("stroke", fill);
|
statesBody.select("#state-gap" + state).attr("stroke", newFill);
|
||||||
const halo = d3.color(fill) ? d3.color(fill).darker().hex() : "#666666";
|
const halo = d3.color(newFill) ? d3.color(newFill).darker().hex() : "#666666";
|
||||||
statesHalo.select("#state-border" + state).attr("stroke", halo);
|
statesHalo.select("#state-border" + state).attr("stroke", halo);
|
||||||
|
|
||||||
// recolor regiments
|
// recolor regiments
|
||||||
const solidColor = fill[0] === "#" ? fill : "#999";
|
const solidColor = newFill[0] === "#" ? newFill : "#999";
|
||||||
const darkerColor = d3.color(solidColor).darker().hex();
|
const darkerColor = d3.color(solidColor).darker().hex();
|
||||||
armies.select("#army" + state).attr("fill", solidColor);
|
armies.select("#army" + state).attr("fill", solidColor);
|
||||||
armies
|
armies
|
||||||
|
|
|
||||||
311
modules/ui/stylePresets.js
Normal file
|
|
@ -0,0 +1,311 @@
|
||||||
|
// UI module to control the style presets
|
||||||
|
"use strict";
|
||||||
|
|
||||||
|
const systemPresets = ["default", "ancient", "gloom", "light", "watercolor", "clean", "atlas", "cyberpunk", "monochrome"];
|
||||||
|
const customPresetPrefix = "fmgStyle_";
|
||||||
|
|
||||||
|
// add style presets to list
|
||||||
|
{
|
||||||
|
const systemOptions = systemPresets.map(styleName => `<option value="${styleName}">${styleName}</option>`);
|
||||||
|
const storedStyles = Object.keys(localStorage).filter(key => key.startsWith(customPresetPrefix));
|
||||||
|
const customOptions = storedStyles.map(styleName => `<option value="${styleName}">${styleName.replace(customPresetPrefix, "")} [custom]</option>`);
|
||||||
|
const options = systemOptions.join("") + customOptions.join("");
|
||||||
|
document.getElementById("stylePreset").innerHTML = options;
|
||||||
|
}
|
||||||
|
|
||||||
|
async function applyStyleOnLoad() {
|
||||||
|
const desiredPreset = localStorage.getItem("presetStyle") || "default";
|
||||||
|
const styleData = await getStylePreset(desiredPreset);
|
||||||
|
const [appliedPreset, style] = styleData;
|
||||||
|
|
||||||
|
applyStyle(style);
|
||||||
|
updateMapFilter();
|
||||||
|
stylePreset.value = stylePreset.dataset.old = appliedPreset;
|
||||||
|
setPresetRemoveButtonVisibiliy();
|
||||||
|
}
|
||||||
|
|
||||||
|
async function getStylePreset(desiredPreset) {
|
||||||
|
let presetToLoad = desiredPreset;
|
||||||
|
|
||||||
|
const isCustom = !systemPresets.includes(desiredPreset);
|
||||||
|
if (isCustom) {
|
||||||
|
const storedStyleJSON = localStorage.getItem(desiredPreset);
|
||||||
|
if (!storedStyleJSON) {
|
||||||
|
ERROR && console.error(`Custom style ${desiredPreset} in not found in localStorage. Applying default style`);
|
||||||
|
presetToLoad = "default";
|
||||||
|
} else {
|
||||||
|
const isValid = JSON.isValid(storedStyleJSON);
|
||||||
|
if (isValid) return [desiredPreset, JSON.parse(storedStyleJSON)];
|
||||||
|
|
||||||
|
ERROR && console.error(`Custom style ${desiredPreset} stored in localStorage is not valid. Applying default style`);
|
||||||
|
presetToLoad = "default";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const style = await fetchSystemPreset(presetToLoad);
|
||||||
|
return [presetToLoad, style];
|
||||||
|
}
|
||||||
|
|
||||||
|
async function fetchSystemPreset(preset) {
|
||||||
|
const style = await fetch(`./styles/${preset}.json`)
|
||||||
|
.then(res => res.json())
|
||||||
|
.catch(err => {
|
||||||
|
ERROR && console.error("Error on loading style preset", preset, err);
|
||||||
|
return null;
|
||||||
|
});
|
||||||
|
|
||||||
|
if (!style) throw new Error("Cannot fetch style preset", preset);
|
||||||
|
return style;
|
||||||
|
}
|
||||||
|
|
||||||
|
function applyStyle(style) {
|
||||||
|
for (const selector in style) {
|
||||||
|
const el = document.querySelector(selector);
|
||||||
|
if (!el) continue;
|
||||||
|
for (const attribute in style[selector]) {
|
||||||
|
const value = style[selector][attribute];
|
||||||
|
|
||||||
|
if (value === "null" || value === null) {
|
||||||
|
el.removeAttribute(attribute);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (attribute === "text-shadow") {
|
||||||
|
el.style[attribute] = value;
|
||||||
|
} else {
|
||||||
|
el.setAttribute(attribute, value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function requestStylePresetChange(preset) {
|
||||||
|
const isConfirmed = sessionStorage.getItem("styleChangeConfirmed");
|
||||||
|
if (isConfirmed) {
|
||||||
|
changeStyle(preset);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
confirmationDialog({
|
||||||
|
title: "Change style preset",
|
||||||
|
message: "Are you sure you want to change the style preset? All unsaved style changes will be lost",
|
||||||
|
confirm: "Change",
|
||||||
|
onConfirm: () => {
|
||||||
|
sessionStorage.setItem("styleChangeConfirmed", true);
|
||||||
|
changeStyle(preset);
|
||||||
|
},
|
||||||
|
onCancel: () => {
|
||||||
|
stylePreset.value = stylePreset.dataset.old;
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
async function changeStyle(desiredPreset) {
|
||||||
|
const styleData = await getStylePreset(desiredPreset);
|
||||||
|
const [appliedPreset, style] = styleData;
|
||||||
|
localStorage.setItem("presetStyle", appliedPreset);
|
||||||
|
applyStyleWithUiRefresh(style);
|
||||||
|
}
|
||||||
|
|
||||||
|
function applyStyleWithUiRefresh(style) {
|
||||||
|
applyStyle(style);
|
||||||
|
updateElements();
|
||||||
|
selectStyleElement(); // re-select element to trigger values update
|
||||||
|
updateMapFilter();
|
||||||
|
stylePreset.dataset.old = stylePreset.value;
|
||||||
|
|
||||||
|
invokeActiveZooming();
|
||||||
|
setPresetRemoveButtonVisibiliy();
|
||||||
|
}
|
||||||
|
|
||||||
|
function addStylePreset() {
|
||||||
|
$("#styleSaver").dialog({title: "Style Saver", width: "26em", position: {my: "center", at: "center", of: "svg"}});
|
||||||
|
|
||||||
|
const styleName = stylePreset.value.replace(customPresetPrefix, "");
|
||||||
|
document.getElementById("styleSaverName").value = styleName;
|
||||||
|
styleSaverJSON.value = JSON.stringify(collectStyleData(), null, 2);
|
||||||
|
checkName();
|
||||||
|
|
||||||
|
if (modules.saveStyle) return;
|
||||||
|
modules.saveStyle = true;
|
||||||
|
|
||||||
|
// add listeners
|
||||||
|
document.getElementById("styleSaverName").addEventListener("input", checkName);
|
||||||
|
document.getElementById("styleSaverSave").addEventListener("click", saveStyle);
|
||||||
|
document.getElementById("styleSaverDownload").addEventListener("click", styleDownload);
|
||||||
|
document.getElementById("styleSaverLoad").addEventListener("click", () => styleToLoad.click());
|
||||||
|
document.getElementById("styleToLoad").addEventListener("change", loadStyleFile);
|
||||||
|
|
||||||
|
function collectStyleData() {
|
||||||
|
const style = {};
|
||||||
|
const attributes = {
|
||||||
|
"#map": ["background-color", "filter", "data-filter"],
|
||||||
|
"#armies": ["font-size", "box-size", "stroke", "stroke-width", "fill-opacity", "filter"],
|
||||||
|
"#biomes": ["opacity", "filter", "mask"],
|
||||||
|
"#stateBorders": ["opacity", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter"],
|
||||||
|
"#provinceBorders": ["opacity", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter"],
|
||||||
|
"#cells": ["opacity", "stroke", "stroke-width", "filter", "mask"],
|
||||||
|
"#gridOverlay": ["opacity", "scale", "dx", "dy", "type", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "transform", "filter", "mask"],
|
||||||
|
"#coordinates": ["opacity", "data-size", "font-size", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter", "mask"],
|
||||||
|
"#compass": ["opacity", "transform", "filter", "mask", "shape-rendering"],
|
||||||
|
"#rose": ["transform"],
|
||||||
|
"#relig": ["opacity", "stroke", "stroke-width", "filter"],
|
||||||
|
"#cults": ["opacity", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter"],
|
||||||
|
"#landmass": ["opacity", "fill", "filter"],
|
||||||
|
"#markers": ["opacity", "rescale", "filter"],
|
||||||
|
"#prec": ["opacity", "stroke", "stroke-width", "fill", "filter"],
|
||||||
|
"#population": ["opacity", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter"],
|
||||||
|
"#rural": ["stroke"],
|
||||||
|
"#urban": ["stroke"],
|
||||||
|
"#freshwater": ["opacity", "fill", "stroke", "stroke-width", "filter"],
|
||||||
|
"#salt": ["opacity", "fill", "stroke", "stroke-width", "filter"],
|
||||||
|
"#sinkhole": ["opacity", "fill", "stroke", "stroke-width", "filter"],
|
||||||
|
"#frozen": ["opacity", "fill", "stroke", "stroke-width", "filter"],
|
||||||
|
"#lava": ["opacity", "fill", "stroke", "stroke-width", "filter"],
|
||||||
|
"#dry": ["opacity", "fill", "stroke", "stroke-width", "filter"],
|
||||||
|
"#sea_island": ["opacity", "stroke", "stroke-width", "filter", "auto-filter"],
|
||||||
|
"#lake_island": ["opacity", "stroke", "stroke-width", "filter"],
|
||||||
|
"#terrain": ["opacity", "set", "size", "density", "filter", "mask"],
|
||||||
|
"#rivers": ["opacity", "filter", "fill"],
|
||||||
|
"#ruler": ["opacity", "filter"],
|
||||||
|
"#roads": ["opacity", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter", "mask"],
|
||||||
|
"#trails": ["opacity", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter", "mask"],
|
||||||
|
"#searoutes": ["opacity", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter", "mask"],
|
||||||
|
"#statesBody": ["opacity", "filter"],
|
||||||
|
"#statesHalo": ["opacity", "data-width", "stroke-width", "filter"],
|
||||||
|
"#provs": ["opacity", "fill", "font-size", "font-family", "filter"],
|
||||||
|
"#temperature": ["opacity", "font-size", "fill", "fill-opacity", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter"],
|
||||||
|
"#ice": ["opacity", "fill", "stroke", "stroke-width", "filter"],
|
||||||
|
"#emblems": ["opacity", "stroke-width", "filter"],
|
||||||
|
"#texture": ["opacity", "filter", "mask"],
|
||||||
|
"#textureImage": ["x", "y"],
|
||||||
|
"#zones": ["opacity", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "filter", "mask"],
|
||||||
|
"#oceanLayers": ["filter", "layers"],
|
||||||
|
"#oceanBase": ["fill"],
|
||||||
|
"#oceanicPattern": ["href", "opacity"],
|
||||||
|
"#terrs": ["opacity", "scheme", "terracing", "skip", "relax", "curve", "filter", "mask"],
|
||||||
|
"#legend": ["data-size", "font-size", "font-family", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap", "data-x", "data-y", "data-columns"],
|
||||||
|
"#legendBox": ["fill", "fill-opacity"],
|
||||||
|
"#burgLabels > #cities": ["opacity", "fill", "text-shadow", "data-size", "font-size", "font-family"],
|
||||||
|
"#burgIcons > #cities": ["opacity", "fill", "fill-opacity", "size", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap"],
|
||||||
|
"#anchors > #cities": ["opacity", "fill", "size", "stroke", "stroke-width"],
|
||||||
|
"#burgLabels > #towns": ["opacity", "fill", "text-shadow", "data-size", "font-size", "font-family"],
|
||||||
|
"#burgIcons > #towns": ["opacity", "fill", "fill-opacity", "size", "stroke", "stroke-width", "stroke-dasharray", "stroke-linecap"],
|
||||||
|
"#anchors > #towns": ["opacity", "fill", "size", "stroke", "stroke-width"],
|
||||||
|
"#labels > #states": ["opacity", "fill", "stroke", "stroke-width", "text-shadow", "data-size", "font-size", "font-family", "filter"],
|
||||||
|
"#labels > #addedLabels": ["opacity", "fill", "stroke", "stroke-width", "text-shadow", "data-size", "font-size", "font-family", "filter"],
|
||||||
|
"#fogging": ["opacity", "fill", "filter"]
|
||||||
|
};
|
||||||
|
|
||||||
|
for (const selector in attributes) {
|
||||||
|
const el = document.querySelector(selector);
|
||||||
|
if (!el) continue;
|
||||||
|
|
||||||
|
style[selector] = {};
|
||||||
|
for (const attr of attributes[selector]) {
|
||||||
|
let value = el.style[attr] || el.getAttribute(attr);
|
||||||
|
if (attr === "font-size" && el.hasAttribute("data-size")) value = el.getAttribute("data-size");
|
||||||
|
style[selector][attr] = parseValue(value);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function parseValue(value) {
|
||||||
|
if (value === "null" || value === null) return null;
|
||||||
|
if (value === "") return "";
|
||||||
|
if (!isNaN(+value)) return +value;
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
return style;
|
||||||
|
}
|
||||||
|
|
||||||
|
function checkName() {
|
||||||
|
const styleName = customPresetPrefix + styleSaverName.value;
|
||||||
|
|
||||||
|
const isSystem = systemPresets.includes(styleName) || systemPresets.includes(styleSaverName.value);
|
||||||
|
if (isSystem) return (styleSaverTip.innerHTML = "default");
|
||||||
|
|
||||||
|
const isExisting = Array.from(stylePreset.options).some(option => option.value == styleName);
|
||||||
|
if (isExisting) return (styleSaverTip.innerHTML = "existing");
|
||||||
|
|
||||||
|
styleSaverTip.innerHTML = "new";
|
||||||
|
}
|
||||||
|
|
||||||
|
function saveStyle() {
|
||||||
|
const styleJSON = styleSaverJSON.value;
|
||||||
|
const desiredName = styleSaverName.value;
|
||||||
|
|
||||||
|
if (!styleJSON) return tip("Please provide a style JSON", false, "error");
|
||||||
|
if (!JSON.isValid(styleJSON)) return tip("JSON string is not valid, please check the format", false, "error");
|
||||||
|
if (!desiredName) return tip("Please provide a preset name", false, "error");
|
||||||
|
if (styleSaverTip.innerHTML === "default") return tip("You cannot overwrite default preset, please change the name", false, "error");
|
||||||
|
|
||||||
|
const presetName = customPresetPrefix + desiredName;
|
||||||
|
applyOption(stylePreset, presetName, desiredName + " [custom]");
|
||||||
|
localStorage.setItem("presetStyle", presetName);
|
||||||
|
localStorage.setItem(presetName, styleJSON);
|
||||||
|
|
||||||
|
applyStyleWithUiRefresh(JSON.parse(styleJSON));
|
||||||
|
tip("Style preset is saved and applied", false, "success", 4000);
|
||||||
|
$("#styleSaver").dialog("close");
|
||||||
|
}
|
||||||
|
|
||||||
|
function styleDownload() {
|
||||||
|
const styleJSON = styleSaverJSON.value;
|
||||||
|
const styleName = styleSaverName.value;
|
||||||
|
|
||||||
|
if (!styleJSON) return tip("Please provide a style JSON", false, "error");
|
||||||
|
if (!JSON.isValid(styleJSON)) return tip("JSON string is not valid, please check the format", false, "error");
|
||||||
|
if (!styleName) return tip("Please provide a preset name", false, "error");
|
||||||
|
|
||||||
|
downloadFile(styleJSON, styleName + ".json", "application/json");
|
||||||
|
}
|
||||||
|
|
||||||
|
function loadStyleFile() {
|
||||||
|
const fileName = this.files[0]?.name.replace(/\.[^.]*$/, "");
|
||||||
|
uploadFile(this, styleUpload);
|
||||||
|
|
||||||
|
function styleUpload(dataLoaded) {
|
||||||
|
if (!dataLoaded) return tip("Cannot load the file. Please check the data format", false, "error");
|
||||||
|
const isValid = JSON.isValid(dataLoaded);
|
||||||
|
if (!isValid) return tip("Loaded data is not a valid JSON, please check the format", false, "error");
|
||||||
|
|
||||||
|
styleSaverJSON.value = JSON.stringify(JSON.parse(dataLoaded), null, 2);
|
||||||
|
styleSaverName.value = fileName;
|
||||||
|
checkName();
|
||||||
|
tip("Style preset is uploaded", false, "success", 4000);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function requestRemoveStylePreset() {
|
||||||
|
const isDefault = systemPresets.includes(stylePreset.value);
|
||||||
|
if (isDefault) return tip("Cannot remove system preset", false, "error");
|
||||||
|
|
||||||
|
confirmationDialog({
|
||||||
|
title: "Remove style preset",
|
||||||
|
message: "Are you sure you want to remove the style preset? This action cannot be undone.",
|
||||||
|
confirm: "Remove",
|
||||||
|
onConfirm: removeStylePreset
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
function removeStylePreset() {
|
||||||
|
localStorage.removeItem("presetStyle");
|
||||||
|
localStorage.removeItem(stylePreset.value);
|
||||||
|
stylePreset.selectedOptions[0].remove();
|
||||||
|
|
||||||
|
changeStyle("default");
|
||||||
|
}
|
||||||
|
|
||||||
|
function updateMapFilter() {
|
||||||
|
const filter = svg.attr("data-filter");
|
||||||
|
mapFilters.querySelectorAll(".pressed").forEach(button => button.classList.remove("pressed"));
|
||||||
|
if (!filter) return;
|
||||||
|
mapFilters.querySelector("#" + filter).classList.add("pressed");
|
||||||
|
}
|
||||||
|
|
||||||
|
function setPresetRemoveButtonVisibiliy() {
|
||||||
|
const isDefault = systemPresets.includes(stylePreset.value);
|
||||||
|
removeStyleButton.style.display = isDefault ? "none" : "inline-block";
|
||||||
|
}
|
||||||
161
modules/ui/temperature-graph.js
Normal file
|
|
@ -0,0 +1,161 @@
|
||||||
|
"use strict";
|
||||||
|
|
||||||
|
function showBurgTemperatureGraph(id) {
|
||||||
|
const b = pack.burgs[id];
|
||||||
|
const lat = mapCoordinates.latN - (b.y / graphHeight) * mapCoordinates.latT;
|
||||||
|
const burgTemp = grid.cells.temp[pack.cells.g[b.cell]];
|
||||||
|
const prec = grid.cells.prec[pack.cells.g[b.cell]];
|
||||||
|
|
||||||
|
// prettier-ignore
|
||||||
|
const weights = [
|
||||||
|
[
|
||||||
|
[10.782752257744338, 2.7100404240962126], [-2.8226802110591462, 51.62920138583541], [-6.6250956268643835, 4.427939197315455], [-59.64690518541339, 41.89084162654791], [-1.3302059550553835, -3.6964487738450913],
|
||||||
|
[-2.5844898544535497, 0.09879268612455298], [-5.58528252533573, -0.23426224364501905], [26.94531337690372, 20.898158905988907], [3.816397481634785, -0.19045424064580757], [-4.835697931609101, -10.748232783636434]
|
||||||
|
],
|
||||||
|
[
|
||||||
|
[-2.478952081870123, 0.6405800134306895, -7.136785640930911, -0.2186529024764509, 3.6568435212735424, 31.446026153530838, -19.91005187482281, 0.2543395274783306, -7.036924569659988, -0.7721371621651565],
|
||||||
|
[-197.10583739743538, 6.889921141533474, 0.5058941504631129, 7.7667203434606416, -53.74180550086929, -15.717331715167001, -61.32068414155791, -2.259728220978728, 35.84049189540032, 94.6157364730977],
|
||||||
|
[-5.312011591880851, -0.09923148954215096, -1.7132477487917586, -22.55559652066422, 0.4806107280554336, -26.5583974109492, 2.0558257347014863, 25.815645234787432, -18.569029876991156, -2.6792003366730035],
|
||||||
|
[20.706518520569514, 18.344297403881875, 99.52244671131733, -58.53124969563653, -60.74384321042212, -80.57540534651835, 7.884792406540866, -144.33871131678563, 80.134199744324, 20.50745285622448],
|
||||||
|
[-52.88299538575159, -15.782505343805528, 16.63316001054924, 88.09475330556671, -17.619552086641818, -19.943999528182427, -120.46286026828177, 19.354752020806302, 43.49422099308949, 28.733924806541363],
|
||||||
|
[-2.4621368711159897, -1.2074759925679757, -1.5133898639835084, 2.173715352424188, -5.988707597991683, 3.0234147182203843, 3.3284199340000797, -1.8805161326360575, 5.151910934121654, -1.2540553911612116]
|
||||||
|
],
|
||||||
|
[
|
||||||
|
[-0.3357437479474717, 0.01430651794222215, -0.7927524256670906, 0.2121636229648523, 1.0587803023358318, -3.759288325505095],
|
||||||
|
[-1.1988028704442968, 1.3768997508052783, -3.8480086358278816, 0.5289387340947143, 0.5769459339961177, -1.2528318145750772],
|
||||||
|
[1.0074966649240946, 1.155301164699459, -2.974254371052421, 0.47408176553219467, 0.5939042688615264, -0.7631976947131744]
|
||||||
|
]
|
||||||
|
];
|
||||||
|
// From (-∞, ∞) to ~[-1, 1]
|
||||||
|
const In1 = [(Math.abs(lat) - 26.950680212887473) / 48.378128506956, (prec - 12.229929140832644) / 29.94402033696607];
|
||||||
|
|
||||||
|
let lastIn = In1;
|
||||||
|
let lstOut = [];
|
||||||
|
|
||||||
|
for (let levelN = 0; levelN < weights.length; levelN++) {
|
||||||
|
const layerN = weights[levelN];
|
||||||
|
for (let i = 0; i < layerN.length; i++) {
|
||||||
|
lstOut[i] = 0;
|
||||||
|
for (let j = 0; j < layerN[i].length; j++) {
|
||||||
|
lstOut[i] = lstOut[i] + lastIn[j] * layerN[i][j];
|
||||||
|
}
|
||||||
|
// sigmoid
|
||||||
|
lstOut[i] = 1 / (1 + Math.exp(-lstOut[i]));
|
||||||
|
}
|
||||||
|
lastIn = lstOut.slice(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Standard deviation for average temperature for the year from [0, 1] to [min, max]
|
||||||
|
const yearSig = lstOut[0] * 62.9466411977018 + 0.28613807855649165;
|
||||||
|
// Standard deviation for the difference between the minimum and maximum temperatures for the year
|
||||||
|
const yearDelTmpSig = lstOut[1] * 13.541688670361175 + 0.1414213562373084 > yearSig ? yearSig : lstOut[1] * 13.541688670361175 + 0.1414213562373084;
|
||||||
|
// Expected value for the difference between the minimum and maximum temperatures for the year
|
||||||
|
const yearDelTmpMu = lstOut[2] * 15.266666666666667 + 0.6416666666666663;
|
||||||
|
|
||||||
|
// Temperature change shape
|
||||||
|
const delT = yearDelTmpMu / 2 + (0.5 * yearDelTmpSig) / 2;
|
||||||
|
const minT = burgTemp - Math.max(yearSig + delT, 15);
|
||||||
|
const maxT = burgTemp + (burgTemp - minT);
|
||||||
|
|
||||||
|
const chartWidth = Math.max(window.innerWidth / 2, 580);
|
||||||
|
const chartHeight = 300;
|
||||||
|
|
||||||
|
// drawing starting point from top-left (y = 0) of SVG
|
||||||
|
const xOffset = 60;
|
||||||
|
const yOffset = 10;
|
||||||
|
|
||||||
|
const year = new Date().getFullYear(); // use current year
|
||||||
|
const startDate = new Date(year, 0, 1);
|
||||||
|
const endDate = new Date(year, 11, 31);
|
||||||
|
const months = ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"];
|
||||||
|
|
||||||
|
const xscale = d3.scaleTime().domain([startDate, endDate]).range([0, chartWidth]);
|
||||||
|
const yscale = d3.scaleLinear().domain([minT, maxT]).range([chartHeight, 0]);
|
||||||
|
|
||||||
|
const tempMean = [];
|
||||||
|
const tempMin = [];
|
||||||
|
const tempMax = [];
|
||||||
|
|
||||||
|
months.forEach((month, index) => {
|
||||||
|
const rate = index / 11;
|
||||||
|
let formTmp = Math.cos(rate * 2 * Math.PI) / 2;
|
||||||
|
if (lat > 0) formTmp = -formTmp;
|
||||||
|
|
||||||
|
const x = rate * chartWidth + xOffset;
|
||||||
|
const tempAverage = formTmp * yearSig + burgTemp;
|
||||||
|
const tempDelta = yearDelTmpMu / 2 + (formTmp * yearDelTmpSig) / 2;
|
||||||
|
|
||||||
|
tempMean.push([x, yscale(tempAverage) + yOffset]);
|
||||||
|
tempMin.push([x, yscale(tempAverage - tempDelta) + yOffset]);
|
||||||
|
tempMax.push([x, yscale(tempAverage + tempDelta) + yOffset]);
|
||||||
|
});
|
||||||
|
|
||||||
|
drawGraph();
|
||||||
|
$("#alert").dialog({title: "Annual temperature in " + b.name, width: "auto", position: {my: "center", at: "center", of: "svg"}});
|
||||||
|
|
||||||
|
function drawGraph() {
|
||||||
|
alertMessage.innerHTML = "";
|
||||||
|
const getCurve = data => round(d3.line().curve(d3.curveBasis)(data), 2);
|
||||||
|
|
||||||
|
const legendSize = 60;
|
||||||
|
const chart = d3
|
||||||
|
.select("#alertMessage")
|
||||||
|
.append("svg")
|
||||||
|
.attr("width", chartWidth + 120)
|
||||||
|
.attr("height", chartHeight + yOffset + legendSize);
|
||||||
|
|
||||||
|
const legend = chart.append("g");
|
||||||
|
const legendY = chartHeight + yOffset + legendSize * 0.8;
|
||||||
|
const legendX = n => (chartWidth * n) / 4;
|
||||||
|
const legendTextX = n => legendX(n) + 10;
|
||||||
|
legend.append("circle").attr("cx", legendX(1)).attr("cy", legendY).attr("r", 4).style("fill", "red");
|
||||||
|
legend.append("text").attr("x", legendTextX(1)).attr("y", legendY).attr("alignment-baseline", "central").text("Day temperature");
|
||||||
|
legend.append("circle").attr("cx", legendX(2)).attr("cy", legendY).attr("r", 4).style("fill", "orange");
|
||||||
|
legend.append("text").attr("x", legendTextX(2)).attr("y", legendY).attr("alignment-baseline", "central").text("Mean temperature");
|
||||||
|
legend.append("circle").attr("cx", legendX(3)).attr("cy", legendY).attr("r", 4).style("fill", "blue");
|
||||||
|
legend.append("text").attr("x", legendTextX(3)).attr("y", legendY).attr("alignment-baseline", "central").text("Night temperature");
|
||||||
|
|
||||||
|
const xGrid = d3.axisBottom(xscale).ticks().tickSize(-chartHeight);
|
||||||
|
const yGrid = d3.axisLeft(yscale).ticks(5).tickSize(-chartWidth);
|
||||||
|
|
||||||
|
const grid = chart.append("g").attr("class", "epgrid").attr("stroke-dasharray", "4 1");
|
||||||
|
grid.append("g").attr("transform", `translate(${xOffset}, ${chartHeight + yOffset})`).call(xGrid); // prettier-ignore
|
||||||
|
grid.append("g").attr("transform", `translate(${xOffset}, ${yOffset})`).call(yGrid);
|
||||||
|
grid.selectAll("text").remove();
|
||||||
|
|
||||||
|
// add zero degree line
|
||||||
|
if (minT < 0 && maxT > 0) {
|
||||||
|
grid
|
||||||
|
.append("line")
|
||||||
|
.attr("x1", xOffset)
|
||||||
|
.attr("y1", yscale(0) + yOffset)
|
||||||
|
.attr("x2", chartWidth + xOffset)
|
||||||
|
.attr("y2", yscale(0) + yOffset)
|
||||||
|
.attr("stroke", "gray");
|
||||||
|
}
|
||||||
|
|
||||||
|
const xAxis = d3.axisBottom(xscale).ticks().tickFormat(d3.timeFormat("%B"));
|
||||||
|
const yAxis = d3.axisLeft(yscale).ticks(5).tickFormat(convertTemperature);
|
||||||
|
|
||||||
|
const axis = chart.append("g");
|
||||||
|
axis
|
||||||
|
.append("g")
|
||||||
|
.attr("transform", `translate(${xOffset}, ${chartHeight + yOffset})`)
|
||||||
|
.call(xAxis);
|
||||||
|
axis.append("g").attr("transform", `translate(${xOffset}, ${yOffset})`).call(yAxis);
|
||||||
|
axis.select("path.domain").attr("d", `M0.5,0.5 H${chartWidth + 0.5}`);
|
||||||
|
|
||||||
|
const curves = chart.append("g").attr("fill", "none").style("stroke-width", 2.5);
|
||||||
|
curves.append("path").attr("d", getCurve(tempMean)).attr("data-type", "daily").attr("stroke", "orange").on("mousemove", printVal);
|
||||||
|
curves.append("path").attr("d", getCurve(tempMin)).attr("data-type", "night").attr("stroke", "blue").on("mousemove", printVal);
|
||||||
|
curves.append("path").attr("d", getCurve(tempMax)).attr("data-type", "day").attr("stroke", "red").on("mousemove", printVal);
|
||||||
|
|
||||||
|
function printVal() {
|
||||||
|
const [x, y] = d3.mouse(this);
|
||||||
|
const type = this.getAttribute("data-type");
|
||||||
|
const temp = convertTemperature(yscale.invert(y - yOffset));
|
||||||
|
const month = months[rn(((x - xOffset) / chartWidth) * 12)] || months[0];
|
||||||
|
tip(`Average ${type} temperature in ${month}: ${temp}`);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -11,6 +11,8 @@ function editUnits() {
|
||||||
position: {my: "right top", at: "right-10 top+10", of: "svg", collision: "fit"}
|
position: {my: "right top", at: "right-10 top+10", of: "svg", collision: "fit"}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const drawBar = () => drawScaleBar(scale);
|
||||||
|
|
||||||
// add listeners
|
// add listeners
|
||||||
document.getElementById("distanceUnitInput").addEventListener("change", changeDistanceUnit);
|
document.getElementById("distanceUnitInput").addEventListener("change", changeDistanceUnit);
|
||||||
document.getElementById("distanceScaleOutput").addEventListener("input", changeDistanceScale);
|
document.getElementById("distanceScaleOutput").addEventListener("input", changeDistanceScale);
|
||||||
|
|
@ -19,9 +21,9 @@ function editUnits() {
|
||||||
document.getElementById("heightExponentInput").addEventListener("input", changeHeightExponent);
|
document.getElementById("heightExponentInput").addEventListener("input", changeHeightExponent);
|
||||||
document.getElementById("heightExponentOutput").addEventListener("input", changeHeightExponent);
|
document.getElementById("heightExponentOutput").addEventListener("input", changeHeightExponent);
|
||||||
document.getElementById("temperatureScale").addEventListener("change", changeTemperatureScale);
|
document.getElementById("temperatureScale").addEventListener("change", changeTemperatureScale);
|
||||||
document.getElementById("barSizeOutput").addEventListener("input", drawScaleBar);
|
document.getElementById("barSizeOutput").addEventListener("input", drawBar);
|
||||||
document.getElementById("barSizeInput").addEventListener("input", drawScaleBar);
|
document.getElementById("barSizeInput").addEventListener("input", drawBar);
|
||||||
document.getElementById("barLabel").addEventListener("input", drawScaleBar);
|
document.getElementById("barLabel").addEventListener("input", drawBar);
|
||||||
document.getElementById("barPosX").addEventListener("input", fitScaleBar);
|
document.getElementById("barPosX").addEventListener("input", fitScaleBar);
|
||||||
document.getElementById("barPosY").addEventListener("input", fitScaleBar);
|
document.getElementById("barPosY").addEventListener("input", fitScaleBar);
|
||||||
document.getElementById("barBackOpacity").addEventListener("input", changeScaleBarOpacity);
|
document.getElementById("barBackOpacity").addEventListener("input", changeScaleBarOpacity);
|
||||||
|
|
@ -46,19 +48,18 @@ function editUnits() {
|
||||||
prompt("Provide a custom name for a distance unit", {default: ""}, custom => {
|
prompt("Provide a custom name for a distance unit", {default: ""}, custom => {
|
||||||
this.options.add(new Option(custom, custom, false, true));
|
this.options.add(new Option(custom, custom, false, true));
|
||||||
lock("distanceUnit");
|
lock("distanceUnit");
|
||||||
drawScaleBar();
|
drawScaleBar(scale);
|
||||||
calculateFriendlyGridSize();
|
calculateFriendlyGridSize();
|
||||||
});
|
});
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
drawScaleBar();
|
drawScaleBar(scale);
|
||||||
calculateFriendlyGridSize();
|
calculateFriendlyGridSize();
|
||||||
}
|
}
|
||||||
|
|
||||||
function changeDistanceScale() {
|
function changeDistanceScale() {
|
||||||
distanceScale = +document.getElementById("distanceScaleInput").value;
|
drawScaleBar(scale);
|
||||||
drawScaleBar();
|
|
||||||
calculateFriendlyGridSize();
|
calculateFriendlyGridSize();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -138,7 +139,7 @@ function editUnits() {
|
||||||
localStorage.removeItem("barBackColor");
|
localStorage.removeItem("barBackColor");
|
||||||
localStorage.removeItem("barPosX");
|
localStorage.removeItem("barPosX");
|
||||||
localStorage.removeItem("barPosY");
|
localStorage.removeItem("barPosY");
|
||||||
drawScaleBar();
|
drawScaleBar(scale);
|
||||||
|
|
||||||
// population
|
// population
|
||||||
populationRate = populationRateOutput.value = populationRateInput.value = 1000;
|
populationRate = populationRateOutput.value = populationRateInput.value = 1000;
|
||||||
|
|
|
||||||
|
|
@ -4,6 +4,8 @@ function editZones() {
|
||||||
closeDialogs();
|
closeDialogs();
|
||||||
if (!layerIsOn("toggleZones")) toggleZones();
|
if (!layerIsOn("toggleZones")) toggleZones();
|
||||||
const body = document.getElementById("zonesBodySection");
|
const body = document.getElementById("zonesBodySection");
|
||||||
|
|
||||||
|
updateFilters();
|
||||||
zonesEditorAddLines();
|
zonesEditorAddLines();
|
||||||
|
|
||||||
if (modules.editZones) return;
|
if (modules.editZones) return;
|
||||||
|
|
@ -18,6 +20,8 @@ function editZones() {
|
||||||
});
|
});
|
||||||
|
|
||||||
// add listeners
|
// add listeners
|
||||||
|
document.getElementById("zonesFilterType").addEventListener("click", updateFilters);
|
||||||
|
document.getElementById("zonesFilterType").addEventListener("change", filterZonesByType);
|
||||||
document.getElementById("zonesEditorRefresh").addEventListener("click", zonesEditorAddLines);
|
document.getElementById("zonesEditorRefresh").addEventListener("click", zonesEditorAddLines);
|
||||||
document.getElementById("zonesEditStyle").addEventListener("click", () => editStyle("zones"));
|
document.getElementById("zonesEditStyle").addEventListener("click", () => editStyle("zones"));
|
||||||
document.getElementById("zonesLegend").addEventListener("click", toggleLegend);
|
document.getElementById("zonesLegend").addEventListener("click", toggleLegend);
|
||||||
|
|
@ -33,55 +37,60 @@ function editZones() {
|
||||||
const el = ev.target,
|
const el = ev.target,
|
||||||
cl = el.classList,
|
cl = el.classList,
|
||||||
zone = el.parentNode.dataset.id;
|
zone = el.parentNode.dataset.id;
|
||||||
if (cl.contains("culturePopulation")) {
|
if (el.tagName === "FILL-BOX") changeFill(el);
|
||||||
changePopulation(zone);
|
else if (cl.contains("culturePopulation")) changePopulation(zone);
|
||||||
return;
|
else if (cl.contains("icon-trash-empty")) zoneRemove(zone);
|
||||||
}
|
else if (cl.contains("icon-eye")) toggleVisibility(el);
|
||||||
if (cl.contains("icon-trash-empty")) {
|
else if (cl.contains("icon-pin")) toggleFog(zone, cl);
|
||||||
zoneRemove(zone);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (cl.contains("icon-eye")) {
|
|
||||||
toggleVisibility(el);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (cl.contains("icon-pin")) {
|
|
||||||
toggleFog(zone, cl);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (cl.contains("fillRect")) {
|
|
||||||
changeFill(el);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (customization) selectZone(el);
|
if (customization) selectZone(el);
|
||||||
});
|
});
|
||||||
|
|
||||||
body.addEventListener("input", function (ev) {
|
body.addEventListener("input", function (ev) {
|
||||||
const el = ev.target,
|
const el = ev.target;
|
||||||
zone = el.parentNode.dataset.id;
|
const zone = zones.select("#" + el.parentNode.dataset.id);
|
||||||
if (el.classList.contains("religionName")) zones.select("#" + zone).attr("data-description", el.value);
|
|
||||||
|
if (el.classList.contains("zoneName")) zone.attr("data-description", el.value);
|
||||||
|
else if (el.classList.contains("zoneType")) zone.attr("data-type", el.value);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// update type filter with a list of used types
|
||||||
|
function updateFilters() {
|
||||||
|
const zones = Array.from(document.querySelectorAll("#zones > g"));
|
||||||
|
const types = unique(zones.map(zone => zone.dataset.type));
|
||||||
|
|
||||||
|
const filterSelect = document.getElementById("zonesFilterType");
|
||||||
|
const typeToFilterBy = types.includes(zonesFilterType.value) ? zonesFilterType.value : "all";
|
||||||
|
|
||||||
|
filterSelect.innerHTML = "<option value='all'>all</option>" + types.map(type => `<option value="${type}">${type}</option>`).join("");
|
||||||
|
filterSelect.value = typeToFilterBy;
|
||||||
|
}
|
||||||
|
|
||||||
// add line for each zone
|
// add line for each zone
|
||||||
function zonesEditorAddLines() {
|
function zonesEditorAddLines() {
|
||||||
const unit = areaUnit.value === "square" ? " " + distanceUnitInput.value + "²" : " " + areaUnit.value;
|
const unit = areaUnit.value === "square" ? " " + distanceUnitInput.value + "²" : " " + areaUnit.value;
|
||||||
let lines = "";
|
|
||||||
|
|
||||||
zones.selectAll("g").each(function () {
|
const typeToFilterBy = document.getElementById("zonesFilterType").value;
|
||||||
const c = this.dataset.cells ? this.dataset.cells.split(",").map(c => +c) : [];
|
const zones = Array.from(document.querySelectorAll("#zones > g"));
|
||||||
const description = this.dataset.description;
|
const filteredZones = typeToFilterBy === "all" ? zones : zones.filter(zone => zone.dataset.type === typeToFilterBy);
|
||||||
const fill = this.getAttribute("fill");
|
|
||||||
|
const lines = filteredZones.map(zoneEl => {
|
||||||
|
const c = zoneEl.dataset.cells ? zoneEl.dataset.cells.split(",").map(c => +c) : [];
|
||||||
|
const description = zoneEl.dataset.description;
|
||||||
|
const type = zoneEl.dataset.type;
|
||||||
|
const fill = zoneEl.getAttribute("fill");
|
||||||
const area = d3.sum(c.map(i => pack.cells.area[i])) * distanceScaleInput.value ** 2;
|
const area = d3.sum(c.map(i => pack.cells.area[i])) * distanceScaleInput.value ** 2;
|
||||||
const rural = d3.sum(c.map(i => pack.cells.pop[i])) * populationRate;
|
const rural = d3.sum(c.map(i => pack.cells.pop[i])) * populationRate;
|
||||||
const urban = d3.sum(c.map(i => pack.cells.burg[i]).map(b => pack.burgs[b].population)) * populationRate * urbanization;
|
const urban = d3.sum(c.map(i => pack.cells.burg[i]).map(b => pack.burgs[b].population)) * populationRate * urbanization;
|
||||||
const population = rural + urban;
|
const population = rural + urban;
|
||||||
const populationTip = `Total population: ${si(population)}; Rural population: ${si(rural)}; Urban population: ${si(urban)}. Click to change`;
|
const populationTip = `Total population: ${si(population)}; Rural population: ${si(rural)}; Urban population: ${si(urban)}. Click to change`;
|
||||||
const inactive = this.style.display === "none";
|
const inactive = zoneEl.style.display === "none";
|
||||||
const focused = defs.select("#fog #focus" + this.id).size();
|
const focused = defs.select("#fog #focus" + zoneEl.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}>
|
return `<div class="states" data-id="${zoneEl.id}" data-fill="${fill}" data-description="${description}"
|
||||||
<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>
|
data-type="${type}" data-cells=${c.length} data-area=${area} data-population=${population}>
|
||||||
<input data-tip="Zone description. Click and type to change" class="religionName" value="${description}" autocorrect="off" spellcheck="false">
|
<fill-box fill="${fill}"></fill-box>
|
||||||
|
<input data-tip="Zone description. Click and type to change" style="width: 11em" class="zoneName" value="${description}" autocorrect="off" spellcheck="false">
|
||||||
|
<input data-tip="Zone type. Click and type to change" class="zoneType" value="${type}">
|
||||||
<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>
|
||||||
<span data-tip="Zone area" style="padding-right:4px" class="icon-map-o hide"></span>
|
<span data-tip="Zone area" style="padding-right:4px" class="icon-map-o hide"></span>
|
||||||
|
|
@ -95,13 +104,13 @@ function editZones() {
|
||||||
</div>`;
|
</div>`;
|
||||||
});
|
});
|
||||||
|
|
||||||
body.innerHTML = lines;
|
body.innerHTML = lines.join("");
|
||||||
|
|
||||||
// update footer
|
// update footer
|
||||||
const totalArea = (zonesFooterArea.dataset.area = graphWidth * graphHeight * distanceScaleInput.value ** 2);
|
const totalArea = (zonesFooterArea.dataset.area = graphWidth * graphHeight * distanceScaleInput.value ** 2);
|
||||||
const totalPop = (d3.sum(pack.cells.pop) + d3.sum(pack.burgs.filter(b => !b.removed).map(b => b.population)) * urbanization) * populationRate;
|
const totalPop = (d3.sum(pack.cells.pop) + d3.sum(pack.burgs.filter(b => !b.removed).map(b => b.population)) * urbanization) * populationRate;
|
||||||
zonesFooterPopulation.dataset.population = totalPop;
|
zonesFooterPopulation.dataset.population = totalPop;
|
||||||
zonesFooterNumber.innerHTML = zones.selectAll("g").size();
|
zonesFooterNumber.innerHTML = `${filteredZones.length} of ${zones.length}`;
|
||||||
zonesFooterCells.innerHTML = pack.cells.i.length;
|
zonesFooterCells.innerHTML = pack.cells.i.length;
|
||||||
zonesFooterArea.innerHTML = si(totalArea) + unit;
|
zonesFooterArea.innerHTML = si(totalArea) + unit;
|
||||||
zonesFooterPopulation.innerHTML = si(totalPop);
|
zonesFooterPopulation.innerHTML = si(totalPop);
|
||||||
|
|
@ -127,6 +136,19 @@ function editZones() {
|
||||||
zones.select("#" + zone).style("outline", null);
|
zones.select("#" + zone).style("outline", null);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function filterZonesByType() {
|
||||||
|
const typeToFilterBy = this.value;
|
||||||
|
const zones = Array.from(document.querySelectorAll("#zones > g"));
|
||||||
|
|
||||||
|
for (const zone of zones) {
|
||||||
|
const type = zone.dataset.type;
|
||||||
|
const visible = typeToFilterBy === "all" || type === typeToFilterBy;
|
||||||
|
zone.style.display = visible ? "block" : "none";
|
||||||
|
}
|
||||||
|
|
||||||
|
zonesEditorAddLines();
|
||||||
|
}
|
||||||
|
|
||||||
$(body).sortable({items: "div.states", handle: ".icon-resize-vertical", containment: "parent", axis: "y", update: movezone});
|
$(body).sortable({items: "div.states", handle: ".icon-resize-vertical", containment: "parent", axis: "y", update: movezone});
|
||||||
function movezone(ev, ui) {
|
function movezone(ev, ui) {
|
||||||
const zone = $("#" + ui.item.attr("data-id"));
|
const zone = $("#" + ui.item.attr("data-id"));
|
||||||
|
|
@ -142,7 +164,7 @@ function editZones() {
|
||||||
function enterZonesManualAssignent() {
|
function enterZonesManualAssignent() {
|
||||||
if (!layerIsOn("toggleZones")) toggleZones();
|
if (!layerIsOn("toggleZones")) toggleZones();
|
||||||
customization = 10;
|
customization = 10;
|
||||||
document.querySelectorAll("#zonesBottom > button").forEach(el => (el.style.display = "none"));
|
document.querySelectorAll("#zonesBottom > *").forEach(el => (el.style.display = "none"));
|
||||||
document.getElementById("zonesManuallyButtons").style.display = "inline-block";
|
document.getElementById("zonesManuallyButtons").style.display = "inline-block";
|
||||||
|
|
||||||
zonesEditor.querySelectorAll(".hide").forEach(el => el.classList.add("hidden"));
|
zonesEditor.querySelectorAll(".hide").forEach(el => el.classList.add("hidden"));
|
||||||
|
|
@ -256,7 +278,7 @@ function editZones() {
|
||||||
function exitZonesManualAssignment(close) {
|
function exitZonesManualAssignment(close) {
|
||||||
customization = 0;
|
customization = 0;
|
||||||
removeCircle();
|
removeCircle();
|
||||||
document.querySelectorAll("#zonesBottom > button").forEach(el => (el.style.display = "inline-block"));
|
document.querySelectorAll("#zonesBottom > *").forEach(el => (el.style.display = "inline-block"));
|
||||||
document.getElementById("zonesManuallyButtons").style.display = "none";
|
document.getElementById("zonesManuallyButtons").style.display = "none";
|
||||||
|
|
||||||
zonesEditor.querySelectorAll(".hide:not(.show)").forEach(el => el.classList.remove("hidden"));
|
zonesEditor.querySelectorAll(".hide:not(.show)").forEach(el => el.classList.remove("hidden"));
|
||||||
|
|
@ -275,9 +297,9 @@ function editZones() {
|
||||||
|
|
||||||
function changeFill(el) {
|
function changeFill(el) {
|
||||||
const fill = el.getAttribute("fill");
|
const fill = el.getAttribute("fill");
|
||||||
const callback = function (fill) {
|
const callback = newFill => {
|
||||||
el.setAttribute("fill", fill);
|
el.fill = newFill;
|
||||||
document.getElementById(el.parentNode.parentNode.dataset.id).setAttribute("fill", fill);
|
document.getElementById(el.parentNode.dataset.id).setAttribute("fill", newFill);
|
||||||
};
|
};
|
||||||
|
|
||||||
openPicker(fill, callback);
|
openPicker(fill, callback);
|
||||||
|
|
@ -344,37 +366,22 @@ function editZones() {
|
||||||
function addZonesLayer() {
|
function addZonesLayer() {
|
||||||
const id = getNextId("zone");
|
const id = getNextId("zone");
|
||||||
const description = "Unknown zone";
|
const description = "Unknown zone";
|
||||||
const fill = "url(#hatch" + (id.slice(4) % 14) + ")";
|
const type = "Unknown";
|
||||||
zones.append("g").attr("id", id).attr("data-description", description).attr("data-cells", "").attr("fill", fill);
|
const fill = "url(#hatch" + (id.slice(4) % 42) + ")";
|
||||||
const unit = areaUnit.value === "square" ? " " + distanceUnitInput.value + "²" : " " + areaUnit.value;
|
zones.append("g").attr("id", id).attr("data-description", description).attr("data-type", type).attr("data-cells", "").attr("fill", fill);
|
||||||
|
|
||||||
const line = `<div class="states" data-id="${id}" data-fill="${fill}" data-description="${description}" data-cells=0 data-area=0 data-population=0>
|
zonesEditorAddLines();
|
||||||
<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">
|
|
||||||
<span data-tip="Cells count" class="icon-check-empty hide"></span>
|
|
||||||
<div data-tip="Cells count" class="stateCells hide">0</div>
|
|
||||||
<span data-tip="Zone area" style="padding-right:4px" class="icon-map-o hide"></span>
|
|
||||||
<div data-tip="Zone area" class="biomeArea hide">0 ${unit}</div>
|
|
||||||
<span class="icon-male hide"></span>
|
|
||||||
<div class="culturePopulation hide">0</div>
|
|
||||||
<span data-tip="Drag to raise or lower the zone" class="icon-resize-vertical hide"></span>
|
|
||||||
<span data-tip="Toggle zone focus" class="icon-pin inactive hide placeholder"></span>
|
|
||||||
<span data-tip="Toggle zone visibility" class="icon-eye hide placeholder"></span>
|
|
||||||
<span data-tip="Remove zone" class="icon-trash-empty hide"></span>
|
|
||||||
</div>`;
|
|
||||||
|
|
||||||
body.insertAdjacentHTML("beforeend", line);
|
|
||||||
zonesFooterNumber.innerHTML = zones.selectAll("g").size();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function downloadZonesData() {
|
function downloadZonesData() {
|
||||||
const unit = areaUnit.value === "square" ? distanceUnitInput.value + "2" : areaUnit.value;
|
const unit = areaUnit.value === "square" ? distanceUnitInput.value + "2" : areaUnit.value;
|
||||||
let data = "Id,Fill,Description,Cells,Area " + unit + ",Population\n"; // headers
|
let data = "Id,Fill,Description,Type,Cells,Area " + unit + ",Population\n"; // headers
|
||||||
|
|
||||||
body.querySelectorAll(":scope > div").forEach(function (el) {
|
body.querySelectorAll(":scope > div").forEach(function (el) {
|
||||||
data += el.dataset.id + ",";
|
data += el.dataset.id + ",";
|
||||||
data += el.dataset.fill + ",";
|
data += el.dataset.fill + ",";
|
||||||
data += el.dataset.description + ",";
|
data += el.dataset.description + ",";
|
||||||
|
data += el.dataset.type + ",";
|
||||||
data += el.dataset.cells + ",";
|
data += el.dataset.cells + ",";
|
||||||
data += el.dataset.area + ",";
|
data += el.dataset.area + ",";
|
||||||
data += el.dataset.population + "\n";
|
data += el.dataset.population + "\n";
|
||||||
|
|
|
||||||
|
|
@ -1,3 +0,0 @@
|
||||||
start chrome.exe http://localhost:8000/
|
|
||||||
@echo off
|
|
||||||
php -S localhost:8000
|
|
||||||
389
styles/ancient.json
Normal file
|
|
@ -0,0 +1,389 @@
|
||||||
|
{
|
||||||
|
"#map": {
|
||||||
|
"background-color": "#000000",
|
||||||
|
"filter": null,
|
||||||
|
"data-filter": null
|
||||||
|
},
|
||||||
|
"#armies": {
|
||||||
|
"font-size": 8,
|
||||||
|
"box-size": 4,
|
||||||
|
"stroke": "#000",
|
||||||
|
"stroke-width": 0.2,
|
||||||
|
"fill-opacity": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#biomes": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#stateBorders": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#provinceBorders": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 0.2,
|
||||||
|
"stroke-dasharray": 1,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cells": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#gridOverlay": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"scale": 1,
|
||||||
|
"dx": 0,
|
||||||
|
"dy": 0,
|
||||||
|
"type": "pointyHex",
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#coordinates": {
|
||||||
|
"opacity": 1,
|
||||||
|
"data-size": 12,
|
||||||
|
"font-size": 12,
|
||||||
|
"stroke": "#d4d4d4",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 5,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#compass": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"transform": null,
|
||||||
|
"filter": "url(#filter-sepia)",
|
||||||
|
"mask": "url(#water)",
|
||||||
|
"shape-rendering": "optimizespeed"
|
||||||
|
},
|
||||||
|
"#rose": {
|
||||||
|
"transform": "translate(80 80) scale(.25)"
|
||||||
|
},
|
||||||
|
"#relig": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#404040",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cults": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#landmass": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#e3dfce",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#markers": {
|
||||||
|
"opacity": null,
|
||||||
|
"rescale": 1,
|
||||||
|
"filter": ""
|
||||||
|
},
|
||||||
|
"#prec": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"fill": "#003dff",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#population": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke-width": 1.6,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#rural": {
|
||||||
|
"stroke": "#0000ff"
|
||||||
|
},
|
||||||
|
"#urban": {
|
||||||
|
"stroke": "#ff0000"
|
||||||
|
},
|
||||||
|
"#freshwater": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"fill": "#c8d6e0",
|
||||||
|
"stroke": "#968d6e",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#salt": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#339482",
|
||||||
|
"stroke": "#836a34",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sinkhole": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#c3d6df",
|
||||||
|
"stroke": "#b29062",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#frozen": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#cdd4e7",
|
||||||
|
"stroke": "#cfe0eb",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#lava": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#a04e18",
|
||||||
|
"stroke": "#835520",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"filter": "url(#paper)"
|
||||||
|
},
|
||||||
|
"#dry": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#c6b795",
|
||||||
|
"stroke": "#8e816f",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sea_island": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke": "#1f3846",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": "url(#dropShadow)",
|
||||||
|
"auto-filter": 1
|
||||||
|
},
|
||||||
|
"#lake_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#7c8eaf",
|
||||||
|
"stroke-width": 0.35,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#terrain": {
|
||||||
|
"opacity": 1,
|
||||||
|
"set": "simple",
|
||||||
|
"size": 1,
|
||||||
|
"density": 0.4,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#rivers": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": "",
|
||||||
|
"fill": "#a69b7d"
|
||||||
|
},
|
||||||
|
"#ruler": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#roads": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#8d502a",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 3,
|
||||||
|
"stroke-linecap": "inherit",
|
||||||
|
"filter": "",
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#trails": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#924217",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": "1 2",
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#searoutes": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#b16925",
|
||||||
|
"stroke-width": 0.8,
|
||||||
|
"stroke-dasharray": "1 2",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#statesBody": {
|
||||||
|
"opacity": 0.2,
|
||||||
|
"filter": "url(#filter-sepia)"
|
||||||
|
},
|
||||||
|
"#statesHalo": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"data-width": 10,
|
||||||
|
"stroke-width": 10,
|
||||||
|
"filter": "blur(6px)"
|
||||||
|
},
|
||||||
|
"#provs": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#000000",
|
||||||
|
"font-size": 10,
|
||||||
|
"font-family": "Georgia",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#temperature": {
|
||||||
|
"opacity": null,
|
||||||
|
"font-size": "8px",
|
||||||
|
"fill": "#000000",
|
||||||
|
"fill-opacity": 0.3,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 1.8,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#ice": {
|
||||||
|
"opacity": 0.35,
|
||||||
|
"fill": "#e8f0f6",
|
||||||
|
"stroke": "#e8f0f6",
|
||||||
|
"stroke-width": 3,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#emblems": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke-width": 0.8,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#texture": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"filter": "",
|
||||||
|
"mask": ""
|
||||||
|
},
|
||||||
|
"#textureImage": {
|
||||||
|
"x": 0,
|
||||||
|
"y": 0
|
||||||
|
},
|
||||||
|
"#zones": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#333333",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#oceanLayers": {
|
||||||
|
"filter": "",
|
||||||
|
"layers": "-6,-4,-2"
|
||||||
|
},
|
||||||
|
"#oceanBase": {
|
||||||
|
"fill": "#c99f64"
|
||||||
|
},
|
||||||
|
"#oceanicPattern": {
|
||||||
|
"href": "./images/kiwiroo.png",
|
||||||
|
"opacity": 0.4
|
||||||
|
},
|
||||||
|
"#terrs": {
|
||||||
|
"opacity": null,
|
||||||
|
"scheme": "bright",
|
||||||
|
"terracing": 0,
|
||||||
|
"skip": 2,
|
||||||
|
"relax": 1,
|
||||||
|
"curve": 0,
|
||||||
|
"filter": "url(#blur3)",
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#legend": {
|
||||||
|
"data-size": 13,
|
||||||
|
"font-size": 13,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"stroke": "#812929",
|
||||||
|
"stroke-width": 2.5,
|
||||||
|
"stroke-dasharray": "0 4 10 4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"data-x": 99,
|
||||||
|
"data-y": 93,
|
||||||
|
"data-columns": 8
|
||||||
|
},
|
||||||
|
"#burgLabels > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 12,
|
||||||
|
"font-size": 12,
|
||||||
|
"font-family": "Great Vibes"
|
||||||
|
},
|
||||||
|
"#burgIcons > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#fdfab9",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#6f4e1f",
|
||||||
|
"stroke-width": 0.3,
|
||||||
|
"stroke-dasharray": ".3 .4",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 2,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#burgLabels > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 5,
|
||||||
|
"font-size": 5,
|
||||||
|
"font-family": "Great Vibes"
|
||||||
|
},
|
||||||
|
"#burgIcons > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#fef4d8",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 0.5,
|
||||||
|
"stroke": "#72472c",
|
||||||
|
"stroke-width": 0.12,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#labels > #states": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"stroke": "#3a3a3a",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 22,
|
||||||
|
"font-size": 22,
|
||||||
|
"font-family": "Great Vibes",
|
||||||
|
"filter": "url(#filter-sepia)"
|
||||||
|
},
|
||||||
|
"#labels > #addedLabels": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"stroke": "#3a3a3a",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 18,
|
||||||
|
"font-size": 18,
|
||||||
|
"font-family": "Times New Roman",
|
||||||
|
"filter": "url(#filter-sepia)"
|
||||||
|
},
|
||||||
|
"#fogging": {
|
||||||
|
"opacity": 0.98,
|
||||||
|
"fill": "#30426f",
|
||||||
|
"filter": null
|
||||||
|
}
|
||||||
|
}
|
||||||
385
styles/atlas.json
Normal file
|
|
@ -0,0 +1,385 @@
|
||||||
|
{
|
||||||
|
"#map": {
|
||||||
|
"background-color": "#000000",
|
||||||
|
"filter": null,
|
||||||
|
"data-filter": null
|
||||||
|
},
|
||||||
|
"#armies": {
|
||||||
|
"font-size": 6,
|
||||||
|
"box-size": 3,
|
||||||
|
"stroke": "#000",
|
||||||
|
"stroke-width": 0.3,
|
||||||
|
"fill-opacity": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#biomes": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#stateBorders": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 1.01,
|
||||||
|
"stroke-dasharray": 0,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#provinceBorders": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.69,
|
||||||
|
"stroke-dasharray": 0,
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cells": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#gridOverlay": {
|
||||||
|
"opacity": 1,
|
||||||
|
"scale": 7.99,
|
||||||
|
"dx": -2,
|
||||||
|
"dy": 3,
|
||||||
|
"type": "square",
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.05,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#coordinates": {
|
||||||
|
"opacity": 1,
|
||||||
|
"data-size": 12,
|
||||||
|
"font-size": 12,
|
||||||
|
"stroke": "#d4d4d4",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 5,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#compass": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#water)",
|
||||||
|
"shape-rendering": "optimizespeed"
|
||||||
|
},
|
||||||
|
"#rose": {
|
||||||
|
"transform": "translate(80 80) scale(.25)"
|
||||||
|
},
|
||||||
|
"#relig": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cults": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#landmass": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#eef6fb",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#markers": {
|
||||||
|
"opacity": null,
|
||||||
|
"rescale": 1,
|
||||||
|
"filter": "url(#dropShadow01)"
|
||||||
|
},
|
||||||
|
"#prec": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"fill": "#003dff",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#population": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke-width": 1.6,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#rural": {
|
||||||
|
"stroke": "#0000ff"
|
||||||
|
},
|
||||||
|
"#urban": {
|
||||||
|
"stroke": "#ff0000"
|
||||||
|
},
|
||||||
|
"#freshwater": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#cae3f7",
|
||||||
|
"stroke": "#0089ca",
|
||||||
|
"stroke-width": 1.01,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#salt": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#cae3f7",
|
||||||
|
"stroke": "#0089ca",
|
||||||
|
"stroke-width": 1.01,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sinkhole": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#cae3f7",
|
||||||
|
"stroke": "#0089ca",
|
||||||
|
"stroke-width": 1.01,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#frozen": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#cdd4e7",
|
||||||
|
"stroke": "#cfe0eb",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#lava": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#90270d",
|
||||||
|
"stroke": "#f93e0c",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"filter": "url(#crumpled)"
|
||||||
|
},
|
||||||
|
"#dry": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#c9bfa7",
|
||||||
|
"stroke": "#8e816f",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sea_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#028ac9",
|
||||||
|
"stroke-width": 1.01,
|
||||||
|
"filter": "",
|
||||||
|
"auto-filter": 0
|
||||||
|
},
|
||||||
|
"#lake_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#7c8eaf",
|
||||||
|
"stroke-width": 0.35,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#terrain": {
|
||||||
|
"opacity": null,
|
||||||
|
"set": "simple",
|
||||||
|
"size": 1,
|
||||||
|
"density": 0.4,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#rivers": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"fill": "#0089ca"
|
||||||
|
},
|
||||||
|
"#ruler": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#roads": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#ff2c2c",
|
||||||
|
"stroke-width": 1.05,
|
||||||
|
"stroke-dasharray": 0,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#trails": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#9f5122",
|
||||||
|
"stroke-width": 0.43,
|
||||||
|
"stroke-dasharray": 0,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#searoutes": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#0089ca",
|
||||||
|
"stroke-width": 0.45,
|
||||||
|
"stroke-dasharray": "1 2",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#statesBody": {
|
||||||
|
"opacity": 0.49,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#statesHalo": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"data-width": 10,
|
||||||
|
"stroke-width": 10,
|
||||||
|
"filter": "blur(5px)"
|
||||||
|
},
|
||||||
|
"#provs": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"font-size": 10,
|
||||||
|
"font-family": "Georgia",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#temperature": {
|
||||||
|
"opacity": null,
|
||||||
|
"font-size": "8px",
|
||||||
|
"fill": "#000000",
|
||||||
|
"fill-opacity": 0.3,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 1.8,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#ice": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"fill": "#e8f0f6",
|
||||||
|
"stroke": "#e8f0f6",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#emblems": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#texture": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#zones": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#333333",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#oceanLayers": {
|
||||||
|
"filter": "",
|
||||||
|
"layers": "none"
|
||||||
|
},
|
||||||
|
"#oceanBase": {
|
||||||
|
"fill": "#b4d2f3"
|
||||||
|
},
|
||||||
|
"#oceanicPattern": {
|
||||||
|
"href": "",
|
||||||
|
"opacity": 1
|
||||||
|
},
|
||||||
|
"#terrs": {
|
||||||
|
"opacity": null,
|
||||||
|
"scheme": "bright",
|
||||||
|
"terracing": 0,
|
||||||
|
"skip": 0,
|
||||||
|
"relax": 0,
|
||||||
|
"curve": 0,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#legend": {
|
||||||
|
"data-size": 13,
|
||||||
|
"font-size": 13,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"stroke": "#812929",
|
||||||
|
"stroke-width": 2.5,
|
||||||
|
"stroke-dasharray": "0 4 10 4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"data-x": 99,
|
||||||
|
"data-y": 93,
|
||||||
|
"data-columns": 8
|
||||||
|
},
|
||||||
|
"#burgLabels > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 5,
|
||||||
|
"font-size": 5,
|
||||||
|
"font-family": "Questrial"
|
||||||
|
},
|
||||||
|
"#burgIcons > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.24,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "round"
|
||||||
|
},
|
||||||
|
"#anchors > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 2,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#burgLabels > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 4,
|
||||||
|
"font-size": 4,
|
||||||
|
"font-family": "Questrial"
|
||||||
|
},
|
||||||
|
"#burgIcons > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 0.5,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.12,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "round"
|
||||||
|
},
|
||||||
|
"#anchors > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#labels > #states": {
|
||||||
|
"opacity": 0,
|
||||||
|
"fill": "#000000",
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 21,
|
||||||
|
"font-size": 21,
|
||||||
|
"font-family": "Questrial",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#labels > #addedLabels": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 18,
|
||||||
|
"font-size": 18,
|
||||||
|
"font-family": "Questrial",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#fogging": {
|
||||||
|
"opacity": 0.98,
|
||||||
|
"fill": "#30426f",
|
||||||
|
"filter": null
|
||||||
|
}
|
||||||
|
}
|
||||||
388
styles/clean.json
Normal file
|
|
@ -0,0 +1,388 @@
|
||||||
|
{
|
||||||
|
"#map": {
|
||||||
|
"background-color": "#000000",
|
||||||
|
"filter": null,
|
||||||
|
"data-filter": null
|
||||||
|
},
|
||||||
|
"#armies": {
|
||||||
|
"font-size": 6,
|
||||||
|
"box-size": 3,
|
||||||
|
"stroke": "#000",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"opacity": 1,
|
||||||
|
"fill-opacity": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#biomes": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"filter": "url(#blur7)",
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#stateBorders": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#414141",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"stroke-dasharray": 0,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#provinceBorders": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#414141",
|
||||||
|
"stroke-width": 0.45,
|
||||||
|
"stroke-dasharray": 1,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cells": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.09,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#gridOverlay": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"scale": 1,
|
||||||
|
"dx": 0,
|
||||||
|
"dy": "0",
|
||||||
|
"type": "pointyHex",
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#coordinates": {
|
||||||
|
"opacity": 1,
|
||||||
|
"data-size": 12,
|
||||||
|
"font-size": 12,
|
||||||
|
"stroke": "#414141",
|
||||||
|
"stroke-width": 0.45,
|
||||||
|
"stroke-dasharray": 3,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#compass": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#water)",
|
||||||
|
"shape-rendering": "optimizespeed"
|
||||||
|
},
|
||||||
|
"#rose": {
|
||||||
|
"transform": null
|
||||||
|
},
|
||||||
|
"#relig": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#404040",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cults": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#landmass": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#eeedeb",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#markers": {
|
||||||
|
"opacity": null,
|
||||||
|
"rescale": null,
|
||||||
|
"filter": "url(#dropShadow01)"
|
||||||
|
},
|
||||||
|
"#prec": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"fill": "#0080ff",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#population": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke-width": 2.58,
|
||||||
|
"stroke-dasharray": 0,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": "url(#blur3)"
|
||||||
|
},
|
||||||
|
"#rural": {
|
||||||
|
"stroke": "#ff0000"
|
||||||
|
},
|
||||||
|
"#urban": {
|
||||||
|
"stroke": "#800000"
|
||||||
|
},
|
||||||
|
"#freshwater": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#aadaff",
|
||||||
|
"stroke": "#5f799d",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#salt": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#409b8a",
|
||||||
|
"stroke": "#388985",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sinkhole": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#5bc9fd",
|
||||||
|
"stroke": "#53a3b0",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#frozen": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#cdd4e7",
|
||||||
|
"stroke": "#cfe0eb",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#lava": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#90270d",
|
||||||
|
"stroke": "#f93e0c",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"filter": "url(#crumpled)"
|
||||||
|
},
|
||||||
|
"#dry": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#c9bfa7",
|
||||||
|
"stroke": "#8e816f",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sea_island": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#595959",
|
||||||
|
"stroke-width": 0.4,
|
||||||
|
"filter": null,
|
||||||
|
"auto-filter": 0
|
||||||
|
},
|
||||||
|
"#lake_island": {
|
||||||
|
"opacity": 0,
|
||||||
|
"stroke": "#7c8eaf",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#terrain": {
|
||||||
|
"opacity": 1,
|
||||||
|
"set": "simple",
|
||||||
|
"size": 1,
|
||||||
|
"density": 0.4,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#rivers": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"fill": "#aadaff"
|
||||||
|
},
|
||||||
|
"#ruler": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#roads": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#f6d068",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"stroke-dasharray": 0,
|
||||||
|
"stroke-linecap": "inherit",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#trails": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#ffffff",
|
||||||
|
"stroke-width": 0.25,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#searoutes": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#4f82c6",
|
||||||
|
"stroke-width": 0.45,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#water)"
|
||||||
|
},
|
||||||
|
"#statesBody": {
|
||||||
|
"opacity": 0.3,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#statesHalo": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"data-width": 1,
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#provs": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#000000",
|
||||||
|
"data-size": 10,
|
||||||
|
"font-size": 10,
|
||||||
|
"font-family": "Georgia",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#temperature": {
|
||||||
|
"opacity": null,
|
||||||
|
"font-size": "8px",
|
||||||
|
"fill": "#000000",
|
||||||
|
"fill-opacity": 0.3,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 1.8,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#ice": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"fill": "#e8f0f6",
|
||||||
|
"stroke": "#e8f0f6",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": "url(#dropShadow01)"
|
||||||
|
},
|
||||||
|
"#emblems": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#texture": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#textureImage": {},
|
||||||
|
"#zones": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#ff6262",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#oceanLayers": {
|
||||||
|
"filter": null,
|
||||||
|
"layers": "none"
|
||||||
|
},
|
||||||
|
"#oceanBase": {
|
||||||
|
"fill": "#aadaff"
|
||||||
|
},
|
||||||
|
"#oceanicPattern": {
|
||||||
|
"href": "",
|
||||||
|
"opacity": 0.2
|
||||||
|
},
|
||||||
|
"#terrs": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"scheme": "bright",
|
||||||
|
"terracing": 0,
|
||||||
|
"skip": 5,
|
||||||
|
"relax": 0,
|
||||||
|
"curve": 0,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#legend": {
|
||||||
|
"data-size": 12.74,
|
||||||
|
"font-size": 12.74,
|
||||||
|
"font-family": "Arial",
|
||||||
|
"stroke": "#909090",
|
||||||
|
"stroke-width": 1.13,
|
||||||
|
"stroke-dasharray": 0,
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"data-x": 98.39,
|
||||||
|
"data-y": 12.67,
|
||||||
|
"data-columns": null
|
||||||
|
},
|
||||||
|
"#legendBox": {},
|
||||||
|
"#burgLabels > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#414141",
|
||||||
|
"text-shadow": "white 0 0 4px",
|
||||||
|
"data-size": 7,
|
||||||
|
"font-size": 7,
|
||||||
|
"font-family": "Arial"
|
||||||
|
},
|
||||||
|
"#burgIcons > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.24,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 2,
|
||||||
|
"stroke": "#303030",
|
||||||
|
"stroke-width": 1.7
|
||||||
|
},
|
||||||
|
"#burgLabels > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#414141",
|
||||||
|
"data-size": 3,
|
||||||
|
"font-size": 3,
|
||||||
|
"font-family": "Arial"
|
||||||
|
},
|
||||||
|
"#burgIcons > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 0.5,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.12,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.06
|
||||||
|
},
|
||||||
|
"#labels > #states": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#292929",
|
||||||
|
"stroke": "#303030",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0 0 2px",
|
||||||
|
"data-size": 10,
|
||||||
|
"font-size": 10,
|
||||||
|
"font-family": "Arial",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#labels > #addedLabels": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#414141",
|
||||||
|
"stroke": "#3a3a3a",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0 0 4px",
|
||||||
|
"data-size": 18,
|
||||||
|
"font-size": 18,
|
||||||
|
"font-family": "Arial",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#fogging": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"filter": null
|
||||||
|
}
|
||||||
|
}
|
||||||
385
styles/cyberpunk.json
Normal file
|
|
@ -0,0 +1,385 @@
|
||||||
|
{
|
||||||
|
"#map": {
|
||||||
|
"background-color": "#000000",
|
||||||
|
"filter": null,
|
||||||
|
"data-filter": null
|
||||||
|
},
|
||||||
|
"#armies": {
|
||||||
|
"font-size": 8,
|
||||||
|
"box-size": 4,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.6,
|
||||||
|
"fill-opacity": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#biomes": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"filter": "",
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#stateBorders": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#ffffff",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 3,
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": ""
|
||||||
|
},
|
||||||
|
"#provinceBorders": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke": "#ffffff",
|
||||||
|
"stroke-width": 0.3,
|
||||||
|
"stroke-dasharray": 1,
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": ""
|
||||||
|
},
|
||||||
|
"#cells": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#gridOverlay": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"scale": 1,
|
||||||
|
"dx": 0,
|
||||||
|
"dy": 0,
|
||||||
|
"type": "pointyHex",
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#coordinates": {
|
||||||
|
"opacity": 1,
|
||||||
|
"data-size": 14,
|
||||||
|
"font-size": 14,
|
||||||
|
"stroke": "#4a4a4a",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 6,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#compass": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "",
|
||||||
|
"shape-rendering": "optimizespeed"
|
||||||
|
},
|
||||||
|
"#rose": {
|
||||||
|
"transform": null
|
||||||
|
},
|
||||||
|
"#relig": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke": "#404040",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"filter": "url(#splotch)"
|
||||||
|
},
|
||||||
|
"#cults": {
|
||||||
|
"opacity": 0.35,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": "url(#splotch)"
|
||||||
|
},
|
||||||
|
"#landmass": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#04011e",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#markers": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"rescale": 1,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#prec": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"fill": "#003dff",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#population": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke-width": 1.6,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "square",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#rural": {
|
||||||
|
"stroke": "#5294ff"
|
||||||
|
},
|
||||||
|
"#urban": {
|
||||||
|
"stroke": "#5cdeff"
|
||||||
|
},
|
||||||
|
"#freshwater": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"fill": "#381579",
|
||||||
|
"stroke": "#47228c",
|
||||||
|
"stroke-width": 3,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#salt": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#409b8a",
|
||||||
|
"stroke": "#388985",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sinkhole": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#5bc9fd",
|
||||||
|
"stroke": "#53a3b0",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#frozen": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#cdd4e7",
|
||||||
|
"stroke": "#cfe0eb",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#lava": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#90270d",
|
||||||
|
"stroke": "#f93e0c",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"filter": "url(#crumpled)"
|
||||||
|
},
|
||||||
|
"#dry": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#c9bfa7",
|
||||||
|
"stroke": "#8e816f",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sea_island": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#1f3846",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": "url(#dropShadow)",
|
||||||
|
"auto-filter": 1
|
||||||
|
},
|
||||||
|
"#lake_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#7c8eaf",
|
||||||
|
"stroke-width": 0.35,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#terrain": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"set": "simple",
|
||||||
|
"size": 1,
|
||||||
|
"density": 0.4,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#rivers": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"fill": "#6738bc"
|
||||||
|
},
|
||||||
|
"#ruler": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#roads": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#c44ac0",
|
||||||
|
"stroke-width": 0.9,
|
||||||
|
"stroke-dasharray": "2 3",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#trails": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#df2654",
|
||||||
|
"stroke-width": 0.2,
|
||||||
|
"stroke-dasharray": ".5 1",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#searoutes": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#a890c6",
|
||||||
|
"stroke-width": 0.6,
|
||||||
|
"stroke-dasharray": "1.2 2.4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#statesBody": {
|
||||||
|
"opacity": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#statesHalo": {
|
||||||
|
"opacity": 1,
|
||||||
|
"data-width": 13,
|
||||||
|
"stroke-width": 13,
|
||||||
|
"filter": "blur(8.25px)"
|
||||||
|
},
|
||||||
|
"#provs": {
|
||||||
|
"opacity": 0.2,
|
||||||
|
"fill": "#933e3e",
|
||||||
|
"font-size": 8,
|
||||||
|
"font-family": "Orbitron",
|
||||||
|
"filter": ""
|
||||||
|
},
|
||||||
|
"#temperature": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"font-size": "22px",
|
||||||
|
"fill": "#551282",
|
||||||
|
"fill-opacity": 0.3,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 3,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#ice": {
|
||||||
|
"opacity": 0.3,
|
||||||
|
"fill": "#919191",
|
||||||
|
"stroke": "#949494",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#emblems": {
|
||||||
|
"opacity": 0.75,
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"filter": ""
|
||||||
|
},
|
||||||
|
"#texture": {
|
||||||
|
"opacity": 0.14,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#water)"
|
||||||
|
},
|
||||||
|
"#zones": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#ffffff",
|
||||||
|
"stroke-width": 0.3,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "inherit",
|
||||||
|
"filter": "url(#dropShadow05)",
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#oceanLayers": {
|
||||||
|
"filter": "",
|
||||||
|
"layers": "-6,-3,-1"
|
||||||
|
},
|
||||||
|
"#oceanBase": {
|
||||||
|
"fill": "#05001f"
|
||||||
|
},
|
||||||
|
"#oceanicPattern": {
|
||||||
|
"href": "",
|
||||||
|
"opacity": 0.15
|
||||||
|
},
|
||||||
|
"#terrs": {
|
||||||
|
"opacity": 1,
|
||||||
|
"scheme": "monochrome",
|
||||||
|
"terracing": 6,
|
||||||
|
"skip": 0,
|
||||||
|
"relax": 2,
|
||||||
|
"curve": 0,
|
||||||
|
"filter": "",
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#legend": {
|
||||||
|
"data-size": 13,
|
||||||
|
"font-size": 13,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"stroke": "#812929",
|
||||||
|
"stroke-width": 2.5,
|
||||||
|
"stroke-dasharray": "0 4 10 4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"data-x": 99,
|
||||||
|
"data-y": 93,
|
||||||
|
"data-columns": 8
|
||||||
|
},
|
||||||
|
"#burgLabels > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 8,
|
||||||
|
"font-size": 8,
|
||||||
|
"font-family": "Orbitron"
|
||||||
|
},
|
||||||
|
"#burgIcons > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 2,
|
||||||
|
"stroke": "#444444",
|
||||||
|
"stroke-width": 0.25,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 4,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1
|
||||||
|
},
|
||||||
|
"#burgLabels > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 3,
|
||||||
|
"font-size": 3,
|
||||||
|
"font-family": "Orbitron"
|
||||||
|
},
|
||||||
|
"#burgIcons > #towns": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 0.8,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.2,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 1.6,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1
|
||||||
|
},
|
||||||
|
"#labels > #states": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 18,
|
||||||
|
"font-size": 18,
|
||||||
|
"font-family": "Orbitron",
|
||||||
|
"filter": ""
|
||||||
|
},
|
||||||
|
"#labels > #addedLabels": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 18,
|
||||||
|
"font-size": 18,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#fogging": {
|
||||||
|
"opacity": 0.98,
|
||||||
|
"fill": "#1b1423",
|
||||||
|
"filter": null
|
||||||
|
}
|
||||||
|
}
|
||||||
385
styles/default.json
Normal file
|
|
@ -0,0 +1,385 @@
|
||||||
|
{
|
||||||
|
"#map": {
|
||||||
|
"background-color": "#000000",
|
||||||
|
"filter": null,
|
||||||
|
"data-filter": null
|
||||||
|
},
|
||||||
|
"#armies": {
|
||||||
|
"font-size": 6,
|
||||||
|
"box-size": 3,
|
||||||
|
"stroke": "#000",
|
||||||
|
"stroke-width": 0.3,
|
||||||
|
"fill-opacity": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#biomes": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#stateBorders": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#provinceBorders": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": "0 2",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cells": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#gridOverlay": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"scale": 1,
|
||||||
|
"dx": 0,
|
||||||
|
"dy": 0,
|
||||||
|
"type": "pointyHex",
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#coordinates": {
|
||||||
|
"opacity": 1,
|
||||||
|
"data-size": 12,
|
||||||
|
"font-size": 12,
|
||||||
|
"stroke": "#d4d4d4",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 5,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#compass": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#water)",
|
||||||
|
"shape-rendering": "optimizespeed"
|
||||||
|
},
|
||||||
|
"#rose": {
|
||||||
|
"transform": null
|
||||||
|
},
|
||||||
|
"#relig": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cults": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#landmass": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#eef6fb",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#markers": {
|
||||||
|
"opacity": null,
|
||||||
|
"rescale": 1,
|
||||||
|
"filter": "url(#dropShadow01)"
|
||||||
|
},
|
||||||
|
"#prec": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"fill": "#003dff",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#population": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke-width": 1.6,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#rural": {
|
||||||
|
"stroke": "#0000ff"
|
||||||
|
},
|
||||||
|
"#urban": {
|
||||||
|
"stroke": "#ff0000"
|
||||||
|
},
|
||||||
|
"#freshwater": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#a6c1fd",
|
||||||
|
"stroke": "#5f799d",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#salt": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#409b8a",
|
||||||
|
"stroke": "#388985",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sinkhole": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#5bc9fd",
|
||||||
|
"stroke": "#53a3b0",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#frozen": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#cdd4e7",
|
||||||
|
"stroke": "#cfe0eb",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#lava": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#90270d",
|
||||||
|
"stroke": "#f93e0c",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"filter": "url(#crumpled)"
|
||||||
|
},
|
||||||
|
"#dry": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#c9bfa7",
|
||||||
|
"stroke": "#8e816f",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sea_island": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke": "#1f3846",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": "url(#dropShadow)",
|
||||||
|
"auto-filter": 1
|
||||||
|
},
|
||||||
|
"#lake_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#7c8eaf",
|
||||||
|
"stroke-width": 0.35,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#terrain": {
|
||||||
|
"opacity": null,
|
||||||
|
"set": "simple",
|
||||||
|
"size": 1,
|
||||||
|
"density": 0.4,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#rivers": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"fill": "#5d97bb"
|
||||||
|
},
|
||||||
|
"#ruler": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#roads": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#d06324",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#trails": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#d06324",
|
||||||
|
"stroke-width": 0.25,
|
||||||
|
"stroke-dasharray": ".8 1.6",
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#searoutes": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#ffffff",
|
||||||
|
"stroke-width": 0.45,
|
||||||
|
"stroke-dasharray": "1 2",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#statesBody": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#statesHalo": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"data-width": 10,
|
||||||
|
"stroke-width": 10,
|
||||||
|
"filter": "blur(5px)"
|
||||||
|
},
|
||||||
|
"#provs": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#000000",
|
||||||
|
"font-size": 10,
|
||||||
|
"font-family": "Georgia",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#temperature": {
|
||||||
|
"opacity": null,
|
||||||
|
"font-size": "8px",
|
||||||
|
"fill": "#000000",
|
||||||
|
"fill-opacity": 0.3,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 1.8,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#ice": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"fill": "#e8f0f6",
|
||||||
|
"stroke": "#e8f0f6",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#emblems": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#texture": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#zones": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#333333",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#oceanLayers": {
|
||||||
|
"filter": null,
|
||||||
|
"layers": "-6,-3,-1"
|
||||||
|
},
|
||||||
|
"#oceanBase": {
|
||||||
|
"fill": "#466eab"
|
||||||
|
},
|
||||||
|
"#oceanicPattern": {
|
||||||
|
"href": "./images/pattern1.png",
|
||||||
|
"opacity": 0.2
|
||||||
|
},
|
||||||
|
"#terrs": {
|
||||||
|
"opacity": null,
|
||||||
|
"scheme": "bright",
|
||||||
|
"terracing": 0,
|
||||||
|
"skip": 5,
|
||||||
|
"relax": 0,
|
||||||
|
"curve": 0,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#legend": {
|
||||||
|
"data-size": 13,
|
||||||
|
"font-size": 13,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"stroke": "#812929",
|
||||||
|
"stroke-width": 2.5,
|
||||||
|
"stroke-dasharray": "0 4 10 4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"data-x": 99,
|
||||||
|
"data-y": 93,
|
||||||
|
"data-columns": 8
|
||||||
|
},
|
||||||
|
"#burgLabels > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 7,
|
||||||
|
"font-size": 7,
|
||||||
|
"font-family": "Almendra SC"
|
||||||
|
},
|
||||||
|
"#burgIcons > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.24,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 2,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#burgLabels > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 4,
|
||||||
|
"font-size": 4,
|
||||||
|
"font-family": "Almendra SC"
|
||||||
|
},
|
||||||
|
"#burgIcons > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 0.5,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.12,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#labels > #states": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"stroke": "#3a3a3a",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 22,
|
||||||
|
"font-size": 22,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#labels > #addedLabels": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"stroke": "#3a3a3a",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 18,
|
||||||
|
"font-size": 18,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#fogging": {
|
||||||
|
"opacity": 0.98,
|
||||||
|
"fill": "#30426f",
|
||||||
|
"filter": null
|
||||||
|
}
|
||||||
|
}
|
||||||
391
styles/gloom.json
Normal file
|
|
@ -0,0 +1,391 @@
|
||||||
|
{
|
||||||
|
"#map": {
|
||||||
|
"background-color": "#000000",
|
||||||
|
"filter": null,
|
||||||
|
"data-filter": null
|
||||||
|
},
|
||||||
|
"#armies": {
|
||||||
|
"font-size": 6,
|
||||||
|
"box-size": 3,
|
||||||
|
"stroke": "#000",
|
||||||
|
"stroke-width": 0.3,
|
||||||
|
"opacity": 1,
|
||||||
|
"fill-opacity": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#biomes": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": "url(#blur5)",
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#stateBorders": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#provinceBorders": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 0.3,
|
||||||
|
"stroke-dasharray": ".7 1",
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cells": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#gridOverlay": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"scale": 1,
|
||||||
|
"dx": 0,
|
||||||
|
"dy": "0",
|
||||||
|
"type": "pointyHex",
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#coordinates": {
|
||||||
|
"opacity": 1,
|
||||||
|
"data-size": 14,
|
||||||
|
"font-size": 14,
|
||||||
|
"stroke": "#4a4a4a",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 6,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#compass": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#water)",
|
||||||
|
"shape-rendering": "optimizespeed"
|
||||||
|
},
|
||||||
|
"#rose": {
|
||||||
|
"transform": "translate(100 100) scale(0.3)"
|
||||||
|
},
|
||||||
|
"#relig": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#404040",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cults": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 1.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#landmass": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#e0e0e0",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#markers": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"rescale": 1,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#prec": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"fill": "#003dff",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#population": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke-width": 1.6,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#rural": {
|
||||||
|
"stroke": "#0000aa"
|
||||||
|
},
|
||||||
|
"#urban": {
|
||||||
|
"stroke": "#9d0000"
|
||||||
|
},
|
||||||
|
"#freshwater": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#a6c1fd",
|
||||||
|
"stroke": "#5f799d",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#salt": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#409b8a",
|
||||||
|
"stroke": "#388985",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sinkhole": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#5bc9fd",
|
||||||
|
"stroke": "#53a3b0",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#frozen": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#cdd4e7",
|
||||||
|
"stroke": "#cfe0eb",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#lava": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#90270d",
|
||||||
|
"stroke": "#f93e0c",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"filter": "url(#crumpled)"
|
||||||
|
},
|
||||||
|
"#dry": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#c9bfa7",
|
||||||
|
"stroke": "#8e816f",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sea_island": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#1f3846",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": "url(#dropShadow)",
|
||||||
|
"auto-filter": 1
|
||||||
|
},
|
||||||
|
"#lake_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#7c8eaf",
|
||||||
|
"stroke-width": 0.35,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#terrain": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"set": "simple",
|
||||||
|
"size": 1,
|
||||||
|
"density": 0.4,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#rivers": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"fill": "#779582"
|
||||||
|
},
|
||||||
|
"#ruler": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#roads": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#8b4418",
|
||||||
|
"stroke-width": 0.9,
|
||||||
|
"stroke-dasharray": "2 3",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#trails": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#844017",
|
||||||
|
"stroke-width": 0.2,
|
||||||
|
"stroke-dasharray": ".5 1",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#searoutes": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#5e1865",
|
||||||
|
"stroke-width": 0.6,
|
||||||
|
"stroke-dasharray": "1.2 2.4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#statesBody": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#statesHalo": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"data-width": 12,
|
||||||
|
"stroke-width": 12,
|
||||||
|
"filter": "blur(10px)"
|
||||||
|
},
|
||||||
|
"#provs": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#000000",
|
||||||
|
"data-size": 10,
|
||||||
|
"font-size": 10,
|
||||||
|
"font-family": "Georgia",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#temperature": {
|
||||||
|
"opacity": 1,
|
||||||
|
"font-size": "11px",
|
||||||
|
"fill": "#62001b",
|
||||||
|
"fill-opacity": 0.3,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 2,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#ice": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"fill": "#e8f0f6",
|
||||||
|
"stroke": "#e8f0f6",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#emblems": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#texture": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#textureImage": {
|
||||||
|
"x": 0,
|
||||||
|
"y": 0
|
||||||
|
},
|
||||||
|
"#zones": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke": "#333333",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": "url(#dropShadow01)",
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#oceanLayers": {
|
||||||
|
"filter": null,
|
||||||
|
"layers": "-6,-4,-2"
|
||||||
|
},
|
||||||
|
"#oceanBase": {
|
||||||
|
"fill": "#4e6964"
|
||||||
|
},
|
||||||
|
"#oceanicPattern": {
|
||||||
|
"href": "./images/pattern3.png",
|
||||||
|
"opacity": 0.2
|
||||||
|
},
|
||||||
|
"#terrs": {
|
||||||
|
"opacity": 1,
|
||||||
|
"scheme": "bright",
|
||||||
|
"terracing": 0,
|
||||||
|
"skip": 0,
|
||||||
|
"relax": 1,
|
||||||
|
"curve": 1,
|
||||||
|
"filter": "url(#filter-grayscale)",
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#legend": {
|
||||||
|
"data-size": 13,
|
||||||
|
"font-size": 13,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"stroke": "#812929",
|
||||||
|
"stroke-width": 2.5,
|
||||||
|
"stroke-dasharray": "0 4 10 4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"data-x": 99,
|
||||||
|
"data-y": 93,
|
||||||
|
"data-columns": 8
|
||||||
|
},
|
||||||
|
"#legendBox": {},
|
||||||
|
"#burgLabels > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"text-shadow": "white 0 0 4px",
|
||||||
|
"data-size": 7,
|
||||||
|
"font-size": 7,
|
||||||
|
"font-family": "Bitter"
|
||||||
|
},
|
||||||
|
"#burgIcons > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 2,
|
||||||
|
"stroke": "#444444",
|
||||||
|
"stroke-width": 0.25,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #cities": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 4,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1
|
||||||
|
},
|
||||||
|
"#burgLabels > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"data-size": 3,
|
||||||
|
"font-size": 3,
|
||||||
|
"font-family": "Bitter"
|
||||||
|
},
|
||||||
|
"#burgIcons > #towns": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 0.8,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.2,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 1.6,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#labels > #states": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#4e4e4e",
|
||||||
|
"stroke": "#b5b5b5",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0 0 4px",
|
||||||
|
"data-size": 22,
|
||||||
|
"font-size": 22,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#labels > #addedLabels": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"stroke": "#3a3a3a",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0 0 4px",
|
||||||
|
"data-size": 18,
|
||||||
|
"font-size": 18,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#fogging": {
|
||||||
|
"opacity": 0.98,
|
||||||
|
"fill": "#1b1423",
|
||||||
|
"filter": null
|
||||||
|
}
|
||||||
|
}
|
||||||
385
styles/light.json
Normal file
|
|
@ -0,0 +1,385 @@
|
||||||
|
{
|
||||||
|
"#map": {
|
||||||
|
"background-color": "#000000",
|
||||||
|
"filter": null,
|
||||||
|
"data-filter": null
|
||||||
|
},
|
||||||
|
"#armies": {
|
||||||
|
"font-size": 8,
|
||||||
|
"box-size": 4,
|
||||||
|
"stroke": "#000",
|
||||||
|
"stroke-width": 0.02,
|
||||||
|
"fill-opacity": 0.8,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#biomes": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#stateBorders": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#4c483e",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": "square",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#provinceBorders": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 0.2,
|
||||||
|
"stroke-dasharray": 1,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cells": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#gridOverlay": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"scale": 1,
|
||||||
|
"dx": 0,
|
||||||
|
"dy": 0,
|
||||||
|
"type": "pointyHex",
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#coordinates": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"data-size": 15,
|
||||||
|
"font-size": 15,
|
||||||
|
"stroke": "#734d37",
|
||||||
|
"stroke-width": 1.5,
|
||||||
|
"stroke-dasharray": 5,
|
||||||
|
"stroke-linecap": "square",
|
||||||
|
"filter": null,
|
||||||
|
"mask": ""
|
||||||
|
},
|
||||||
|
"#compass": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#water)",
|
||||||
|
"shape-rendering": "optimizespeed"
|
||||||
|
},
|
||||||
|
"#rose": {
|
||||||
|
"transform": null
|
||||||
|
},
|
||||||
|
"#relig": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cults": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#landmass": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#f9f2ea",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#markers": {
|
||||||
|
"opacity": null,
|
||||||
|
"rescale": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#prec": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"fill": "#2554ef",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#population": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke-width": 1.6,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#rural": {
|
||||||
|
"stroke": "#0000ff"
|
||||||
|
},
|
||||||
|
"#urban": {
|
||||||
|
"stroke": "#ff0000"
|
||||||
|
},
|
||||||
|
"#freshwater": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#98cdc4",
|
||||||
|
"stroke": "#719892",
|
||||||
|
"stroke-width": 0.46,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#salt": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#409b8a",
|
||||||
|
"stroke": "#388985",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sinkhole": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#5bc9fd",
|
||||||
|
"stroke": "#53a3b0",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#frozen": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#cdd4e7",
|
||||||
|
"stroke": "#cfe0eb",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#lava": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#90270d",
|
||||||
|
"stroke": "#f93e0c",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"filter": "url(#crumpled)"
|
||||||
|
},
|
||||||
|
"#dry": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#c9bfa7",
|
||||||
|
"stroke": "#8e816f",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sea_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#5e5e5e",
|
||||||
|
"stroke-width": 0.4,
|
||||||
|
"filter": "url(#dropShadow)",
|
||||||
|
"auto-filter": 1
|
||||||
|
},
|
||||||
|
"#lake_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#7c8eaf",
|
||||||
|
"stroke-width": 0.35,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#terrain": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"set": "colored",
|
||||||
|
"size": 1,
|
||||||
|
"density": 0.3,
|
||||||
|
"filter": null,
|
||||||
|
"mask": ""
|
||||||
|
},
|
||||||
|
"#rivers": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"fill": "#6d94ba"
|
||||||
|
},
|
||||||
|
"#ruler": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#roads": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#3c1d0b",
|
||||||
|
"stroke-width": 1.37,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": "inherit",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#trails": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#95481a",
|
||||||
|
"stroke-width": 0.88,
|
||||||
|
"stroke-dasharray": ".8 1.6",
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#searoutes": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#ffffff",
|
||||||
|
"stroke-width": 0.45,
|
||||||
|
"stroke-dasharray": "1 2",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#statesBody": {
|
||||||
|
"opacity": 0.2,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#statesHalo": {
|
||||||
|
"opacity": 0.3,
|
||||||
|
"data-width": 25,
|
||||||
|
"stroke-width": 25,
|
||||||
|
"filter": "blur(5px)"
|
||||||
|
},
|
||||||
|
"#provs": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"fill": "#000000",
|
||||||
|
"font-size": 5,
|
||||||
|
"font-family": "IM Fell English",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#temperature": {
|
||||||
|
"opacity": null,
|
||||||
|
"font-size": "8px",
|
||||||
|
"fill": "#000000",
|
||||||
|
"fill-opacity": 0.3,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 1.8,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#ice": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#e8f0f6",
|
||||||
|
"stroke": "#e8f0f6",
|
||||||
|
"stroke-width": 1.5,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#emblems": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#texture": {
|
||||||
|
"opacity": 0.39,
|
||||||
|
"filter": null,
|
||||||
|
"mask": ""
|
||||||
|
},
|
||||||
|
"#zones": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#333333",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#oceanLayers": {
|
||||||
|
"filter": "url(#dropShadow05)",
|
||||||
|
"layers": "-6,-3,-1"
|
||||||
|
},
|
||||||
|
"#oceanBase": {
|
||||||
|
"fill": "#8dc1c8"
|
||||||
|
},
|
||||||
|
"#oceanicPattern": {
|
||||||
|
"href": "./images/pattern1.png",
|
||||||
|
"opacity": 0.2
|
||||||
|
},
|
||||||
|
"#terrs": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"scheme": "light",
|
||||||
|
"terracing": 10,
|
||||||
|
"skip": 5,
|
||||||
|
"relax": 0,
|
||||||
|
"curve": 0,
|
||||||
|
"filter": "url(#turbulence)",
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#legend": {
|
||||||
|
"data-size": 13,
|
||||||
|
"font-size": 13,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"stroke": "#812929",
|
||||||
|
"stroke-width": 2.5,
|
||||||
|
"stroke-dasharray": "0 4 10 4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"data-x": 54.73,
|
||||||
|
"data-y": 62.98,
|
||||||
|
"data-columns": 8
|
||||||
|
},
|
||||||
|
"#burgLabels > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3a3a3a",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 8,
|
||||||
|
"font-size": 8,
|
||||||
|
"font-family": "IM Fell English"
|
||||||
|
},
|
||||||
|
"#burgIcons > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 3,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.4,
|
||||||
|
"stroke-dasharray": "0.5 0.25",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 5.5,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#burgLabels > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 4,
|
||||||
|
"font-size": 4,
|
||||||
|
"font-family": "IM Fell English"
|
||||||
|
},
|
||||||
|
"#burgIcons > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 1.2,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.2,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 2.2,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#labels > #states": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e3e",
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.3,
|
||||||
|
"text-shadow": "white 0px 0px 6px",
|
||||||
|
"data-size": 14,
|
||||||
|
"font-size": 14,
|
||||||
|
"font-family": "IM Fell English",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#labels > #addedLabels": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#f24706",
|
||||||
|
"stroke": "#701b05",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 6,
|
||||||
|
"font-size": 6,
|
||||||
|
"font-family": "IM Fell English",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#fogging": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#30426f",
|
||||||
|
"filter": null
|
||||||
|
}
|
||||||
|
}
|
||||||
381
styles/monochrome.json
Normal file
|
|
@ -0,0 +1,381 @@
|
||||||
|
{
|
||||||
|
"#map": {
|
||||||
|
"background-color": "#000000",
|
||||||
|
"filter": "url(#filter-grayscale)",
|
||||||
|
"data-filter": "grayscale"
|
||||||
|
},
|
||||||
|
"#armies": {
|
||||||
|
"font-size": 6,
|
||||||
|
"box-size": 3,
|
||||||
|
"stroke": "#000",
|
||||||
|
"stroke-width": 0.3,
|
||||||
|
"opacity": 1,
|
||||||
|
"fill-opacity": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#biomes": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": "url(#blur5)",
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#stateBorders": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#provinceBorders": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 0.4,
|
||||||
|
"stroke-dasharray": 1,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cells": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#gridOverlay": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"scale": 1,
|
||||||
|
"dx": 0,
|
||||||
|
"dy": "0",
|
||||||
|
"type": "pointyHex",
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#coordinates": {
|
||||||
|
"opacity": 1,
|
||||||
|
"data-size": 12,
|
||||||
|
"font-size": 12,
|
||||||
|
"stroke": "#d4d4d4",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 5,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#compass": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#water)",
|
||||||
|
"shape-rendering": "optimizespeed"
|
||||||
|
},
|
||||||
|
"#rose": {
|
||||||
|
"transform": null
|
||||||
|
},
|
||||||
|
"#relig": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#404040",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cults": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#landmass": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#markers": {
|
||||||
|
"opacity": null,
|
||||||
|
"rescale": 1,
|
||||||
|
"filter": "url(#dropShadow01)"
|
||||||
|
},
|
||||||
|
"#prec": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"fill": "#003dff",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#population": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke-width": 1.6,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#rural": {
|
||||||
|
"stroke": "#0000ff"
|
||||||
|
},
|
||||||
|
"#urban": {
|
||||||
|
"stroke": "#ff0000"
|
||||||
|
},
|
||||||
|
"#freshwater": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"stroke": "#515151",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#salt": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"stroke": "#484848",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sinkhole": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"stroke": "#5f5f5f",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#frozen": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"stroke": "#6f6f6f",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#lava": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#000000",
|
||||||
|
"stroke": "#5d5d5d",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sea_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#1f3846",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null,
|
||||||
|
"auto-filter": 0
|
||||||
|
},
|
||||||
|
"#lake_island": {
|
||||||
|
"opacity": 0,
|
||||||
|
"stroke": "#7c8eaf",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#terrain": {
|
||||||
|
"opacity": null,
|
||||||
|
"set": "simple",
|
||||||
|
"size": 1,
|
||||||
|
"density": 0.4,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#rivers": {
|
||||||
|
"opacity": 0.2,
|
||||||
|
"filter": "url(#blur1)",
|
||||||
|
"fill": "#000000"
|
||||||
|
},
|
||||||
|
"#ruler": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#roads": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#d06324",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"stroke-dasharray": 2,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#trails": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#d06324",
|
||||||
|
"stroke-width": 0.25,
|
||||||
|
"stroke-dasharray": ".8 1.6",
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#searoutes": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"stroke": "#ffffff",
|
||||||
|
"stroke-width": 0.45,
|
||||||
|
"stroke-dasharray": "1 2",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#statesBody": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#statesHalo": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"data-width": 10,
|
||||||
|
"stroke-width": 10,
|
||||||
|
"filter": "blur(5px)"
|
||||||
|
},
|
||||||
|
"#provs": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#000000",
|
||||||
|
"data-size": 10,
|
||||||
|
"font-size": 10,
|
||||||
|
"font-family": "Georgia",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#temperature": {
|
||||||
|
"opacity": null,
|
||||||
|
"font-size": "8px",
|
||||||
|
"fill": "#000000",
|
||||||
|
"fill-opacity": 0.3,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 1.8,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#ice": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"fill": "#e8f0f6",
|
||||||
|
"stroke": "#e8f0f6",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#texture": {
|
||||||
|
"opacity": 1,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#emblems": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#textureImage": {},
|
||||||
|
"#zones": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#333333",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#oceanLayers": {
|
||||||
|
"filter": null,
|
||||||
|
"layers": "none"
|
||||||
|
},
|
||||||
|
"#oceanBase": {
|
||||||
|
"fill": "#000000"
|
||||||
|
},
|
||||||
|
"#oceanicPattern": {
|
||||||
|
"href": "",
|
||||||
|
"opacity": 0.2
|
||||||
|
},
|
||||||
|
"#terrs": {
|
||||||
|
"opacity": 1,
|
||||||
|
"scheme": "monochrome",
|
||||||
|
"terracing": 0,
|
||||||
|
"skip": 5,
|
||||||
|
"relax": 0,
|
||||||
|
"curve": 0,
|
||||||
|
"filter": "url(#blur3)",
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#legend": {
|
||||||
|
"data-size": 13,
|
||||||
|
"font-size": 13,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"stroke": "#812929",
|
||||||
|
"stroke-width": 2.5,
|
||||||
|
"stroke-dasharray": "0 4 10 4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"data-x": 99,
|
||||||
|
"data-y": 93,
|
||||||
|
"data-columns": 8
|
||||||
|
},
|
||||||
|
"#legendBox": {},
|
||||||
|
"#burgLabels > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"text-shadow": "white 0 0 4px",
|
||||||
|
"data-size": 7,
|
||||||
|
"font-size": 7,
|
||||||
|
"font-family": "Almendra SC"
|
||||||
|
},
|
||||||
|
"#burgIcons > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.24,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 2,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#burgLabels > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"data-size": 4,
|
||||||
|
"font-size": 4,
|
||||||
|
"font-family": "Almendra SC"
|
||||||
|
},
|
||||||
|
"#burgIcons > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 0.5,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.12,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#labels > #states": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"stroke": "#3a3a3a",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0 0 4px",
|
||||||
|
"data-size": 22,
|
||||||
|
"font-size": 22,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#labels > #addedLabels": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"stroke": "#3a3a3a",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0 0 4px",
|
||||||
|
"data-size": 18,
|
||||||
|
"font-size": 18,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#fogging": {
|
||||||
|
"opacity": 0.98,
|
||||||
|
"fill": "#30426f",
|
||||||
|
"filter": null
|
||||||
|
}
|
||||||
|
}
|
||||||
385
styles/watercolor.json
Normal file
|
|
@ -0,0 +1,385 @@
|
||||||
|
{
|
||||||
|
"#map": {
|
||||||
|
"background-color": "#000000",
|
||||||
|
"filter": null,
|
||||||
|
"data-filter": null
|
||||||
|
},
|
||||||
|
"#armies": {
|
||||||
|
"font-size": 8,
|
||||||
|
"box-size": 4,
|
||||||
|
"stroke": "#000",
|
||||||
|
"stroke-width": 0.2,
|
||||||
|
"fill-opacity": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#biomes": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#stateBorders": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 3,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#provinceBorders": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke": "#56566d",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": "0 2",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#cells": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#808080",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#gridOverlay": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"scale": 1,
|
||||||
|
"dx": 0,
|
||||||
|
"dy": 0,
|
||||||
|
"type": "pointyHex",
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#coordinates": {
|
||||||
|
"opacity": 1,
|
||||||
|
"data-size": 12,
|
||||||
|
"font-size": 12,
|
||||||
|
"stroke": "#d4d4d4",
|
||||||
|
"stroke-width": 1,
|
||||||
|
"stroke-dasharray": 5,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#compass": {
|
||||||
|
"opacity": 0.8,
|
||||||
|
"transform": null,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#water)",
|
||||||
|
"shape-rendering": "optimizespeed"
|
||||||
|
},
|
||||||
|
"#rose": {
|
||||||
|
"transform": "translate(80 80) scale(.25)"
|
||||||
|
},
|
||||||
|
"#relig": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": "url(#bluredSplotch)"
|
||||||
|
},
|
||||||
|
"#cults": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#777777",
|
||||||
|
"stroke-width": 0.5,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": "url(#splotch)"
|
||||||
|
},
|
||||||
|
"#landmass": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#eef6fb",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#markers": {
|
||||||
|
"opacity": null,
|
||||||
|
"rescale": 1,
|
||||||
|
"filter": "url(#dropShadow01)"
|
||||||
|
},
|
||||||
|
"#prec": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.1,
|
||||||
|
"fill": "#003dff",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#population": {
|
||||||
|
"opacity": null,
|
||||||
|
"stroke-width": 1.6,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#rural": {
|
||||||
|
"stroke": "#0000ff"
|
||||||
|
},
|
||||||
|
"#urban": {
|
||||||
|
"stroke": "#ff0000"
|
||||||
|
},
|
||||||
|
"#freshwater": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#a6c1fd",
|
||||||
|
"stroke": "#5f799d",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#salt": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"fill": "#409b8a",
|
||||||
|
"stroke": "#388985",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sinkhole": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#5bc9fd",
|
||||||
|
"stroke": "#53a3b0",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#frozen": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"fill": "#cdd4e7",
|
||||||
|
"stroke": "#cfe0eb",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#lava": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#90270d",
|
||||||
|
"stroke": "#f93e0c",
|
||||||
|
"stroke-width": 2,
|
||||||
|
"filter": "url(#crumpled)"
|
||||||
|
},
|
||||||
|
"#dry": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#c9bfa7",
|
||||||
|
"stroke": "#8e816f",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#sea_island": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"stroke": "#1f3846",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"filter": "url(#dropShadow)",
|
||||||
|
"auto-filter": 1
|
||||||
|
},
|
||||||
|
"#lake_island": {
|
||||||
|
"opacity": 1,
|
||||||
|
"stroke": "#7c8eaf",
|
||||||
|
"stroke-width": 0.35,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#terrain": {
|
||||||
|
"opacity": 1,
|
||||||
|
"set": "gray",
|
||||||
|
"size": 1,
|
||||||
|
"density": 0.4,
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#rivers": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null,
|
||||||
|
"fill": "#2e89c2"
|
||||||
|
},
|
||||||
|
"#ruler": {
|
||||||
|
"opacity": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#roads": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#969696",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#trails": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#969696",
|
||||||
|
"stroke-width": 0.4,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#searoutes": {
|
||||||
|
"opacity": 0.9,
|
||||||
|
"stroke": "#969696",
|
||||||
|
"stroke-width": 0.7,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#statesBody": {
|
||||||
|
"opacity": 0.05,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#statesHalo": {
|
||||||
|
"opacity": 0.4,
|
||||||
|
"data-width": 8,
|
||||||
|
"stroke-width": 8,
|
||||||
|
"filter": "blur(2px)"
|
||||||
|
},
|
||||||
|
"#provs": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#000000",
|
||||||
|
"font-size": 4,
|
||||||
|
"font-family": "Comfortaa",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#temperature": {
|
||||||
|
"opacity": null,
|
||||||
|
"font-size": "8px",
|
||||||
|
"fill": "#000000",
|
||||||
|
"fill-opacity": 0.3,
|
||||||
|
"stroke": null,
|
||||||
|
"stroke-width": 1.8,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": null,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#ice": {
|
||||||
|
"opacity": 0.7,
|
||||||
|
"fill": "#dfe8ec",
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"filter": "url(#dropShadow05)"
|
||||||
|
},
|
||||||
|
"#emblems": {
|
||||||
|
"opacity": 0.95,
|
||||||
|
"stroke-width": 1,
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#texture": {
|
||||||
|
"opacity": 0.2,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#zones": {
|
||||||
|
"opacity": 0.6,
|
||||||
|
"stroke": "#333333",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"stroke-dasharray": null,
|
||||||
|
"stroke-linecap": "butt",
|
||||||
|
"filter": null,
|
||||||
|
"mask": null
|
||||||
|
},
|
||||||
|
"#oceanLayers": {
|
||||||
|
"filter": null,
|
||||||
|
"layers": "-6,-4,-2"
|
||||||
|
},
|
||||||
|
"#oceanBase": {
|
||||||
|
"fill": "#2d788b"
|
||||||
|
},
|
||||||
|
"#oceanicPattern": {
|
||||||
|
"href": "./images/kiwiroo.png",
|
||||||
|
"opacity": 0.5
|
||||||
|
},
|
||||||
|
"#terrs": {
|
||||||
|
"opacity": 0.5,
|
||||||
|
"scheme": "light",
|
||||||
|
"terracing": 0,
|
||||||
|
"skip": 5,
|
||||||
|
"relax": 1,
|
||||||
|
"curve": 0,
|
||||||
|
"filter": null,
|
||||||
|
"mask": "url(#land)"
|
||||||
|
},
|
||||||
|
"#legend": {
|
||||||
|
"data-size": 13,
|
||||||
|
"font-size": 13,
|
||||||
|
"font-family": "Almendra SC",
|
||||||
|
"stroke": "#812929",
|
||||||
|
"stroke-width": 2.5,
|
||||||
|
"stroke-dasharray": "0 4 10 4",
|
||||||
|
"stroke-linecap": "round",
|
||||||
|
"data-x": 99,
|
||||||
|
"data-y": 93,
|
||||||
|
"data-columns": 8
|
||||||
|
},
|
||||||
|
"#burgLabels > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#043449",
|
||||||
|
"text-shadow": "white 0px 0px 2px",
|
||||||
|
"data-size": 5,
|
||||||
|
"font-size": 5,
|
||||||
|
"font-family": "Comfortaa"
|
||||||
|
},
|
||||||
|
"#burgIcons > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.24,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #cities": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 2,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#burgLabels > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 3,
|
||||||
|
"font-size": 3,
|
||||||
|
"font-family": "Comfortaa"
|
||||||
|
},
|
||||||
|
"#burgIcons > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"fill-opacity": 0.7,
|
||||||
|
"size": 0.5,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 0.12,
|
||||||
|
"stroke-dasharray": "",
|
||||||
|
"stroke-linecap": "butt"
|
||||||
|
},
|
||||||
|
"#anchors > #towns": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"size": 1,
|
||||||
|
"stroke": "#3e3e4b",
|
||||||
|
"stroke-width": 1.2
|
||||||
|
},
|
||||||
|
"#labels > #states": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#ffffff",
|
||||||
|
"stroke": "#000000",
|
||||||
|
"stroke-width": 0.15,
|
||||||
|
"text-shadow": "black 1px 1px 2px",
|
||||||
|
"data-size": 20,
|
||||||
|
"font-size": 20,
|
||||||
|
"font-family": "Gloria Hallelujah",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#labels > #addedLabels": {
|
||||||
|
"opacity": 1,
|
||||||
|
"fill": "#3e3e4b",
|
||||||
|
"stroke": "#3a3a3a",
|
||||||
|
"stroke-width": 0,
|
||||||
|
"text-shadow": "white 0px 0px 4px",
|
||||||
|
"data-size": 18,
|
||||||
|
"font-size": 18,
|
||||||
|
"font-family": "Comfortaa",
|
||||||
|
"filter": null
|
||||||
|
},
|
||||||
|
"#fogging": {
|
||||||
|
"opacity": 0.97,
|
||||||
|
"fill": "#8398ce",
|
||||||
|
"filter": null
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -5,7 +5,7 @@
|
||||||
function convertTemperature(temp) {
|
function convertTemperature(temp) {
|
||||||
switch (temperatureScale.value) {
|
switch (temperatureScale.value) {
|
||||||
case "°C":
|
case "°C":
|
||||||
return temp + "°C";
|
return rn(temp) + "°C";
|
||||||
case "°F":
|
case "°F":
|
||||||
return rn((temp * 9) / 5 + 32) + "°F";
|
return rn((temp * 9) / 5 + 32) + "°F";
|
||||||
case "K":
|
case "K":
|
||||||
|
|
@ -21,7 +21,7 @@ function convertTemperature(temp) {
|
||||||
case "°Rø":
|
case "°Rø":
|
||||||
return rn((temp * 21) / 40 + 7.5) + "°Rø";
|
return rn((temp * 21) / 40 + 7.5) + "°Rø";
|
||||||
default:
|
default:
|
||||||
return temp + "°C";
|
return rn(temp) + "°C";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||