@arcgis/map-components
Version:
ArcGIS Map Components
291 lines (290 loc) • 12.8 kB
JavaScript
/* COPYRIGHT Esri - https://js.arcgis.com/5.1/LICENSE.txt */
import { c as C } from "../../chunks/runtime.js";
import { css as x, html as b } from "lit";
import * as G from "@arcgis/core/geometry/operators/cutOperator.js";
import * as T from "@arcgis/core/geometry/operators/lengthOperator.js";
import * as L from "@arcgis/core/geometry/operators/projectOperator.js";
import * as I from "@arcgis/core/geometry/operators/proximityOperator.js";
import v from "@arcgis/core/geometry/Polyline.js";
import A from "@arcgis/core/Graphic.js";
import w from "@arcgis/core/rest/networks/support/TraceLocation.js";
import S from "@arcgis/core/symbols/SimpleMarkerSymbol.js";
import { LitElement as F, createEvent as _ } from "@arcgis/lumina";
import { log as c, composeMissingPropertyMessage as m } from "@arcgis/toolkit/log";
import { u as N } from "../../chunks/useT9n.js";
import { d as k, i as R } from "../../chunks/layer-utils.js";
const P = x`calcite-block{--calcite-block-content-space: 0;--calcite-block-border-color: transparent;margin:0}.add-location-button{--calcite-button-border-color: var(--calcite-color-border-1);--calcite-button-icon-color: var(--calcite-color-text-1);--calcite-button-text-color: var(--calcite-color-text-1)}.button-container{justify-content:center;display:grid}.clear-button{--calcite-button-border-color: transparent}`;
class E extends F {
constructor() {
super(...arguments), this.messages = N({ blocking: !0 }), this.isSelectWaiting = !1, this.traceLocationType = "starting-point", this.spatialTolerance = 0.05, this.autoDestroyDisabled = !1, this.arcgisTraceLocationChange = _(), this.arcgisTraceLocationSelectEnd = _(), this.arcgisTraceLocationSelectStart = _();
}
static {
this.properties = { isSelectWaiting: 16, beforeTraceLocationSelectStart: 0, afterHitTest: 0, view: 0, traceLocationType: 1, traceLocations: 0, filterLayers: 0, sketchViewModel: 0, spatialTolerance: 9, autoDestroyDisabled: 5, utilityNetwork: 0 };
}
static {
this.styles = P;
}
async destroy() {
this._resetCursor(), await this.manager.destroy();
}
async load() {
L.isLoaded() || await L.load();
}
_calculatePercentAlong(e, t) {
const r = e.clone(), s = r.spatialReference, o = t.spatialReference;
if (!s || !o)
return c("warn", this, "Unable to calculate percent along because geometry is missing a spatial reference."), -1;
let a = t;
if (!s.equals(o)) {
const h = L.execute(t, s);
if (!h)
return c("warn", this, "Unable to project flag point to source geometry spatial reference."), -1;
a = h;
}
const n = I.getNearestCoordinate(r, a);
if (n.isEmpty)
return c("warn", this, "Unable to compute nearest coordinate for polyline flag."), -1;
const i = n.coordinate, l = i.x - 0.5, u = i.y - 0.5, p = i.x + 0.5, d = i.y + 0.5, g = new v({
hasZ: !1,
hasM: !0,
paths: [
[
[l, u],
[p, d]
]
],
spatialReference: r.spatialReference
}), f = G.execute(r, g);
if (f.length > 0) {
const h = T.execute(r, { unit: "feet" });
let y;
return f[0].paths[0][0][0] === r.paths[0][0][0] ? y = T.execute(f[0], { unit: "feet" }) : f.length > 1 ? y = T.execute(f[1], { unit: "feet" }) : y = 0, y / h;
}
return c("warn", this, "Unable to cut the source geometry with the flag geometry."), -1;
}
get _edgeSourceLayerIds() {
const e = this.utilityNetwork?.dataElement?.domainNetworks;
return e ? e.flatMap((t) => t.edgeSources).map((t) => t.layerId).filter(Boolean) : [];
}
async _handleAddButtonClick() {
const { view: e, sketchViewModel: t } = this;
if (!(e && t)) {
c("error", this, "Cannot add trace location."), t || c("error", this, m("sketchViewModel")), e || c("error", this, m("view"));
return;
}
if (this.beforeTraceLocationSelectStart) {
this.isSelectWaiting = !0;
try {
await this.beforeTraceLocationSelectStart();
} finally {
this.isSelectWaiting = !1;
}
}
await this._startSketch(e, t);
}
async _startSketch(e, t) {
this.arcgisTraceLocationSelectStart.emit({ cancelSelect: () => t.cancel() }).defaultPrevented || (this._clickHandler?.remove(), this._clickHandler = t.on("create", (s) => this._handleSketchComplete(s, e, t)), "acquireCursor" in e && e.acquireCursor("crosshair"), t.snappingOptions.enabled = !0, t.create("point"));
}
_handleSketchComplete(e, t, r) {
if (e.state === "complete" && e.graphic) {
r.layer.remove(e.graphic), this._performHitTest(e, t, r);
return;
}
e.state === "cancel" && (this._resetCursor(), this.arcgisTraceLocationSelectEnd.emit());
}
async _performHitTest(e, t, r) {
const { utilityNetwork: s } = this, { graphic: o } = e;
if (!s) {
c("error", this, m("utilityNetwork")), this._resetCursor(), this.arcgisTraceLocationSelectEnd.emit();
return;
}
if (o?.geometry?.type !== "point") {
c("warn", this, "No screen point available for hit test."), this._startSketch(t, r);
return;
}
const a = o.geometry, n = t.toScreen(a);
if (!n) {
c("warn", this, "No screen point available for hit test."), this._startSketch(t, r);
return;
}
const l = (await t.hitTest(n, {
include: this.filterLayers
})).results.filter((p) => p.type === "graphic" && p?.layer && p.graphic);
if (!l.length) {
c("info", this, "No usable hit test results found."), this._startSketch(t, r);
return;
}
this._resetCursor(), await this._processHitTestResults(l, a, t) ? this.arcgisTraceLocationSelectEnd.emit() : this._startSketch(t, r);
}
_resetCursor() {
const { view: e, sketchViewModel: t } = this;
if (!e) {
c("error", this, m("view"));
return;
}
t && (t.snappingOptions.enabled = !1), this._clickHandler?.remove(), this._clickHandler = void 0, "acquireCursor" in e && e.acquireCursor("default");
}
async _processHitTestResults(e, t, r) {
if (!e.length)
return c("error", this, "There are no hit test results to process."), !1;
const s = e[0], o = e.map((l) => {
const u = l, p = u.graphic;
return p.origin = u.layer, p.sourceLayer = u.layer, p;
});
let a = s.graphic;
if (this.afterHitTest)
try {
a = await this.afterHitTest(o);
} catch {
a = null;
}
if (!a)
return c("error", this, "No graphic available from hit test results."), this.arcgisTraceLocationSelectEnd.emit(), !0;
const n = await this._ensureNecessaryAttributes(a);
return n ? await this._generateTraceLocation(n, t, r) : (c("error", this, "Unable to ensure necessary attributes on the selected graphic."), this.arcgisTraceLocationSelectEnd.emit(), !0);
}
async _ensureNecessaryAttributes(e) {
const t = (k(e.layer), e.layer), r = t.geometryType === null, s = t.fieldsIndex?.get("assetgroup") ?? !1, o = t.fieldsIndex?.get("assetgroup")?.name ?? "assetgroup", a = t.fieldsIndex?.get("assettype") ?? !1, n = t.fieldsIndex?.get("assettype")?.name ?? "assettype", i = e.getGlobalId(), l = e.getObjectId(), u = s ? !!e.getAttribute(o) : !0, p = a ? !!e.getAttribute(n) : !0, d = !!e.geometry;
if (i && l && u && p && (d || r))
return e;
const g = t.createQuery();
return g.objectIds = [l], (await t.queryFeatures(g))?.features[0] || null;
}
async _generateTraceLocation(e, t, r) {
const { traceLocations: s } = this, o = e.getGlobalId() ?? "", a = e.geometry?.type, n = await this._generateFlagInfo(e, t);
if (!n)
return c("error", this, "Unable to generate flag info for trace location."), !1;
const i = s?.filter((u) => u.spatialProperties.mapGraphic?.getGlobalId() === o) ?? [];
if (i.length > 0) {
if (a !== "polyline")
return c("warn", this, "A flag with the same globalId already exists."), !1;
if (i.some((u) => Math.abs(u.traceLocation.percentAlong - n.traceLocation.percentAlong) <= this.spatialTolerance))
return c("warn", this, "A flag with the same globalId already exists within tolerance."), !1;
}
const l = this._addFlagGraphic(e, t, r);
return l ? (n.spatialProperties.flagGraphic = l, s?.add(n), !0) : (c("warn", this, "Unable to add flag graphic."), !1);
}
async _generateFlagInfo(e, t) {
const { traceLocationType: r, utilityNetwork: s } = this, o = e.getGlobalId() ?? "", a = e.geometry?.type, n = await this._generateItemTitle(e);
if (a === "point" || a === "polygon") {
const i = s?.getTerminalConfiguration(e), l = i ? i.terminals[0].id : 1;
return {
traceLocation: new w({
type: r,
isFilterBarrier: !1,
globalId: o,
terminalId: l
}),
flagProperties: {
title: n,
expanded: !1,
terminalConfiguration: i ?? void 0,
selectedTerminals: i ? /* @__PURE__ */ new Set([l]) : void 0
},
spatialProperties: {
mapPoint: t,
mapGraphic: e
}
};
} else if (a === "polyline") {
const i = this._calculatePercentAlong(e.geometry, t);
return i < 0 ? (c("warn", this, "Unable to calculate percent along for polyline flag."), null) : {
traceLocation: new w({
type: r,
isFilterBarrier: !1,
globalId: o,
percentAlong: i
}),
flagProperties: {
title: n,
expanded: !1,
terminalConfiguration: void 0,
selectedTerminals: void 0
},
spatialProperties: {
mapPoint: t,
mapGraphic: e
}
};
} else if (!a) {
const i = R(e.layer) ? e.layer.parent : e.layer, l = i && this._edgeSourceLayerIds.includes(i.layerId), u = s?.getTerminalConfiguration(e), p = u ? u.terminals[0].id : l ? -1 : 1, d = l ? 0.5 : -1;
return {
traceLocation: new w({
type: r,
isFilterBarrier: !1,
globalId: o,
terminalId: p,
percentAlong: d
}),
flagProperties: {
title: n,
expanded: !1,
terminalConfiguration: u ?? void 0,
selectedTerminals: u ? /* @__PURE__ */ new Set([p]) : void 0
},
spatialProperties: {
mapPoint: t,
mapGraphic: e
}
};
}
return null;
}
async _generateItemTitle(e) {
const { messages: t } = this, r = (k(e.layer), e.layer);
return ("getFeatureTitle" in r ? await r.getFeatureTitle(e) : null) || e?.getObjectId()?.toString() || t.labels.unknown;
}
_addFlagGraphic(e, t, r) {
const s = e.geometry ? e.geometry.type === "point" ? e.geometry : t : null, o = this._createFlagSymbol(), a = new A({
geometry: s,
symbol: o,
attributes: e.attributes
});
return r.graphics.add(a), a;
}
_createFlagSymbol() {
const { traceLocationType: e } = this, t = [244, 21, 21, 0.6], r = [21, 244, 21, 0.6];
return e === "stopping-point" ? new S({
color: t,
style: "x",
size: 12,
outline: {
color: t,
width: 2
}
}) : e === "barrier" ? new S({
color: t,
style: "square",
size: 12,
outline: {
color: t,
width: 0
}
}) : new S({
color: r,
style: "circle",
size: 12,
outline: {
color: r,
width: 0
}
});
}
_handleClearButtonClick() {
const { view: e, traceLocations: t } = this;
t?.forEach((r) => {
r.spatialProperties.flagGraphic && e && e.graphics.remove(r.spatialProperties.flagGraphic);
}), t?.removeAll();
}
renderAddLocationBlock() {
const { traceLocationType: e, messages: t, traceLocations: r, view: s } = this, o = e === "starting-point" ? t.types.startingPoint : e === "barrier" ? t.types.barrier : t.types.stoppingPoint, a = o.heading, n = o.description, i = o.buttonText;
return b`<calcite-block .heading=${a} .label=${a} expanded .description=${n}>${r?.length ? b`<calcite-button class="clear-button" slot=actions-end appearance=transparent .label=${t.buttons.clear} =${() => this._handleClearButtonClick()}>${t.buttons.clear}</calcite-button><arcgis-utility-network-trace-location-list .traceLocations=${r} .traceLocationType=${e} .view=${s}></arcgis-utility-network-trace-location-list>` : null}<div class="button-container"><calcite-button .loading=${this.isSelectWaiting} class="add-location-button" icon-start=select appearance=outline .label=${i} =${() => this._handleAddButtonClick()}>${i}</calcite-button></div></calcite-block>`;
}
render() {
return b`<div class="root">${this.renderAddLocationBlock()}</div>`;
}
}
C("arcgis-utility-network-trace-location", E);
export {
E as ArcgisUtilityNetworkTraceLocation
};