diff --git a/package.json b/package.json index 7f61bee..e7feb29 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "fantasy-maphub", "name_full": "Fantasy MapHub Generators", - "version": "1.2.2", + "version": "1.2.3-add-data-other-types-of-.1", "description": "An offline-first hub that bundles several Watabou map generators into one consistent web app: same UI patterns, local assets, and modern import/export. It adds OpenAPI docs, proto-first serialization (including pure protobuf files), and a PWA build so everything works without an internet connection.", "license": "MPL-2.0", "author": "mail@sunsung.fun", @@ -27,7 +27,8 @@ "build:rewrite:tags": "node scripts/replace-tags-dist.mjs", "build:rewrite:minify": "node scripts/minify-static-js.mjs", "build:rewrite:hash-url": "node scripts/add-query-hash.mjs", - "build:list": "run-s build:gen:index-pages build:gen:icons build:gen:languages build:gen:openapi build:rewrite:tags build:rewrite:minify build:rewrite:hash-url", + "build:gen:sitemap": "node scripts/generate-sitemap.mjs", + "build:list": "run-s build:gen:index-pages build:gen:icons build:gen:languages build:gen:openapi build:rewrite:tags build:rewrite:minify build:rewrite:hash-url build:gen:sitemap", "build": "vite build && npm run build:list", "preview": "vite preview", "test": "vitest run", diff --git a/protobuf/data/dwellings/decor.proto b/protobuf/data/dwellings/decor.proto new file mode 100644 index 0000000..f010b0c --- /dev/null +++ b/protobuf/data/dwellings/decor.proto @@ -0,0 +1,31 @@ +syntax = "proto3"; + +package data; + +import "data/dwellings/enum.proto"; +import "data/dwellings/types.proto"; + +// // // // + +message DwellingsLightObj { + DwellingsPointObj pos = 1; + float radius = 2; + float power = 3; + bool on = 4; +} + +message DwellingsPropObj { + DwellingsPropType kind = 1; + DwellingsPointObj pos = 2; + DwellingsEdgeObj wall = 3; + DwellingsEdgeObj from_edge = 4; + DwellingsEdgeObj to_edge = 5; +} + +message DwellingsPolygonObj { + repeated DwellingsPointObj points = 1; +} + +message DwellingsDecorGroupObj { + repeated DwellingsPolygonObj polygons = 1; +} diff --git a/protobuf/data/dwellings/enum.proto b/protobuf/data/dwellings/enum.proto index ca81403..a4fd59d 100644 --- a/protobuf/data/dwellings/enum.proto +++ b/protobuf/data/dwellings/enum.proto @@ -17,4 +17,23 @@ enum DwellingsDoorType { NULL = 1; DOORWAY = 2; REGULAR = 3; -} \ No newline at end of file +} + + +enum DwellingsPropType { + PROP_UNSPECIFIED = 0; + ALTAR = 1; + STATUE = 2; + CURTAIN = 3; + BED = 4; +} + +enum DwellingsArchitectureType { + ARCHITECTURE_UNSPECIFIED = 0; + + simple = 1; + castle = 2; + logs = 3; + modern = 4; + scifi = 5; +} diff --git a/protobuf/data/dwellings/lvl.proto b/protobuf/data/dwellings/level.proto similarity index 54% rename from protobuf/data/dwellings/lvl.proto rename to protobuf/data/dwellings/level.proto index 71d2762..93c6397 100644 --- a/protobuf/data/dwellings/lvl.proto +++ b/protobuf/data/dwellings/level.proto @@ -3,22 +3,20 @@ syntax = "proto3"; package data; import "data/dwellings/enum.proto"; +import "data/dwellings/types.proto"; +import "data/dwellings/decor.proto"; // // // // -message DwellingsCellObj { - int32 i = 1; - int32 j = 2; -} - message DwellingsRoomObj { optional string name = 1; repeated DwellingsCellObj cells = 2; -} + reserved 3 to 9; -message DwellingsEdgeObj { - DwellingsCellObj cell = 1; - DwellingsDirectionType dir = 2; + optional string embed_type_id = 10; + optional DwellingsLightObj embed_light = 11; + repeated DwellingsPropObj embed_props = 12; + repeated DwellingsDecorGroupObj embed_decor = 13; } message DwellingsDoorObj { @@ -30,4 +28,7 @@ message DwellingsStairObj { DwellingsCellObj cell = 1; DwellingsDirectionType dir = 2; bool up = 3; -} \ No newline at end of file + reserved 4 to 9; + + optional bool embed_trapdoor = 10; +} diff --git a/protobuf/data/dwellings/obj.proto b/protobuf/data/dwellings/obj.proto index 79eb6d5..bbd9365 100644 --- a/protobuf/data/dwellings/obj.proto +++ b/protobuf/data/dwellings/obj.proto @@ -2,7 +2,9 @@ syntax = "proto3"; package data; -import "data/dwellings/lvl.proto"; +import "data/dwellings/enum.proto"; +import "data/dwellings/types.proto"; +import "data/dwellings/level.proto"; // // // // @@ -12,6 +14,9 @@ message DwellingsPlanObj { repeated DwellingsDoorObj doors = 3; repeated DwellingsEdgeObj windows = 4; repeated DwellingsStairObj stairs = 5; + reserved 6 to 19; + + repeated DwellingsCellObj embed_chimneys = 20; } // @@ -20,4 +25,8 @@ message DwellingsObj { repeated DwellingsPlanObj floors = 1; DwellingsEdgeObj exit = 2; DwellingsEdgeObj spiral = 3; + reserved 4 to 19; + + optional string embed_name = 20; + optional DwellingsArchitectureType embed_architecture = 21; } diff --git a/protobuf/data/dwellings/types.proto b/protobuf/data/dwellings/types.proto new file mode 100644 index 0000000..566bf1a --- /dev/null +++ b/protobuf/data/dwellings/types.proto @@ -0,0 +1,22 @@ +syntax = "proto3"; + +package data; + +import "data/dwellings/enum.proto"; + +// // // // + +message DwellingsCellObj { + int32 i = 1; + int32 j = 2; +} + +message DwellingsPointObj { + float x = 1; + float y = 2; +} + +message DwellingsEdgeObj { + DwellingsCellObj cell = 1; + DwellingsDirectionType dir = 2; +} diff --git a/protobuf/data/geo/common.proto b/protobuf/data/geo/common.proto new file mode 100644 index 0000000..b4acd89 --- /dev/null +++ b/protobuf/data/geo/common.proto @@ -0,0 +1,30 @@ +syntax = "proto3"; + +package data; + +import "google/protobuf/struct.proto"; + +// // // // + +message GeoTransformObj { + double scale = 1; + double cx = 2; + double cy = 3; + bool invert_y = 4; + uint32 precision_pow10 = 5; +} + +message GeoBBoxObj { + double min_x = 1; + double min_y = 2; + double max_x = 3; + double max_y = 4; +} + +message GeoPartObj { + uint32 index = 1; + string uid = 2; + google.protobuf.Struct props = 3; + string name = 4; + GeoBBoxObj bbox = 5; +} diff --git a/protobuf/data/geo/editor.proto b/protobuf/data/geo/editor.proto new file mode 100644 index 0000000..5b31229 --- /dev/null +++ b/protobuf/data/geo/editor.proto @@ -0,0 +1,105 @@ +syntax = "proto3"; + +package data; + +import "google/protobuf/struct.proto"; +import "data/geo/enum.proto"; + +// // // // + +message EditorPoint2DObj { + double x = 1; + double y = 2; +} + +message EditorPolylineObj { + repeated EditorPoint2DObj points = 1; + bool closed = 2; +} + +message EditorBezierObj { + repeated EditorPoint2DObj control_points = 1; + + bool closed = 2; + uint32 segments = 3; +} + +message EditorArcObj { + EditorPoint2DObj center = 1; + double radius = 2; + double start_angle_rad = 3; + double end_angle_rad = 4; + bool ccw = 5; +} + +message EditorLinkObj { + string a_uid = 1; + string b_uid = 2; + EditorLinkType type = 3; + google.protobuf.Struct props = 4; +} + +message EditorLayerStateObj { + string layer_id = 1; + bool visible = 2; + bool locked = 3; + int32 z_index = 4; +} + +message EditorGroupObj { + string group_uid = 1; + string name = 2; + repeated string member_uids = 3; + google.protobuf.Struct props = 4; +} + +message EditorRoadModelObj { + string target_uid = 1; + EditorPolylineObj centerline = 2; + double width = 3; + bool closed = 4; + google.protobuf.Struct props = 5; +} + +message EditorShapeModelObj { + string target_uid = 1; + + oneof model { + EditorPolylineObj polyline = 2; + EditorBezierObj bezier = 3; + EditorArcObj arc = 4; + } + + google.protobuf.Struct props = 10; +} + +message EditorSnapNodeObj { + string node_uid = 1; + EditorPoint2DObj pos = 2; + repeated string incident_uids = 3; + google.protobuf.Struct props = 4; +} + +message EditorConstraintObj { + string constraint_uid = 1; + EditorConstraintType type = 2; + repeated string target_uids = 3; + google.protobuf.Struct params = 4; +} + +message EditorPayloadObj { + uint32 payload_rev = 1; + EditorCoordSpaceType coord_space = 2; + + repeated EditorLayerStateObj layers = 10; + repeated EditorGroupObj groups = 11; + repeated EditorLinkObj links = 12; + + repeated EditorRoadModelObj road_models = 20; + repeated EditorShapeModelObj shape_models = 21; + + repeated EditorSnapNodeObj snap_nodes = 30; + repeated EditorConstraintObj constraints = 31; + + google.protobuf.Struct props = 40; +} diff --git a/protobuf/data/geo/enum.proto b/protobuf/data/geo/enum.proto index 843e3cc..81aac73 100644 --- a/protobuf/data/geo/enum.proto +++ b/protobuf/data/geo/enum.proto @@ -2,8 +2,6 @@ syntax = "proto3"; package data; -import "google/protobuf/struct.proto"; - // // // // enum GeoFeatureType { @@ -58,4 +56,27 @@ enum GeoType { Polygon = 23; MultiPolygon = 24; reserved 25 to 50; -} \ No newline at end of file +} + +enum EditorCoordSpaceType { + EDITOR_COORD_SPACE_UNSPECIFIED = 0; + world = 1; + export = 2; +} + +enum EditorLinkType { + EDITOR_LINK_TYPE_UNSPECIFIED = 0; + EDITOR_LINK_TYPE_PARENT_CHILD = 1; + EDITOR_LINK_TYPE_GROUP_MEMBER = 2; + EDITOR_LINK_TYPE_ATTACH = 3; + EDITOR_LINK_TYPE_OVER_UNDER = 4; + EDITOR_LINK_TYPE_ALONG = 5; +} + +enum EditorConstraintType { + EDITOR_CONSTRAINT_TYPE_UNSPECIFIED = 0; + EDITOR_CONSTRAINT_TYPE_SNAP = 1; + EDITOR_CONSTRAINT_TYPE_FIXED_LENGTH = 2; + EDITOR_CONSTRAINT_TYPE_PARALLEL = 3; + EDITOR_CONSTRAINT_TYPE_PERPENDICULAR = 4; +} diff --git a/protobuf/data/geo/obj.proto b/protobuf/data/geo/obj.proto index d6c6b4c..e3de48d 100644 --- a/protobuf/data/geo/obj.proto +++ b/protobuf/data/geo/obj.proto @@ -4,6 +4,8 @@ package data; import "google/protobuf/struct.proto"; import "data/geo/enum.proto"; +import "data/geo/common.proto"; +import "data/geo/editor.proto"; // // // // @@ -11,22 +13,28 @@ message GeoObj { GeoType type = 1; GeoObj geometry = 2; google.protobuf.ListValue coordinates = 3; - reserved 4 to 9; + reserved 4 to 8; + string embed_uid = 9; repeated GeoObj features = 10; repeated GeoObj geometries = 11; - reserved 12 to 19; + reserved 12 to 16; + repeated GeoPartObj embed_parts = 17; + GeoTransformObj embed_export_transform = 18; + GeoBBoxObj embed_bbox = 19; optional GeoGeneratorType generator = 20; optional GeoFeatureType id = 21; optional string version = 22; optional string name = 23; optional double width = 24; - reserved 25 to 39; + reserved 25 to 38; + google.protobuf.Struct embed_props = 39; optional double road_width = 40; optional double river_width = 41; optional double tower_radius = 42; optional double wall_thickness = 43; reserved 44 to 79; + EditorPayloadObj embed_editor_payload = 80; } diff --git a/scripts/generate-sitemap.mjs b/scripts/generate-sitemap.mjs new file mode 100644 index 0000000..a8b0891 --- /dev/null +++ b/scripts/generate-sitemap.mjs @@ -0,0 +1,126 @@ +import fs from "node:fs"; +import path from "node:path"; +import * as process from "node:process"; +import { TAGS } from "../static.config.mjs"; + +const DIST_DIR_NAME = "dist"; +const DIST_DIR_PATH = path.resolve(DIST_DIR_NAME); +const OUTPUT_FILE = path.join(DIST_DIR_PATH, "sitemap.xml"); + +const SITE_ORIGIN = "https://"+TAGS.HOMEPAGE; + +const INDEX_BASENAME = "index.html"; +const HTML_EXTENSION = ".html"; + +const EXCLUDED_BASENAMES = new Set(["404.html"]); + +const XML_HEADER = ''; +const URLSET_OPEN = + ''; +const URLSET_CLOSE = ""; + +const ENCODING_UTF8 = "utf8"; +const URL_SEPARATOR = "/"; + +const ERROR_DIST_MISSING = 'dist directory not found. Run "vite build" first.'; +const LOG_DONE = (count) => `OK: sitemap.xml generated with ${count} URL(s).`; + +if (!fs.existsSync(DIST_DIR_PATH)) { + console.error(ERROR_DIST_MISSING); + process.exit(1); +} + +function collectHtmlFiles(rootDir) { + const result = []; + const stack = [rootDir]; + + while (stack.length) { + const dir = stack.pop(); + const entries = fs.readdirSync(dir, { withFileTypes: true }); + + for (const entry of entries) { + const fullPath = path.join(dir, entry.name); + + if (entry.isDirectory()) { + stack.push(fullPath); + continue; + } + + if (!entry.isFile()) continue; + + const ext = path.extname(entry.name).toLowerCase(); + if (ext !== HTML_EXTENSION) continue; + if (EXCLUDED_BASENAMES.has(entry.name)) continue; + + result.push(fullPath); + } + } + + return result; +} + +function toUrlPath(rootDir, absPath) { + const relPath = path + .relative(rootDir, absPath) + .split(path.sep) + .join(URL_SEPARATOR); + + if (relPath === INDEX_BASENAME) return URL_SEPARATOR; + + if (relPath.endsWith(URL_SEPARATOR + INDEX_BASENAME)) { + return URL_SEPARATOR + relPath.slice(0, -INDEX_BASENAME.length); + } + + return URL_SEPARATOR + relPath; +} + +function lastModISO(absPath) { + const stat = fs.statSync(absPath); + return stat.mtime.toISOString().split("T")[0]; +} + +function escapeXml(value) { + return value + .replace(/&/g, "&") + .replace(//g, ">") + .replace(/"/g, """) + .replace(/'/g, "'"); +} + +function buildUrlEntry(loc, lastmod) { + const lines = []; + lines.push(" "); + lines.push(` ${escapeXml(loc)}`); + lines.push(` ${lastmod}`); + lines.push(" "); + return lines.join("\n"); +} + +function buildSitemap(rootDir) { + const htmlFiles = collectHtmlFiles(rootDir); + + const entries = htmlFiles + .map((absPath) => ({ + loc: SITE_ORIGIN + toUrlPath(rootDir, absPath), + lastmod: lastModISO(absPath), + })) + .sort((a, b) => a.loc.localeCompare(b.loc)); + + const parts = [XML_HEADER, URLSET_OPEN]; + + for (const entry of entries) { + parts.push(buildUrlEntry(entry.loc, entry.lastmod)); + } + + parts.push(URLSET_CLOSE); + parts.push(""); + + return { xml: parts.join("\n"), count: entries.length }; +} + +const { xml, count } = buildSitemap(DIST_DIR_PATH); + +fs.writeFileSync(OUTPUT_FILE, xml, ENCODING_UTF8); + +console.log(LOG_DONE(count)); diff --git a/src/js/Dwellings.js b/src/js/Dwellings.js index 58bde10..2a4e488 100644 --- a/src/js/Dwellings.js +++ b/src/js/Dwellings.js @@ -6563,8 +6563,8 @@ var $lime_init = function (K, v) { return sb.house2proto(a) }; sb.export=function(a){ - var b=sb.exportProto(a),c=sb.proto2json(b),d=id.fixName(a.name); - id.saveJSON(c,d,!0); + var b=sb.exportProto(a),d=id.fixName(a.name); + id.saveJSON(b,d,!0); return b }; sb.exportAsProto=function(a){ @@ -6574,12 +6574,16 @@ var $lime_init = function (K, v) { return b }; sb.house2proto=function(a){ - for(var b=[],c=0,d=a.floors;c g.length && 0 < b.length + c.length;) 0 < b.length && g.unshift(b.shift()), 0 < c.length && g.push(c.shift()); - c = new di(g[0].a, g[g.length - 1].b); + c = new di(g[0], g[g.length - 1]); a.props.add(c); a.defaultLight(!1) }; var di = function (a, b) { X.call(this); - this.a = a; - this.b = b + this.a = a.a; + this.b = b.b; + this.fromEdge = a; + this.toEdge = b }; h["dwellings.model.props.Curtain"] = di; di.__name__ = "dwellings.model.props.Curtain"; diff --git a/src/js/ToyTown2.js b/src/js/ToyTown2.js index e019b01..7c6c405 100644 --- a/src/js/ToyTown2.js +++ b/src/js/ToyTown2.js @@ -17033,6 +17033,11 @@ if (params !== null) (function (S, u) { } d = kf.render(h, !1, 2); Cc.addStartCap(d, e); + + if (!f || f.length < 2) { + console.warn("Bad road poly:", d); + continue; + } this.addSubGeometry(new Cc(d, e)) } }; @@ -17632,8 +17637,12 @@ if (params !== null) (function (S, u) { }; ia.addWall = function (a, b, c, d, e, f) { var h = Q.distance(b, e), - r = Math.min(c.y, d.y) - ia.zero, - m = 1.8, + r = Math.min(c.y, d.y) - ia.zero; + if (!isFinite(h) || h <= 1e-6 || !isFinite(r) || r <= 0) { + ia.addWindowlessWall(a, b, c, d, e, f); + return; + } + var m = 1.8, C = 3, g = 2, k = 1.5; @@ -17641,6 +17650,10 @@ if (params !== null) (function (S, u) { 1)); var n = Math.floor((h - 2 * g + C) / (.8 + C)), l = Math.floor((r - k - q + m) / (1.2 + m)); + if (!isFinite(n) || !isFinite(l) || n < 1 || l < 1) { + ia.addWindowlessWall(a, b, c, d, e, f); + return; + } if (1 > n || 1 > l) ia.addWindowlessWall(a, b, c, d, e, f); else { var p = (r - 1.2 * l) / (k + (l - 1) * m + q); @@ -18070,6 +18083,10 @@ if (params !== null) (function (S, u) { d *= Math.pow(kd.area(b) / kd.rectArea(e), 2); var f = ba.distance(e[0], e[1]), h = ba.distance(e[2], e[1]); + if (!isFinite(q) || q <= 1e-6) { + Pf.add(a, b, c, true); + return; + } if (f < h) { var r = vc.lerp(e[0], e[1]); var m = vc.lerp(e[2], e[3]); @@ -18367,28 +18384,69 @@ if (params !== null) (function (S, u) { DataProto.data.GeoGeneratorType[DataProto.data.GeoGeneratorType.mfcg] == this.generator && (7 > a[1] || 7 == a[1] && 5 > a[2]) && (this.scale = bc.LEGACY_SCALE) }, getThickMultiLineString: function (a, b) { - null == b && (b = 0); - var c = a.type; - if (null == c) return this.thicken(this.getMultiLineString(a), b); - switch (c) { + if (b == null) b = 0; + var defaultWidth = b; + + var t = a.type; + if (t == null) { + var lines = this.getMultiLineString(a) || []; + var out0 = []; + for (var i0 = 0; i0 < lines.length; i0++) { + var line0 = lines[i0]; + if (!line0 || line0.length < 2) { + console.warn("Skip bad line (need >=2 points):", line0); + continue; + } + out0.push(new lf(line0, defaultWidth)); + } + return out0; + } + + switch (t) { case DataProto.data.GeoType[DataProto.data.GeoType.FeatureCollection]: - a = a.features; - c = []; - for (b = 0; b < a.length;) { - var d = a[b]; - ++b; - c.push(new lf(this.getLineString(d.geometry), d.width)) + var features = a.features || []; + var out = []; + for (var i = 0; i < features.length; i++) { + var f = features[i]; + var poly = this.getLineString(f.geometry); + if (!poly || poly.length < 2) { + console.warn("Skip bad road feature (need >=2 points):", f); + continue; + } + var w = (f.width != null) ? f.width : defaultWidth; + out.push(new lf(poly, w)); } - return c; + return out; + case DataProto.data.GeoType[DataProto.data.GeoType.GeometryCollection]: - a = a.geometries; - c = []; - if(typeof a === "array"){ - for (b = 0; b < a.length;) d = a[b], ++b, c.push(new lf(this.getLineString(d), d.width)); + var geoms = a.geometries || []; + var out2 = []; + if (Array.isArray(geoms)) { + for (var j = 0; j < geoms.length; j++) { + var g = geoms[j]; + var poly2 = this.getLineString(g); + if (!poly2 || poly2.length < 2) { + console.warn("Skip bad road geometry (need >=2 points):", g); + continue; + } + var w2 = (g.width != null) ? g.width : defaultWidth; + out2.push(new lf(poly2, w2)); + } } - return c; + return out2; + default: - return this.thicken(this.getMultiLineString(a), b) + var lines2 = this.getMultiLineString(a) || []; + var out3 = []; + for (var k = 0; k < lines2.length; k++) { + var line = lines2[k]; + if (!line || line.length < 2) { + console.warn("Skip bad line (need >=2 points):", line); + continue; + } + out3.push(new lf(line, defaultWidth)); + } + return out3; } }, getThickMultiPolygon: function (a, b) { diff --git a/src/js/Village.js b/src/js/Village.js index 22bc638..113eaab 100644 --- a/src/js/Village.js +++ b/src/js/Village.js @@ -9451,7 +9451,8 @@ var $lime_init = function (E, u) { f.items.push(Ua.multiPolygon(DataProto.data.GeoFeatureType[DataProto.data.GeoFeatureType.fields], b)) } return f - }, Hh.getProto = function (a) { + }; + Hh.getProto = function (a) { Ua.CX = 0, Ua.CY = 0, Ua.SCALE = .7; var b = [], c = { @@ -9460,197 +9461,505 @@ var $lime_init = function (E, u) { roadWidth: a.bp.maxRoad * Ua.SCALE, generator: DataProto.data.GeoGeneratorType.vg, version: params.meta.ver_app, - wallThickness: Ua.SCALE + wallThickness: Ua.SCALE, + embedUid: "meta", + embedProps: Hh._structFromJs({ + name: a.name, + pop: a.pop, + seed: a.bp.seed, + numbered: a.bp.numbered, + realW: a.realW, + realH: a.realH + }) + }, + d = Fc.rect(a.realW, a.realH), + f = { + scale: Ua.SCALE, + cx: Ua.CX, + cy: Ua.CY, + invertY: !0, + precisionPow10: 3 }, - d = Fc.rect(a.realW, a.realH); + h = [], + k = [], + p = 0, + l = null; + b.push(c); + + var m = [Ua.arrPoly(d)], + n = Hh._bboxFromNested(m); + b.push({ type: DataProto.data.GeoType.Polygon, id: DataProto.data.GeoFeatureType.earth, - coordinates: Hh._listValueFromNested([Ua.arrPoly(d)]) + coordinates: Hh._listValueFromNested(m), + embedUid: "earth", + embedBbox: Hh._bboxToProto(n), + embedProps: Hh._structFromJs({kind: "earth"}) }); - var f = a.network.roads, h = f, k = [], p, l; - for (f = f.keys(); f.hasNext();) { - var m = f.next(), n = h.get(m), q = m; - n.type != wb.SQUARE && (m = n.type == wb.HIGHWAY ? 0 < x.widthLargeRoad ? x.widthLargeRoad : x.strokeNormal : 0 < x.widthSmallRoad ? x.widthSmallRoad : x.strokeNormal, k.push({ - type: DataProto.data.GeoType.LineString, - width: m * Ua.SCALE, - coordinates: Hh._listValueFromNested(Ua.arrPoly(q)) - })); + + l = Hh._bboxMerge(l, n); + + var q = a.network.roads, z = q, A = [], B = null, C = 0, D; + + for (q = q.keys(); q.hasNext();) { + var E = q.next(), F = z.get(E), G = E; + if (F.type != wb.SQUARE) { + D = F.type == wb.HIGHWAY ? 0 < x.widthLargeRoad ? x.widthLargeRoad : x.strokeNormal : 0 < x.widthSmallRoad ? x.widthSmallRoad : x.strokeNormal; + var H = Ua.arrPoly(G), I = Hh._bboxFromNested(H), J = "roads:" + C++; + A.push({ + type: DataProto.data.GeoType.LineString, + width: D * Ua.SCALE, + coordinates: Hh._listValueFromNested(H), + embedUid: J, + embedBbox: Hh._bboxToProto(I), + embedProps: Hh._structFromJs({kind: "road", roadType: F.type, widthWorld: D}) + }); + B = Hh._bboxMerge(B, I); + l = Hh._bboxMerge(l, I); + h.push({ + targetUid: J, + centerline: Hh._editorPolylineFromWorld(G, !1), + width: D, + closed: !1, + props: Hh._structFromJs({roadType: F.type}) + }); + } } - var g2 = { + + var K = { type: DataProto.data.GeoType.GeometryCollection, id: DataProto.data.GeoFeatureType.roads, - geometries: k + geometries: A, + embedUid: "roads", + embedBbox: Hh._bboxToProto(B), + embedProps: Hh._structFromJs({kind: "roads"}) }; - k = [], p = 0, l = a.piers; - for (; p < l.length;) { - var r = l[p]; - ++p; - k.push({ + + A = [], B = null, C = 0; + q = 0; + var L = a.piers; + + for (; q < L.length;) { + var M = L[q]; + ++q; + var N = Ua.arrPoly(M), O = Hh._bboxFromNested(N), P = "planks:" + C++; + A.push({ type: DataProto.data.GeoType.LineString, width: 5 * Ua.SCALE, - coordinates: Hh._listValueFromNested(Ua.arrPoly(r)) + coordinates: Hh._listValueFromNested(N), + embedUid: P, + embedBbox: Hh._bboxToProto(O), + embedProps: Hh._structFromJs({kind: "plank", widthWorld: 5}) + }); + B = Hh._bboxMerge(B, O); + l = Hh._bboxMerge(l, O); + k.push({ + targetUid: P, + polyline: Hh._editorPolylineFromWorld(M, !1), + props: Hh._structFromJs({kind: "plank", widthWorld: 5}) }); } - var m2 = { + + var Q = { type: DataProto.data.GeoType.GeometryCollection, id: DataProto.data.GeoFeatureType.planks, - geometries: k + geometries: A, + embedUid: "planks", + embedBbox: Hh._bboxToProto(B), + embedProps: Hh._structFromJs({kind: "planks"}) }; - k = [], p = 0, l = a.forest.trees; - for (; p < l.length;) { - var s = l[p]; - ++p; - k.push(s.data.center); + + A = [], q = 0, L = a.forest.trees; + for (; q < L.length;) { + M = L[q]; + ++q; + A.push(M.data.center); } + if (na.showOrchards) - for (p = 0, l = a.farmland.orchards; p < l.length;) { - var t = l[p]; - ++p; - var u = $b.getOrchardTrees(a, t); - for (var v = 0; v < u.length;) { - var w = u[v]; - ++v; - k.push(w.pos); - } - } - var n = [], q = [], z = [], A = [], B; - p = 0, l = a.buildings; - for (; p < l.length;) { - B = l[p]; - ++p; - q.push(B.rect); - } - p = 0, l = a.props; - for (; p < l.length;) { - var C = l[p]; - ++p; - C instanceof Sf ? k.push(Ka.__cast(C, Sf).pos) : C instanceof Tf && (B = Ka.__cast(C, Tf), C = Fc.regular(16, B.r), Eb.asTranslate(C, B.pos.x, B.pos.y), n.push(C)); - } - for (p = 0; p < q.length;) { - B = q[p]; - ++p; - z.push([Ua.arrPoly(B)]); - } - for (p = 0; p < n.length;) { - B = n[p]; - ++p; - A.push([Ua.arrPoly(B)]); + for (q = 0, L = a.farmland.orchards; q < L.length;) { + var R = L[q]; + ++q; + var S = $b.getOrchardTrees(a, R); + for (var T = 0; T < S.length;) { + var U = S[T]; + ++T; + A.push(U.pos); + } + } + + var V = [], W = [], X = [], Y = [], ca; + q = 0, L = a.buildings; + for (; q < L.length;) { + ca = L[q]; + ++q; + V.push(ca); + } + + var da = []; + q = 0, L = a.props; + for (; q < L.length;) { + var ea = L[q]; + ++q; + ea instanceof Sf ? A.push(Ka.__cast(ea, Sf).pos) : ea instanceof Tf && (ca = Ka.__cast(ea, Tf), ea = Fc.regular(16, ca.r), Eb.asTranslate(ea, ca.pos.x, ca.pos.y), W.push(ea), da.push({pos: ca.pos, r: ca.r})); } + + var fa = [], ga = null; + for (q = 0; q < V.length;) { + ca = V[q]; + var ha = q++, + ia = Ua.arrPoly(ca.rect), + ja = [ia], + ka = Hh._bboxFromNested(ja), + la = "buildings:" + ha; + X.push(ja); + fa.push({ + index: ha, + uid: la, + name: la, + bbox: Hh._bboxToProto(ka), + props: Hh._structFromJs({kind: "building", width: ca.width, depth: ca.depth, height: ca.height, large: ca.large}) + }); + ga = Hh._bboxMerge(ga, ka); + l = Hh._bboxMerge(l, ka); + k.push({ + targetUid: la, + polyline: Hh._editorPolylineFromWorld(ca.rect, !0), + props: Hh._structFromJs({kind: "building", width: ca.width, depth: ca.depth, height: ca.height, large: ca.large}) + }); + } + + var ma = []; + B = null; + for (q = 0; q < W.length;) { + ea = W[q]; + ha = q++; + ia = Ua.arrPoly(ea); + ja = [ia]; + ka = Hh._bboxFromNested(ja); + la = "prisms:" + ha; + Y.push(ja); + ma.push({ + index: ha, + uid: la, + name: la, + bbox: Hh._bboxToProto(ka), + props: Hh._structFromJs({kind: "prism", radius: da[ha] != null ? da[ha].r : null}) + }); + B = Hh._bboxMerge(B, ka); + l = Hh._bboxMerge(l, ka); + k.push({ + targetUid: la, + polyline: Hh._editorPolylineFromWorld(ea, !0), + props: Hh._structFromJs({kind: "prism", radius: da[ha] != null ? da[ha].r : null}) + }); + } + + var na2 = Ua.arrPoly(A), oa = Hh._bboxFromNested(na2), pa = [], qa = 0; + for (; qa < na2.length;) { + var ra = na2[qa], sa = qa++; + pa.push({ + index: sa, + uid: "trees:" + sa, + name: "trees:" + sa, + bbox: Hh._bboxToProto(Hh._bboxFromNested(ra)), + props: Hh._structFromJs({kind: "tree"}) + }); + } + + l = Hh._bboxMerge(l, oa); + b.push({ type: DataProto.data.GeoType.MultiPolygon, id: DataProto.data.GeoFeatureType.buildings, - coordinates: Hh._listValueFromNested(z) + coordinates: Hh._listValueFromNested(X), + embedUid: "buildings", + embedBbox: Hh._bboxToProto(ga), + embedParts: fa, + embedProps: Hh._structFromJs({kind: "buildings"}) }); + b.push({ type: DataProto.data.GeoType.MultiPolygon, id: DataProto.data.GeoFeatureType.prisms, - coordinates: Hh._listValueFromNested(A) + coordinates: Hh._listValueFromNested(Y), + embedUid: "prisms", + embedBbox: Hh._bboxToProto(B), + embedParts: ma, + embedProps: Hh._structFromJs({kind: "prisms"}) }); + b.push({ type: DataProto.data.GeoType.MultiPoint, id: DataProto.data.GeoFeatureType.trees, - coordinates: Hh._listValueFromNested(Ua.arrPoly(k)) + coordinates: Hh._listValueFromNested(na2), + embedUid: "trees", + embedBbox: Hh._bboxToProto(oa), + embedParts: pa, + embedProps: Hh._structFromJs({kind: "trees"}) }); - b.push(g2); - b.push(m2); - var D = {type: DataProto.data.GeoType.FeatureCollection, features: b}; + + b.push(K); + b.push(Q); + + var ta = { + type: DataProto.data.GeoType.FeatureCollection, + features: b, + embedUid: "root", + embedExportTransform: f, + embedBbox: Hh._bboxToProto(l), + embedEditorPayload: { + payloadRev: 1, + coordSpace: DataProto.data.EditorCoordSpaceType.world, + roadModels: h, + shapeModels: k, + props: Hh._structFromJs({generator: "vg", version: params.meta.ver_app}) + }, + embedProps: Hh._structFromJs({generator: "vg", version: params.meta.ver_app, name: a.name}) + }; + if (a.water != null) { - var E = [], F = 0, G = a.water.patches; - for (; F < G.length;) { - var H = G[F]; - ++F; - E.push([Ua.arrPoly(H)]); + var ua = [], va = [], wa = null, ya = 0, za2 = a.water.patches; + for (; ya < za2.length;) { + var Aa = za2[ya]; + ++ya; + var Ba = Ua.arrPoly(Aa), Ca = [Ba], Da = Hh._bboxFromNested(Ca), Ea = "water:" + (ya - 1); + ua.push(Ca); + va.push({ + index: ya - 1, + uid: Ea, + name: Ea, + bbox: Hh._bboxToProto(Da), + props: Hh._structFromJs({kind: "water"}) + }); + wa = Hh._bboxMerge(wa, Da); + l = Hh._bboxMerge(l, Da); + k.push({ + targetUid: Ea, + polyline: Hh._editorPolylineFromWorld(Aa, !0), + props: Hh._structFromJs({kind: "water"}) + }); } - D.features.push({ + + ta.features.push({ type: DataProto.data.GeoType.MultiPolygon, id: DataProto.data.GeoFeatureType.water, - coordinates: Hh._listValueFromNested(E) + coordinates: Hh._listValueFromNested(ua), + embedUid: "water", + embedBbox: Hh._bboxToProto(wa), + embedParts: va, + embedProps: Hh._structFromJs({kind: "water"}) }); - D.features.push({ + + var Fa = Ua.arrPoly(a.water.edgePoints), Ga = Hh._bboxFromNested(Fa), Ha = [], Ia = 0; + for (; Ia < Fa.length;) { + var Ja = Fa[Ia], Ka2 = Ia++; + Ha.push({ + index: Ka2, + uid: "extendable:" + Ka2, + name: "extendable:" + Ka2, + bbox: Hh._bboxToProto(Hh._bboxFromNested(Ja)), + props: Hh._structFromJs({kind: "extendable"}) + }); + } + + ta.features.push({ type: DataProto.data.GeoType.MultiPoint, id: DataProto.data.GeoFeatureType.extendable, - coordinates: Hh._listValueFromNested(Ua.arrPoly(a.water.edgePoints)) + coordinates: Hh._listValueFromNested(Fa), + embedUid: "extendable", + embedBbox: Hh._bboxToProto(Ga), + embedParts: Ha, + embedProps: Hh._structFromJs({kind: "extendable"}) }); + + l = Hh._bboxMerge(l, Ga); } + if (a.network.square != null) { - var I = a.network.square.slice(1), J; + var La2 = a.network.square.slice(1), Ma2; if (a.bp.waterType == "pond") - for (F = 0, G = a.water.patches; F < G.length && (J = G[F], ++F, J = ud.and(I, X.revert(J), !0), J = J != null ? J : I, J != null);) I = J; + for (p = 0, L = a.water.patches; p < L.length && (Ma2 = L[p], ++p, Ma2 = ud.and(La2, X.revert(Ma2), !0), Ma2 = Ma2 != null ? Ma2 : La2, Ma2 != null);) La2 = Ma2; else if (a.bp.waterType != null) - for (F = 0, G = a.water.getLand(); F < G.length;) - if (J = G[F], ++F, J = ud.and(I, J), J != null) { - I = J; + for (p = 0, L = a.water.getLand(); p < L.length;) + if (Ma2 = L[p], ++p, Ma2 = ud.and(La2, Ma2), Ma2 != null) { + La2 = Ma2; break } - D.features.push({ + + var Na2 = [Ua.arrPoly(La2)], Oa2 = Hh._bboxFromNested(Na2); + ta.features.push({ type: DataProto.data.GeoType.MultiPolygon, id: DataProto.data.GeoFeatureType.squares, - coordinates: Hh._listValueFromNested([[Ua.arrPoly(I)]]) + coordinates: Hh._listValueFromNested([Na2]), + embedUid: "squares", + embedBbox: Hh._bboxToProto(Oa2), + embedParts: [{ + index: 0, + uid: "squares:0", + name: "squares:0", + bbox: Hh._bboxToProto(Oa2), + props: Hh._structFromJs({kind: "square"}) + }], + embedProps: Hh._structFromJs({kind: "squares"}) }); + + l = Hh._bboxMerge(l, Oa2); } + if (a.palisade != null) { - var K = [], L = 0, M = a.palisade.segments; - for (; L < M.length;) { - var N = M[L]; - ++L; - K.push(Ua.arrPoly(N)); + var Pa2 = [], Qa2 = [], Ra2 = null, Sa2 = 0, Ta2 = a.palisade.segments; + for (; Sa2 < Ta2.length;) { + var Ua2 = Ta2[Sa2]; + ++Sa2; + var Va2 = Ua.arrPoly(Ua2), Wa2 = Hh._bboxFromNested(Va2), Xa2 = "palisade:" + (Sa2 - 1); + Pa2.push(Va2); + Qa2.push({ + index: Sa2 - 1, + uid: Xa2, + name: Xa2, + bbox: Hh._bboxToProto(Wa2), + props: Hh._structFromJs({kind: "palisade"}) + }); + Ra2 = Hh._bboxMerge(Ra2, Wa2); + l = Hh._bboxMerge(l, Wa2); + k.push({ + targetUid: Xa2, + polyline: Hh._editorPolylineFromWorld(Ua2, !1), + props: Hh._structFromJs({kind: "palisade"}) + }); } - D.features.push({ + + ta.features.push({ type: DataProto.data.GeoType.MultiLineString, id: DataProto.data.GeoFeatureType.palisade, - coordinates: Hh._listValueFromNested(K) + coordinates: Hh._listValueFromNested(Pa2), + embedUid: "palisade", + embedBbox: Hh._bboxToProto(Ra2), + embedParts: Qa2, + embedProps: Hh._structFromJs({kind: "palisade"}) }); } + if (na.showFields) { - var O = [], P = 0, Q = a.farmland.getFields(); - for (; P < Q.length;) { - var R = Q[P]; - ++P; - O.push(db.resampleClosed(R, a.bp.minRoad)); - } - var S = []; - for (P = 0; P < O.length;) { - R = O[P]; - ++P; - S.push([Ua.arrPoly(R)]); - } - D.features.push({ + var Ya2 = [], Za2 = 0, aa2 = a.farmland.getFields(); + for (; Za2 < aa2.length;) { + var ba2 = aa2[Za2]; + ++Za2; + Ya2.push(db.resampleClosed(ba2, a.bp.minRoad)); + } + + var ca2 = 0, da2 = [], ea2, fa2, ga2 = null; + for (; ca2 < Ya2.length;) { + ea2 = Ya2[ca2]; + fa2 = ca2++; + var ha2 = [Ua.arrPoly(ea2)], ia2 = Hh._bboxFromNested(ha2), ja2 = "fields:" + fa2; + da2.push(ha2); + ga2 = Hh._bboxMerge(ga2, ia2); + l = Hh._bboxMerge(l, ia2); + k.push({ + targetUid: ja2, + polyline: Hh._editorPolylineFromWorld(ea2, !0), + props: Hh._structFromJs({kind: "field"}) + }); + } + + var ka2 = []; + for (ca2 = 0; ca2 < da2.length;) { + var la2 = da2[ca2], ma2 = ca2++; + var na3 = Hh._bboxFromNested(la2); + ka2.push({ + index: ma2, + uid: "fields:" + ma2, + name: "fields:" + ma2, + bbox: Hh._bboxToProto(na3), + props: Hh._structFromJs({kind: "field"}) + }); + } + + ta.features.push({ type: DataProto.data.GeoType.MultiPolygon, id: DataProto.data.GeoFeatureType.fields, - coordinates: Hh._listValueFromNested(S) + coordinates: Hh._listValueFromNested(da2), + embedUid: "fields", + embedBbox: Hh._bboxToProto(ga2), + embedParts: ka2, + embedProps: Hh._structFromJs({kind: "fields"}) }); } - return DataProto.data.GeoObj.fromObject(D) - }, Hh.stringifyProto = function (a) { + + ta.embedBbox = Hh._bboxToProto(l); + ta.embedEditorPayload.roadModels = h; + ta.embedEditorPayload.shapeModels = k; + return DataProto.data.GeoObj.fromObject(ta) + }; + Hh.stringifyProto = function (a) { return JSON.stringify(Hh.protoToGeoJson(a), null, " ") - }, Hh.protoToGeoJson = function (a) { + }; + Hh.protoToGeoJson = function (a) { var b = {type: DataProto.data.GeoType[a.type]}; - a.id != null && (b.id = DataProto.data.GeoFeatureType[a.id]), a.width != null && (b.width = a.width), a.name != null && (b.name = a.name), a.roadWidth != null && (b.roadWidth = a.roadWidth), a.riverWidth != null && (b.riverWidth = a.riverWidth), a.towerRadius != null && (b.towerRadius = a.towerRadius), a.generator != null && (b.generator = DataProto.data.GeoGeneratorType[a.generator]), a.version != null && (b.version = a.version), a.wallThickness != null && (b.wallThickness = a.wallThickness); + a.id != null && (b.id = DataProto.data.GeoFeatureType[a.id]); + a.width != null && (b.width = a.width); + a.name != null && (b.name = a.name); + a.roadWidth != null && (b.roadWidth = a.roadWidth); + a.riverWidth != null && (b.riverWidth = a.riverWidth); + a.towerRadius != null && (b.towerRadius = a.towerRadius); + a.wallThickness != null && (b.wallThickness = a.wallThickness); + a.generator != null && (b.generator = DataProto.data.GeoGeneratorType[a.generator]); + a.version != null && (b.version = a.version); + + a.embedUid != null && (b.embedUid = a.embedUid); + + a.embedExportTransform != null && (b.embedExportTransform = { + scale: a.embedExportTransform.scale, + cx: a.embedExportTransform.cx, + cy: a.embedExportTransform.cy, + invertY: a.embedExportTransform.invertY, + precisionPow10: a.embedExportTransform.precisionPow10 + }); + + a.embedBbox != null && (b.embedBbox = { + minX: a.embedBbox.minX, + minY: a.embedBbox.minY, + maxX: a.embedBbox.maxX, + maxY: a.embedBbox.maxY + }); + + if (a.embedParts != null && a.embedParts.length) { + b.embedParts = []; + for (var c = 0; c < a.embedParts.length;) { + var d = a.embedParts[c++]; + var f = {index: d.index, uid: d.uid}; + d.name != null && (f.name = d.name); + d.bbox != null && (f.bbox = {minX: d.bbox.minX, minY: d.bbox.minY, maxX: d.bbox.maxX, maxY: d.bbox.maxY}); + d.props != null && (f.props = Hh._structToJson(d.props)); + b.embedParts.push(f); + } + } + + a.embedProps != null && (b.embedProps = Hh._structToJson(a.embedProps)); + a.embedEditorPayload != null && (b.embedEditorPayload = Hh._editorPayloadToJson(a.embedEditorPayload)); + switch (a.type) { case DataProto.data.GeoType.FeatureCollection: b.features = []; - for (var c = 0; c < a.features.length;) { - var d = a.features[c]; - ++c, b.features.push(Hh.protoToGeoJson(d)) - } + for (c = 0; c < a.features.length;) b.features.push(Hh.protoToGeoJson(a.features[c++])); break; case DataProto.data.GeoType.GeometryCollection: b.geometries = []; - for (c = 0; c < a.geometries.length;) { - d = a.geometries[c]; - ++c, b.geometries.push(Hh.protoToGeoJson(d)) - } + for (c = 0; c < a.geometries.length;) b.geometries.push(Hh.protoToGeoJson(a.geometries[c++])); break; case DataProto.data.GeoType.Feature: a.geometry != null && (b.geometry = Hh.protoToGeoJson(a.geometry)); break; default: - a.coordinates != null && (b.coordinates = Hh._listValueToJson(a.coordinates)) + a.coordinates != null && (b.coordinates = Hh._listValueToJson(a.coordinates)); } return b - }, Hh._listValueFromNested = function (a) { + }; + Hh._listValueFromNested = function (a) { for (var b = [], c = 0; c < a.length;) { var d = a[c]; ++c, Array.isArray(d) ? b.push({listValue: Hh._listValueFromNested(d)}) : b.push({numberValue: d}) @@ -9663,7 +9972,116 @@ var $lime_init = function (E, u) { } return b }, Hh._valueToJson = function (a) { - return a.listValue != null ? Hh._listValueToJson(a.listValue) : a.numberValue != null ? a.numberValue : a.stringValue != null ? a.stringValue : a.boolValue != null ? a.boolValue : null + return a.listValue != null ? Hh._listValueToJson(a.listValue) : a.structValue != null ? Hh._structToJson(a.structValue) : a.numberValue != null ? a.numberValue : a.stringValue != null ? a.stringValue : a.boolValue != null ? a.boolValue : a.nullValue != null ? null : null + }; + Hh._protoValueFromJs = function (a) { + if (a === null || a === undefined) return {nullValue: 0}; + if (Array.isArray(a)) return {listValue: {values: a.map(Hh._protoValueFromJs)}}; + if (typeof a === "number") return {numberValue: a}; + if (typeof a === "string") return {stringValue: a}; + if (typeof a === "boolean") return {boolValue: a}; + if (typeof a === "object") { + var b = {}, c; + for (c in a) Object.prototype.hasOwnProperty.call(a, c) && (b[c] = Hh._protoValueFromJs(a[c])); + return {structValue: {fields: b}}; + } + return {stringValue: String(a)} + }; + + Hh._structFromJs = function (a) { + var b = {}, c; + if (a != null && typeof a === "object") + for (c in a) Object.prototype.hasOwnProperty.call(a, c) && (b[c] = Hh._protoValueFromJs(a[c])); + return {fields: b} + }; + + Hh._structToJson = function (a) { + var b = {}, c = a.fields == null ? {} : a.fields, d; + for (d in c) Object.prototype.hasOwnProperty.call(c, d) && (b[d] = Hh._valueToJson(c[d])); + return b + }; + + Hh._bboxAcc = function (a, b) { + if (b == null) return; + if (Array.isArray(b)) { + if (b.length === 2 && typeof b[0] === "number" && typeof b[1] === "number") { + var c = b[0], d = b[1]; + a.minX = Math.min(a.minX, c); + a.minY = Math.min(a.minY, d); + a.maxX = Math.max(a.maxX, c); + a.maxY = Math.max(a.maxY, d); + } else { + for (var f = 0; f < b.length;) Hh._bboxAcc(a, b[f++]); + } + } + }; + + Hh._bboxFromNested = function (a) { + var b = {minX: Infinity, minY: Infinity, maxX: -Infinity, maxY: -Infinity}; + Hh._bboxAcc(b, a); + return isFinite(b.minX) ? b : null + }; + + Hh._bboxMerge = function (a, b) { + if (a == null) return b; + if (b == null) return a; + return { + minX: Math.min(a.minX, b.minX), + minY: Math.min(a.minY, b.minY), + maxX: Math.max(a.maxX, b.maxX), + maxY: Math.max(a.maxY, b.maxY) + } + }; + + Hh._bboxToProto = function (a) { + return a == null ? null : {minX: a.minX, minY: a.minY, maxX: a.maxX, maxY: a.maxY} + }; + + Hh._editorPointsFromWorld = function (a) { + for (var b = [], c = 0; c < a.length;) { + var d = a[c++]; + b.push({x: d.x, y: d.y}); + } + return b + }; + + Hh._editorPolylineFromWorld = function (a, b) { + null == b && (b = !1); + return {points: Hh._editorPointsFromWorld(a), closed: b} + }; + + Hh._editorPayloadToJson = function (a) { + var b = {}; + a.payloadRev != null && (b.payloadRev = a.payloadRev); + a.coordSpace != null && (b.coordSpace = a.coordSpace); + + if (a.roadModels != null && a.roadModels.length) { + b.roadModels = []; + for (var c = 0; c < a.roadModels.length;) { + var d = a.roadModels[c++], f = {targetUid: d.targetUid}; + d.centerline != null && (f.centerline = {points: d.centerline.points, closed: d.centerline.closed}); + d.width != null && (f.width = d.width); + d.closed != null && (f.closed = d.closed); + d.props != null && (f.props = Hh._structToJson(d.props)); + b.roadModels.push(f); + } + } + + if (a.shapeModels != null && a.shapeModels.length) { + b.shapeModels = []; + for (c = 0; c < a.shapeModels.length;) { + d = a.shapeModels[c++]; + f = {targetUid: d.targetUid}; + d.polyline != null && (f.polyline = {points: d.polyline.points, closed: d.polyline.closed}); + d.bezier != null && (f.bezier = d.bezier); + d.arc != null && (f.arc = d.arc); + d.props != null && (f.props = Hh._structToJson(d.props)); + b.shapeModels.push(f); + } + } + + a.props != null && (b.props = Hh._structToJson(a.props)); + return b }; var zc = function () { @@ -15899,12 +16317,8 @@ var $lime_init = function (E, u) { var d = new Qc; d.addItem("PNG", (G = this.view, r(G, G.exportPNG))); d.addItem("SVG", (G = this.view, r(G, G.exportSVG))); - d.addItem("JSON", function () { - Hh.export(a.village) - }); - d.addItem("PROTO", function () { - Hh.exportBinary(a.village) - }); + d.addItem("JSON", function () {Hh.export(a.village)}); + d.addItem("PROTO", function () {Hh.exportBinary(a.village)}); var f = new Qc, h = this.view; h = this.village.findBuilding(new I(h.map.get_mouseX(), h.map.get_mouseY())); diff --git a/src/js/mfcg.js b/src/js/mfcg.js index c981e59..b5fc0d4 100644 --- a/src/js/mfcg.js +++ b/src/js/mfcg.js @@ -7892,18 +7892,52 @@ var $lime_init = function (A, t) { }; g.JsonExporter = lg, lg.__name__ = "JsonExporter", + lg.jsToValue = function (a) { + if (a === null || a === void 0) return new DataProto.default.google.protobuf.Value({nullValue: 0}); + if (a instanceof DataProto.default.google.protobuf.Value) return a; + if (Array.isArray(a)) return new DataProto.default.google.protobuf.Value({listValue: lg.toListValue(a)}); + switch (typeof a) { + case "number": + return new DataProto.default.google.protobuf.Value({numberValue: a}); + case "string": + return new DataProto.default.google.protobuf.Value({stringValue: a}); + case "boolean": + return new DataProto.default.google.protobuf.Value({boolValue: a}); + case "object": + return new DataProto.default.google.protobuf.Value({structValue: lg.toStruct(a)}); + default: + return new DataProto.default.google.protobuf.Value({stringValue: String(a)}) + } + }, lg.toValue = function (a) { - return a instanceof DataProto.default.google.protobuf.Value ? a : Array.isArray(a) ? new DataProto.default.google.protobuf.Value({listValue: lg.toListValue(a)}) : new DataProto.default.google.protobuf.Value({numberValue: a}) + return lg.jsToValue(a) }, lg.toListValue = function (a) { for (var b = [], c = 0; c < a.length;) { var d = a[c]; - ++c, b.push(lg.toValue(d)) + ++c, b.push(lg.jsToValue(d)) } return new DataProto.default.google.protobuf.ListValue({values: b}) }, + lg.toStruct = function (a) { + if (a == null || typeof a !== "object" || Array.isArray(a)) return new DataProto.default.google.protobuf.Struct({fields: {}}); + var b = {}, c = Object.keys(a), d = 0; + for (; d < c.length;) { + var f = c[d++], h = a[f]; + h === null || h === void 0 || (b[f] = lg.jsToValue(h)) + } + return new DataProto.default.google.protobuf.Struct({fields: b}) + }, + lg.structToJson = function (a) { + var b = {}; + if (a != null && a.fields != null) for (var c = Object.keys(a.fields), d = 0; d < c.length;) { + var f = c[d++]; + b[f] = lg.valueToJson(a.fields[f]) + } + return b + }, lg.valueToJson = function (a) { - return a == null ? null : a.listValue != null && Object.hasOwnProperty.call(a, "listValue") ? lg.listValueToJson(a.listValue) : a.numberValue != null && Object.hasOwnProperty.call(a, "numberValue") ? a.numberValue : a.stringValue != null && Object.hasOwnProperty.call(a, "stringValue") ? a.stringValue : a.boolValue != null && Object.hasOwnProperty.call(a, "boolValue") ? a.boolValue : null + return a == null ? null : a.listValue != null && Object.hasOwnProperty.call(a, "listValue") ? lg.listValueToJson(a.listValue) : a.structValue != null && Object.hasOwnProperty.call(a, "structValue") ? lg.structToJson(a.structValue) : a.numberValue != null && Object.hasOwnProperty.call(a, "numberValue") ? a.numberValue : a.stringValue != null && Object.hasOwnProperty.call(a, "stringValue") ? a.stringValue : a.boolValue != null && Object.hasOwnProperty.call(a, "boolValue") ? a.boolValue : a.nullValue != null && Object.hasOwnProperty.call(a, "nullValue") ? null : null }, lg.listValueToJson = function (a) { for (var b = [], c = 0, d = a.values; c < d.length;) { @@ -7912,6 +7946,129 @@ var $lime_init = function (A, t) { } return b }, + lg.makeTransform = function () { + var a = new DataProto.data.GeoTransformObj; + return a.scale = Wa.SCALE, a.cx = Wa.CX, a.cy = Wa.CY, a.invertY = !0, a.precisionPow10 = 3, a + }, + lg._bboxWalk = function (a, b) { + if (a == null) return; + if (Array.isArray(a)) { + if (2 <= a.length && typeof a[0] === "number" && typeof a[1] === "number") { + var c = a[0], d = a[1]; + c < b.minX && (b.minX = c); + d < b.minY && (b.minY = d); + c > b.maxX && (b.maxX = c); + d > b.maxY && (b.maxY = d); + return + } + for (c = 0; c < a.length;) d = a[c], ++c, lg._bboxWalk(d, b) + } + }, + lg.bboxFromCoords = function (a) { + var b = {minX: 1 / 0, minY: 1 / 0, maxX: -1 / 0, maxY: -1 / 0}; + lg._bboxWalk(a, b); + if (b.minX === 1 / 0) return null; + var c = new DataProto.data.GeoBBoxObj; + return c.minX = b.minX, c.minY = b.minY, c.maxX = b.maxX, c.maxY = b.maxY, c + }, + lg.mergeBbox = function (a, b) { + if (a == null) return b; + if (b == null) return a; + var c = new DataProto.data.GeoBBoxObj; + return c.minX = Math.min(a.minX, b.minX), c.minY = Math.min(a.minY, b.minY), c.maxX = Math.max(a.maxX, b.maxX), c.maxY = Math.max(a.maxY, b.maxY), c + }, + lg.computeBbox = function (a) { + if (a == null) return null; + var b = null; + if (a.coordinates != null && Object.hasOwnProperty.call(a, "coordinates")) { + var c = lg.listValueToJson(a.coordinates); + b = lg.bboxFromCoords(c) + } else if (a.geometry != null && Object.hasOwnProperty.call(a, "geometry")) b = lg.computeBbox(a.geometry); + else if (a.features != null && a.features.length) { + c = 0; + for (var d = a.features; c < d.length;) { + var f = d[c]; + ++c; + b = lg.mergeBbox(b, lg.computeBbox(f)) + } + } else if (a.geometries != null && a.geometries.length) { + c = 0; + for (d = a.geometries; c < d.length;) f = d[c], ++c, b = lg.mergeBbox(b, lg.computeBbox(f)) + } + return b + }, + lg.ensureParts = function (a) { + if (a == null) return; + if (!(a.type == DataProto.data.GeoType.MultiPolygon || a.type == DataProto.data.GeoType.MultiPoint || a.type == DataProto.data.GeoType.MultiLineString)) return; + if (a.coordinates == null || !Object.hasOwnProperty.call(a, "coordinates")) return; + if (a.embedParts != null && a.embedParts.length) return; + var b = lg.listValueToJson(a.coordinates); + if (!Array.isArray(b)) return; + a.embedParts = []; + for (var c = 0; c < b.length;) { + var d = c, f = b[c++]; + var h = new DataProto.data.GeoPartObj; + h.index = d; + h.uid = (a.embedUid != null && Object.hasOwnProperty.call(a, "embedUid") ? a.embedUid : "obj") + ":part:" + d; + a.name != null && Object.hasOwnProperty.call(a, "name") && (h.name = "" + a.name + " #" + (d + 1)); + var k = lg.bboxFromCoords(f); + k != null && (h.bbox = k); + h.props = lg.toStruct({parentUid: a.embedUid, index: d}); + a.embedParts.push(h) + } + }, + lg.buildPropsForObj = function (a) { + if (a == null) return null; + var b = {geoType: DataProto.data.GeoType[a.type]}; + a.id != null && Object.hasOwnProperty.call(a, "id") && (b.featureId = DataProto.data.GeoFeatureType[a.id]); + a.width != null && Object.hasOwnProperty.call(a, "width") && (b.width = a.width); + a.roadWidth != null && Object.hasOwnProperty.call(a, "roadWidth") && (b.roadWidth = a.roadWidth); + a.riverWidth != null && Object.hasOwnProperty.call(a, "riverWidth") && (b.riverWidth = a.riverWidth); + a.towerRadius != null && Object.hasOwnProperty.call(a, "towerRadius") && (b.towerRadius = a.towerRadius); + a.wallThickness != null && Object.hasOwnProperty.call(a, "wallThickness") && (b.wallThickness = a.wallThickness); + a.generator != null && Object.hasOwnProperty.call(a, "generator") && (b.generator = DataProto.data.GeoGeneratorType[a.generator]); + a.version != null && Object.hasOwnProperty.call(a, "version") && (b.version = a.version); + a.embedUid != null && Object.hasOwnProperty.call(a, "embedUid") && (b.uid = a.embedUid); + return b + }, + lg.enrichGeoObj = function (a, b) { + if (a == null) return; + a.embedExportTransform == null && b != null && b.transform != null && (a.embedExportTransform = b.transform); + (a.embedUid == null || "" === a.embedUid) && b != null && b.uid != null && (a.embedUid = b.uid); + if (a.embedProps == null) { + var c = lg.buildPropsForObj(a); + c != null && (a.embedProps = lg.toStruct(c)) + } + lg.ensureParts(a); + a.embedBbox == null && (a.embedBbox = lg.computeBbox(a)); + if (a.geometry != null && Object.hasOwnProperty.call(a, "geometry")) lg.enrichGeoObj(a.geometry, {uid: a.embedUid + "/geometry", transform: a.embedExportTransform}); + if (a.features != null && a.features.length) for (c = 0; c < a.features.length;) { + var d = a.features[c], f = d != null && d.id != null && Object.hasOwnProperty.call(d, "id") ? DataProto.data.GeoFeatureType[d.id] : "" + c; + ++c; + lg.enrichGeoObj(d, {uid: a.embedUid + "/features/" + f, transform: a.embedExportTransform}) + } + if (a.geometries != null && a.geometries.length) for (c = 0; c < a.geometries.length;) d = a.geometries[c], f = "" + c, ++c, lg.enrichGeoObj(d, {uid: a.embedUid + "/geometries/" + f, transform: a.embedExportTransform}) + }, + lg.makeEditorPayload = function (a) { + ba.init(); + za.init(); + var b = new DataProto.data.EditorPayloadObj; + b.payloadRev = 1; + b.coordSpace = DataProto.data.EditorCoordSpaceType.export; + var c = {state: ba.data, url: za.data}; + a != null && (c.blueprint = a.bp, c.name = a.name); + b.props = lg.toStruct(c); + return b + }, + lg.enrichRoot = function (a, b) { + if (a == null) return; + var c = lg.makeTransform(); + a.embedExportTransform = c; + a.embedUid = "root"; + a.embedEditorPayload = lg.makeEditorPayload(b); + a.embedProps == null && (a.embedProps = lg.toStruct({generator: "mfcg", version: A.current.meta.h.version, blueprint: b != null ? b.bp : null, state: ba.data, url: za.data})); + lg.enrichGeoObj(a, {uid: "root", transform: c}) + }, lg.toJsonObject = function (a) { var b = DataProto.data.GeoType[a.type], c = {type: b}; a.id != null && Object.hasOwnProperty.call(a, "id") && (c.id = DataProto.data.GeoFeatureType[a.id]); @@ -7923,6 +8080,51 @@ var $lime_init = function (A, t) { a.generator != null && Object.hasOwnProperty.call(a, "generator") && (c.generator = DataProto.data.GeoGeneratorType[a.generator]); a.version != null && Object.hasOwnProperty.call(a, "version") && (c.version = a.version); a.riverWidth != null && Object.hasOwnProperty.call(a, "riverWidth") && (c.riverWidth = a.riverWidth); + a.embedUid != null && Object.hasOwnProperty.call(a, "embedUid") && (c.embedUid = a.embedUid); + a.embedExportTransform != null && Object.hasOwnProperty.call(a, "embedExportTransform") && (c.embedExportTransform = {scale: a.embedExportTransform.scale, cx: a.embedExportTransform.cx, cy: a.embedExportTransform.cy, invertY: a.embedExportTransform.invertY, precisionPow10: a.embedExportTransform.precisionPow10}); + a.embedBbox != null && Object.hasOwnProperty.call(a, "embedBbox") && (c.embedBbox = {minX: a.embedBbox.minX, minY: a.embedBbox.minY, maxX: a.embedBbox.maxX, maxY: a.embedBbox.maxY}); + a.embedProps != null && Object.hasOwnProperty.call(a, "embedProps") && (c.embedProps = lg.structToJson(a.embedProps)); + if (a.embedParts != null && a.embedParts.length) { + c.embedParts = []; + for (var d2 = 0; d2 < a.embedParts.length;) { + var f2 = a.embedParts[d2++]; + c.embedParts.push({ + index: f2.index, + uid: f2.uid, + name: f2.name, + bbox: f2.bbox != null ? {minX: f2.bbox.minX, minY: f2.bbox.minY, maxX: f2.bbox.maxX, maxY: f2.bbox.maxY} : null, + props: f2.props != null ? lg.structToJson(f2.props) : null + }) + } + } + if (a.embedEditorPayload != null && Object.hasOwnProperty.call(a, "embedEditorPayload")) { + var h2 = a.embedEditorPayload, k2 = {}; + h2.payloadRev != null && Object.hasOwnProperty.call(h2, "payloadRev") && (k2.payloadRev = h2.payloadRev); + h2.coordSpace != null && Object.hasOwnProperty.call(h2, "coordSpace") && (k2.coordSpace = DataProto.data.EditorCoordSpaceType[h2.coordSpace]); + h2.layers != null && h2.layers.length && (k2.layers = h2.layers.map(function (a2) { + return {layerId: a2.layerId, visible: a2.visible, locked: a2.locked, zIndex: a2.zIndex} + })); + h2.groups != null && h2.groups.length && (k2.groups = h2.groups.map(function (a2) { + return {groupUid: a2.groupUid, name: a2.name, memberUids: a2.memberUids, props: a2.props != null ? lg.structToJson(a2.props) : null} + })); + h2.links != null && h2.links.length && (k2.links = h2.links.map(function (a2) { + return {aUid: a2.aUid, bUid: a2.bUid, type: DataProto.data.EditorLinkType[a2.type], props: a2.props != null ? lg.structToJson(a2.props) : null} + })); + h2.roadModels != null && h2.roadModels.length && (k2.roadModels = h2.roadModels.map(function (a2) { + return {targetUid: a2.targetUid, centerline: a2.centerline != null ? {closed: a2.centerline.closed, points: a2.centerline.points} : null, width: a2.width, closed: a2.closed, props: a2.props != null ? lg.structToJson(a2.props) : null} + })); + h2.shapeModels != null && h2.shapeModels.length && (k2.shapeModels = h2.shapeModels.map(function (a2) { + return {targetUid: a2.targetUid, polyline: a2.polyline, bezier: a2.bezier, arc: a2.arc, props: a2.props != null ? lg.structToJson(a2.props) : null} + })); + h2.snapNodes != null && h2.snapNodes.length && (k2.snapNodes = h2.snapNodes.map(function (a2) { + return {nodeUid: a2.nodeUid, pos: a2.pos, incidentUids: a2.incidentUids, props: a2.props != null ? lg.structToJson(a2.props) : null} + })); + h2.constraints != null && h2.constraints.length && (k2.constraints = h2.constraints.map(function (a2) { + return {constraintUid: a2.constraintUid, type: DataProto.data.EditorConstraintType[a2.type], targetUids: a2.targetUids, params: a2.params != null ? lg.structToJson(a2.params) : null} + })); + h2.props != null && Object.hasOwnProperty.call(h2, "props") && (k2.props = lg.structToJson(h2.props)); + c.embedEditorPayload = k2 + } switch (a.type) { case DataProto.data.GeoType.Feature: a.geometry != null && Object.hasOwnProperty.call(a, "geometry") && (c.geometry = lg.toJsonObject(a.geometry)); @@ -8071,11 +8273,14 @@ var $lime_init = function (A, t) { n = []; g2 = k.keys(); for (; g2.hasNext();) l2 = g2.next(), n.push(l2); - return b = lg.featureCollection([p, q2, u2, w2, r2, lg.multiThick(DataProto.data.GeoFeatureType.planks, n, null, function (a2) { + b = lg.featureCollection([p, q2, u2, w2, r2, lg.multiThick(DataProto.data.GeoFeatureType.planks, n, null, function (a2) { return a2 }, function (a2) { return k.h[a2.__id__] - }), lg.multiPolygon(DataProto.data.GeoFeatureType.buildings, b), lg.multiPolygon(DataProto.data.GeoFeatureType.prisms, c), lg.multiPolygon(DataProto.data.GeoFeatureType.squares, d), lg.multiPolygon(DataProto.data.GeoFeatureType.greens, f), lg.multiPolygon(DataProto.data.GeoFeatureType.fields, h), lg.multiPoint(DataProto.data.GeoFeatureType.trees, x2), m]), 0 < a.waterEdgeE.length && b.features.push(lg.multiPolygon(DataProto.data.GeoFeatureType.water, [Ua.toPoly(a.waterEdgeE)])), b + }), lg.multiPolygon(DataProto.data.GeoFeatureType.buildings, b), lg.multiPolygon(DataProto.data.GeoFeatureType.prisms, c), lg.multiPolygon(DataProto.data.GeoFeatureType.squares, d), lg.multiPolygon(DataProto.data.GeoFeatureType.greens, f), lg.multiPolygon(DataProto.data.GeoFeatureType.fields, h), lg.multiPoint(DataProto.data.GeoFeatureType.trees, x2), m]); + 0 < a.waterEdgeE.length && b.features.push(lg.multiPolygon(DataProto.data.GeoFeatureType.water, [Ua.toPoly(a.waterEdgeE)])); + lg.enrichRoot(b, a); + return b }, lg.multiThick = function (a, b, c, d, f) { c == null && (c = !1); @@ -8087,7 +8292,6 @@ var $lime_init = function (A, t) { } return lg.geometryCollection(a, h) }; - var Rd = function () { }; g["SvgExporter"] = Rd;