@foodmarketmaker/mapag 0.0.47 → 0.0.49
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/fesm2022/foodmarketmaker-mapag.mjs +1932 -607
- package/fesm2022/foodmarketmaker-mapag.mjs.map +1 -1
- package/index.d.ts +208 -21
- package/package.json +1 -1
|
@@ -7,16 +7,16 @@ import * as i1$1 from '@angular/forms';
|
|
|
7
7
|
import { FormsModule, NG_VALUE_ACCESSOR } from '@angular/forms';
|
|
8
8
|
import { takeUntilDestroyed, rxResource } from '@angular/core/rxjs-interop';
|
|
9
9
|
import { FaIconComponent } from '@fortawesome/angular-fontawesome';
|
|
10
|
-
import { faMousePointer, faList, faTrashAlt, faChevronRight, faGear, faEye, faEyeSlash,
|
|
10
|
+
import { faMousePointer, faList, faTrashAlt, faChevronRight, faGear, faTimes, faEye, faEyeSlash, faCircle, faFire, faThLarge, faFill, faPaintBrush, faImage, faFilter, faFont, faPrint, faInfoCircle } from '@fortawesome/free-solid-svg-icons';
|
|
11
11
|
import booleanContains from '@turf/boolean-contains';
|
|
12
12
|
import booleanOverlap from '@turf/boolean-overlap';
|
|
13
13
|
import { polygon, feature } from '@turf/helpers';
|
|
14
14
|
import { Subject, firstValueFrom, map } from 'rxjs';
|
|
15
|
+
import maplibregl, { Popup } from 'maplibre-gl';
|
|
15
16
|
import MapboxDraw from 'maplibre-gl-draw';
|
|
16
17
|
import RectangleMode from 'mapbox-gl-draw-rectangle-mode';
|
|
17
18
|
import { saveAs } from 'file-saver';
|
|
18
19
|
import 'mapbox-gl-infobox/styles.css';
|
|
19
|
-
import maplibregl, { Popup } from 'maplibre-gl';
|
|
20
20
|
import bbox from '@turf/bbox';
|
|
21
21
|
import bboxPolygon from '@turf/bbox-polygon';
|
|
22
22
|
import buffer from '@turf/buffer';
|
|
@@ -26,6 +26,7 @@ import { BinaryWriter, BinaryReader } from '@bufbuild/protobuf/wire';
|
|
|
26
26
|
import { featureFilter } from '@mapbox/mapbox-gl-style-spec';
|
|
27
27
|
import { NgSelectComponent, NgLabelTemplateDirective, NgOptionTemplateDirective } from '@ng-select/ng-select';
|
|
28
28
|
import { CdkVirtualScrollViewport, CdkVirtualForOf, CdkFixedSizeVirtualScroll } from '@angular/cdk/scrolling';
|
|
29
|
+
import { DomSanitizer } from '@angular/platform-browser';
|
|
29
30
|
|
|
30
31
|
function SaveMap(map) {
|
|
31
32
|
var mapCanvas = map.getCanvas();
|
|
@@ -33,6 +34,19 @@ function SaveMap(map) {
|
|
|
33
34
|
// here is the most important part because if you dont replace you will get a DOM 18 exception.
|
|
34
35
|
window.location.href = image;
|
|
35
36
|
}
|
|
37
|
+
function flyToFeature(map, f, zoom = 12) {
|
|
38
|
+
if (!map) {
|
|
39
|
+
return;
|
|
40
|
+
}
|
|
41
|
+
if (!f.geometry || f.geometry.type !== 'Point') {
|
|
42
|
+
return;
|
|
43
|
+
}
|
|
44
|
+
const coords = f.geometry.coordinates;
|
|
45
|
+
map.flyTo({
|
|
46
|
+
center: [coords[0], coords[1]],
|
|
47
|
+
zoom: zoom,
|
|
48
|
+
});
|
|
49
|
+
}
|
|
36
50
|
function AddLayer(map, layer, afterId) {
|
|
37
51
|
if (!map)
|
|
38
52
|
return false;
|
|
@@ -48,6 +62,19 @@ function AddLayer(map, layer, afterId) {
|
|
|
48
62
|
return false;
|
|
49
63
|
}
|
|
50
64
|
}
|
|
65
|
+
function ToggleDialog(dialogSignal) {
|
|
66
|
+
const dialog = dialogSignal();
|
|
67
|
+
if (!dialog) {
|
|
68
|
+
return;
|
|
69
|
+
}
|
|
70
|
+
const dialogElement = dialog.nativeElement;
|
|
71
|
+
if (dialogElement.open) {
|
|
72
|
+
dialogElement.close();
|
|
73
|
+
}
|
|
74
|
+
else {
|
|
75
|
+
dialogElement.show();
|
|
76
|
+
}
|
|
77
|
+
}
|
|
51
78
|
function RemoveLayer(map, layerId) {
|
|
52
79
|
if (!map)
|
|
53
80
|
return;
|
|
@@ -181,9 +208,8 @@ async function sampleTilesForLayers(pmtiles) {
|
|
|
181
208
|
return [];
|
|
182
209
|
}
|
|
183
210
|
}
|
|
184
|
-
async function pmtilesPixelInfo(url, map,
|
|
211
|
+
async function pmtilesPixelInfo(url, map, lngLat) {
|
|
185
212
|
const pmtiles = new PMTiles(url.replace('pmtiles://', ''));
|
|
186
|
-
const lngLat = e.lngLat; // {lng, lat}
|
|
187
213
|
// Convert lat/lon to tile coordinates at a chosen zoom
|
|
188
214
|
const zoom = 10; // pick a zoom level for sampling
|
|
189
215
|
const x = Math.floor(((lngLat.lng + 180) / 360) * Math.pow(2, zoom));
|
|
@@ -13596,6 +13622,17 @@ class MapboxMapperGroup {
|
|
|
13596
13622
|
clear() {
|
|
13597
13623
|
this.mappers.forEach((mapper) => mapper.clear());
|
|
13598
13624
|
}
|
|
13625
|
+
renderPopup(f) {
|
|
13626
|
+
for (const [name, mapper] of this.mappers) {
|
|
13627
|
+
if (mapper.renderPopup) {
|
|
13628
|
+
const result = mapper.renderPopup(f);
|
|
13629
|
+
if (result) {
|
|
13630
|
+
return result;
|
|
13631
|
+
}
|
|
13632
|
+
}
|
|
13633
|
+
}
|
|
13634
|
+
return undefined;
|
|
13635
|
+
}
|
|
13599
13636
|
}
|
|
13600
13637
|
|
|
13601
13638
|
class StandardLayersMapper {
|
|
@@ -13797,8 +13834,14 @@ class AreaMapperMapper {
|
|
|
13797
13834
|
this.map.setZoom(src.minZoom);
|
|
13798
13835
|
}
|
|
13799
13836
|
}
|
|
13800
|
-
renderPopup(
|
|
13801
|
-
|
|
13837
|
+
renderPopup(feature) {
|
|
13838
|
+
if (!this.map) {
|
|
13839
|
+
return undefined;
|
|
13840
|
+
}
|
|
13841
|
+
if (feature.layer.id !== this.layer) {
|
|
13842
|
+
return undefined;
|
|
13843
|
+
}
|
|
13844
|
+
return undefined;
|
|
13802
13845
|
}
|
|
13803
13846
|
useStat(id, stats) {
|
|
13804
13847
|
const i = stats.findIndex((a) => a.id == id);
|
|
@@ -14179,6 +14222,31 @@ class MapService {
|
|
|
14179
14222
|
this.map.getCanvas().style.cursor = 'pointer';
|
|
14180
14223
|
}
|
|
14181
14224
|
}
|
|
14225
|
+
currentPopup = null;
|
|
14226
|
+
handleMapClick(point, lngLat) {
|
|
14227
|
+
if (!this.map)
|
|
14228
|
+
return;
|
|
14229
|
+
if (!this.mapper)
|
|
14230
|
+
return;
|
|
14231
|
+
// Get the features
|
|
14232
|
+
const features = this.map.queryRenderedFeatures(point);
|
|
14233
|
+
let html = undefined;
|
|
14234
|
+
for (const feature of features) {
|
|
14235
|
+
html = this.mapper.renderPopup(feature);
|
|
14236
|
+
if (html) {
|
|
14237
|
+
break;
|
|
14238
|
+
}
|
|
14239
|
+
}
|
|
14240
|
+
if (html) {
|
|
14241
|
+
if (this.currentPopup) {
|
|
14242
|
+
this.currentPopup.remove();
|
|
14243
|
+
}
|
|
14244
|
+
this.currentPopup = new Popup()
|
|
14245
|
+
.setLngLat(lngLat)
|
|
14246
|
+
.setHTML(html)
|
|
14247
|
+
.addTo(this.map);
|
|
14248
|
+
}
|
|
14249
|
+
}
|
|
14182
14250
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: MapService, deps: [], target: i0.ɵɵFactoryTarget.Injectable });
|
|
14183
14251
|
static ɵprov = i0.ɵɵngDeclareInjectable({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: MapService, providedIn: 'root' });
|
|
14184
14252
|
}
|
|
@@ -15092,6 +15160,15 @@ class MapComponent {
|
|
|
15092
15160
|
this.mapper().onReady(map, this.svc);
|
|
15093
15161
|
});
|
|
15094
15162
|
});
|
|
15163
|
+
map.on('click', (e) => {
|
|
15164
|
+
this.svc.handleMapClick(e.point, e.lngLat);
|
|
15165
|
+
});
|
|
15166
|
+
map.on('touchend', (e) => {
|
|
15167
|
+
// Ignore multi-touch events
|
|
15168
|
+
if (e.points && e.points.length == 1) {
|
|
15169
|
+
this.svc.handleMapClick(e.point, e.lngLat);
|
|
15170
|
+
}
|
|
15171
|
+
});
|
|
15095
15172
|
}
|
|
15096
15173
|
});
|
|
15097
15174
|
}
|
|
@@ -16083,7 +16160,7 @@ class CroplandDataLayerMapper {
|
|
|
16083
16160
|
if (!this.settings().visible) {
|
|
16084
16161
|
return;
|
|
16085
16162
|
}
|
|
16086
|
-
const pixel = await pmtilesPixelInfo(CroplandDataLayerMapper.PMTILES, map, e);
|
|
16163
|
+
const pixel = await pmtilesPixelInfo(CroplandDataLayerMapper.PMTILES, map, e.lngLat);
|
|
16087
16164
|
if (!pixel) {
|
|
16088
16165
|
console.error('No pixel data returned');
|
|
16089
16166
|
return;
|
|
@@ -16614,53 +16691,40 @@ class CropSequenceMapper {
|
|
|
16614
16691
|
type: 'line',
|
|
16615
16692
|
}, StandardLayersMapper.POLYGONS_BACKGROUND);
|
|
16616
16693
|
this._update(this.settings());
|
|
16617
|
-
|
|
16618
|
-
|
|
16694
|
+
}
|
|
16695
|
+
renderPopup(feature) {
|
|
16696
|
+
if (!this.map) {
|
|
16697
|
+
return undefined;
|
|
16619
16698
|
}
|
|
16620
|
-
|
|
16621
|
-
|
|
16622
|
-
}
|
|
16623
|
-
|
|
16624
|
-
|
|
16625
|
-
|
|
16626
|
-
|
|
16627
|
-
|
|
16628
|
-
|
|
16629
|
-
|
|
16630
|
-
|
|
16631
|
-
|
|
16632
|
-
|
|
16633
|
-
|
|
16634
|
-
|
|
16635
|
-
|
|
16636
|
-
|
|
16637
|
-
|
|
16638
|
-
|
|
16639
|
-
|
|
16640
|
-
|
|
16641
|
-
|
|
16642
|
-
|
|
16643
|
-
|
|
16644
|
-
|
|
16645
|
-
|
|
16646
|
-
|
|
16647
|
-
|
|
16648
|
-
|
|
16649
|
-
tb.add('2017', crop2017 ?? 'Unknown');
|
|
16650
|
-
tb.addHeader('Location', "");
|
|
16651
|
-
tb.add('State FIPS', feature.properties ? feature.properties['STATEFIPS'] : 'Unknown');
|
|
16652
|
-
tb.add('County', feature.properties ? feature.properties['CNTY'] : 'Unknown');
|
|
16653
|
-
tb.add('County FIPS', feature.properties ? feature.properties['CNTYFIPS'] : 'Unknown');
|
|
16654
|
-
tb.add('ASD', feature.properties ? feature.properties['ASD'] : 'Unknown');
|
|
16655
|
-
tb.add('Area (M²)', feature.properties ? feature.properties['Shape_Area'] : 'Unknown');
|
|
16656
|
-
const fieldsHtml = tb.toHtml();
|
|
16657
|
-
this.currentFeatureID = feature?.properties?.['globalid'];
|
|
16658
|
-
this.popup = new Popup({ maxWidth: '400px' })
|
|
16659
|
-
.setLngLat(coordinates)
|
|
16660
|
-
.setHTML(`<strong>Crop Sequence</strong><br/>${fieldsHtml}`)
|
|
16661
|
-
.addTo(map);
|
|
16662
|
-
}
|
|
16663
|
-
});
|
|
16699
|
+
if (feature.layer.id !== this.FILL_LAYER_ID && feature.layer.id !== this.LINE_LAYER_ID) {
|
|
16700
|
+
return undefined;
|
|
16701
|
+
}
|
|
16702
|
+
const tb = new TableBuilder();
|
|
16703
|
+
const crop2017 = this.lookupClass(feature.properties ? feature.properties['CDL2017'] : null);
|
|
16704
|
+
const crop2018 = this.lookupClass(feature.properties ? feature.properties['CDL2018'] : null);
|
|
16705
|
+
const crop2019 = this.lookupClass(feature.properties ? feature.properties['CDL2019'] : null);
|
|
16706
|
+
const crop2020 = this.lookupClass(feature.properties ? feature.properties['CDL2020'] : null);
|
|
16707
|
+
const crop2021 = this.lookupClass(feature.properties ? feature.properties['CDL2021'] : null);
|
|
16708
|
+
const crop2022 = this.lookupClass(feature.properties ? feature.properties['CDL2022'] : null);
|
|
16709
|
+
const crop2023 = this.lookupClass(feature.properties ? feature.properties['CDL2023'] : null);
|
|
16710
|
+
const crop2024 = this.lookupClass(feature.properties ? feature.properties['CDL2024'] : null);
|
|
16711
|
+
tb.addHeader('Year', 'Crop Type');
|
|
16712
|
+
tb.add('2024', crop2024 ?? 'Unknown');
|
|
16713
|
+
tb.add('2023', crop2023 ?? 'Unknown');
|
|
16714
|
+
tb.add('2022', crop2022 ?? 'Unknown');
|
|
16715
|
+
tb.add('2021', crop2021 ?? 'Unknown');
|
|
16716
|
+
tb.add('2020', crop2020 ?? 'Unknown');
|
|
16717
|
+
tb.add('2019', crop2019 ?? 'Unknown');
|
|
16718
|
+
tb.add('2018', crop2018 ?? 'Unknown');
|
|
16719
|
+
tb.add('2017', crop2017 ?? 'Unknown');
|
|
16720
|
+
tb.addHeader('Location', "");
|
|
16721
|
+
tb.add('State FIPS', feature.properties ? feature.properties['STATEFIPS'] : 'Unknown');
|
|
16722
|
+
tb.add('County', feature.properties ? feature.properties['CNTY'] : 'Unknown');
|
|
16723
|
+
tb.add('County FIPS', feature.properties ? feature.properties['CNTYFIPS'] : 'Unknown');
|
|
16724
|
+
tb.add('ASD', feature.properties ? feature.properties['ASD'] : 'Unknown');
|
|
16725
|
+
tb.add('Area (M²)', feature.properties ? feature.properties['Shape_Area'] : 'Unknown');
|
|
16726
|
+
const fieldsHtml = tb.toHtml();
|
|
16727
|
+
return fieldsHtml;
|
|
16664
16728
|
}
|
|
16665
16729
|
lookupClass(code) {
|
|
16666
16730
|
const found = CroplandLegend.find((item) => {
|
|
@@ -16693,7 +16757,6 @@ class CropSequenceMapper {
|
|
|
16693
16757
|
count = 0;
|
|
16694
16758
|
total = 0;
|
|
16695
16759
|
map;
|
|
16696
|
-
popup = null;
|
|
16697
16760
|
}
|
|
16698
16761
|
class CropSequenceSettings {
|
|
16699
16762
|
visible = true;
|
|
@@ -16951,10 +17014,10 @@ class FoodhubMapper {
|
|
|
16951
17014
|
RemoveLayer(this.map, this.CIRCLE_LAYER_ID);
|
|
16952
17015
|
RemoveLayer(this.map, this.ICON_LAYER_ID);
|
|
16953
17016
|
RemoveLayer(this.map, this.HEATMAP_LAYER_ID);
|
|
16954
|
-
this.map.off('click', this.CIRCLE_LAYER_ID, this.onClick);
|
|
16955
|
-
this.map.off('click', this.ICON_LAYER_ID, this.onClick);
|
|
16956
|
-
this.map.off('touchend', this.CIRCLE_LAYER_ID, this.onClick);
|
|
16957
|
-
this.map.off('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
17017
|
+
// this.map.off('click', this.CIRCLE_LAYER_ID, this.onClick);
|
|
17018
|
+
// this.map.off('click', this.ICON_LAYER_ID, this.onClick);
|
|
17019
|
+
// this.map.off('touchend', this.CIRCLE_LAYER_ID, this.onClick);
|
|
17020
|
+
// this.map.off('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
16958
17021
|
this.count = 0;
|
|
16959
17022
|
}
|
|
16960
17023
|
updateLegend(settings) {
|
|
@@ -16993,14 +17056,14 @@ class FoodhubMapper {
|
|
|
16993
17056
|
// this.addClusterLayers(map);
|
|
16994
17057
|
}
|
|
16995
17058
|
// Add popup on click
|
|
16996
|
-
this.map.off('click', this.CIRCLE_LAYER_ID, this.onClick);
|
|
16997
|
-
this.map.off('click', this.ICON_LAYER_ID, this.onClick);
|
|
16998
|
-
this.map.off('touchend', this.CIRCLE_LAYER_ID, this.onClick);
|
|
16999
|
-
this.map.off('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
17000
|
-
map.on('click', this.CIRCLE_LAYER_ID, this.onClick);
|
|
17001
|
-
map.on('click', this.ICON_LAYER_ID, this.onClick);
|
|
17002
|
-
map.on('touchend', this.CIRCLE_LAYER_ID, this.onClick);
|
|
17003
|
-
map.on('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
17059
|
+
// this.map.off('click', this.CIRCLE_LAYER_ID, this.onClick);
|
|
17060
|
+
// this.map.off('click', this.ICON_LAYER_ID, this.onClick);
|
|
17061
|
+
// this.map.off('touchend', this.CIRCLE_LAYER_ID, this.onClick);
|
|
17062
|
+
// this.map.off('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
17063
|
+
// map.on('click', this.CIRCLE_LAYER_ID, this.onClick);
|
|
17064
|
+
// map.on('click', this.ICON_LAYER_ID, this.onClick);
|
|
17065
|
+
// map.on('touchend', this.CIRCLE_LAYER_ID, this.onClick);
|
|
17066
|
+
// map.on('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
17004
17067
|
this.filter(map);
|
|
17005
17068
|
untracked(() => this.updateLegend(settings));
|
|
17006
17069
|
}
|
|
@@ -17159,40 +17222,44 @@ class FoodhubMapper {
|
|
|
17159
17222
|
getSettings() {
|
|
17160
17223
|
return { ...this.settings() };
|
|
17161
17224
|
}
|
|
17162
|
-
onClick = (e) => {
|
|
17225
|
+
// onClick = (e: MapLayerMouseEvent | MapLayerTouchEvent) => {
|
|
17226
|
+
// if (!this.map) {
|
|
17227
|
+
// return;
|
|
17228
|
+
// }
|
|
17229
|
+
// const map = this.map;
|
|
17230
|
+
// let features;
|
|
17231
|
+
// const settings = this.settings();
|
|
17232
|
+
// if (settings.type == 'circle') {
|
|
17233
|
+
// features = this.map.queryRenderedFeatures(e.point, {
|
|
17234
|
+
// layers: [this.CIRCLE_LAYER_ID],
|
|
17235
|
+
// });
|
|
17236
|
+
// } else if (settings.type == 'icon') {
|
|
17237
|
+
// features = this.map.queryRenderedFeatures(e.point, {
|
|
17238
|
+
// layers: [this.ICON_LAYER_ID],
|
|
17239
|
+
// });
|
|
17240
|
+
// }
|
|
17241
|
+
// if (!features || features.length == 0) {
|
|
17242
|
+
// return;
|
|
17243
|
+
// }
|
|
17244
|
+
// if (features.length > 0) {
|
|
17245
|
+
// const item = features[0];
|
|
17246
|
+
// if (item) {
|
|
17247
|
+
// console.debug('Rendering Popup for ' + item.id + ' in ' + this.ICON_LAYER_ID);
|
|
17248
|
+
// const html = this.renderPopup(item);
|
|
17249
|
+
// if (!html) {
|
|
17250
|
+
// return;
|
|
17251
|
+
// }
|
|
17252
|
+
// new Popup().setLngLat(e.lngLat).setHTML(html).addTo(map);
|
|
17253
|
+
// }
|
|
17254
|
+
// }
|
|
17255
|
+
// };
|
|
17256
|
+
renderPopup(f) {
|
|
17163
17257
|
if (!this.map) {
|
|
17164
|
-
return;
|
|
17165
|
-
}
|
|
17166
|
-
const map = this.map;
|
|
17167
|
-
let features;
|
|
17168
|
-
const settings = this.settings();
|
|
17169
|
-
if (settings.type == 'circle') {
|
|
17170
|
-
features = this.map.queryRenderedFeatures(e.point, {
|
|
17171
|
-
layers: [this.CIRCLE_LAYER_ID],
|
|
17172
|
-
});
|
|
17173
|
-
}
|
|
17174
|
-
else if (settings.type == 'icon') {
|
|
17175
|
-
features = this.map.queryRenderedFeatures(e.point, {
|
|
17176
|
-
layers: [this.ICON_LAYER_ID],
|
|
17177
|
-
});
|
|
17178
|
-
}
|
|
17179
|
-
if (!features || features.length == 0) {
|
|
17180
|
-
return;
|
|
17258
|
+
return undefined;
|
|
17181
17259
|
}
|
|
17182
|
-
if (
|
|
17183
|
-
|
|
17184
|
-
if (item) {
|
|
17185
|
-
console.debug('Rendering Popup for ' + item.id + ' in ' + this.ICON_LAYER_ID);
|
|
17186
|
-
this.renderPopup(item).then((html) => {
|
|
17187
|
-
if (!html) {
|
|
17188
|
-
return;
|
|
17189
|
-
}
|
|
17190
|
-
new Popup().setLngLat(e.lngLat).setHTML(html).addTo(map);
|
|
17191
|
-
});
|
|
17192
|
-
}
|
|
17260
|
+
if (f.layer.id !== this.CIRCLE_LAYER_ID && f.layer.id !== this.ICON_LAYER_ID && f.layer.id !== this.HEATMAP_LAYER_ID) {
|
|
17261
|
+
return undefined;
|
|
17193
17262
|
}
|
|
17194
|
-
};
|
|
17195
|
-
async renderPopup(f) {
|
|
17196
17263
|
if (!f || !f.properties) {
|
|
17197
17264
|
return undefined;
|
|
17198
17265
|
}
|
|
@@ -17286,36 +17353,27 @@ class HardinessMapper {
|
|
|
17286
17353
|
type: 'fill',
|
|
17287
17354
|
}, StandardLayersMapper.POLYGONS_BACKGROUND);
|
|
17288
17355
|
this._update(this.settings());
|
|
17289
|
-
|
|
17290
|
-
|
|
17291
|
-
|
|
17292
|
-
|
|
17293
|
-
|
|
17294
|
-
|
|
17295
|
-
|
|
17296
|
-
|
|
17297
|
-
|
|
17298
|
-
|
|
17299
|
-
|
|
17300
|
-
|
|
17301
|
-
|
|
17302
|
-
|
|
17303
|
-
if (this.popup) {
|
|
17304
|
-
this.popup.remove();
|
|
17305
|
-
}
|
|
17306
|
-
const fields = feature.properties
|
|
17307
|
-
? Object.entries(feature.properties)
|
|
17308
|
-
.map(([key, value]) => `<strong>${key}:</strong> ${value}`)
|
|
17309
|
-
.join('<br/>')
|
|
17310
|
-
: '';
|
|
17311
|
-
this.currentFeatureID = feature?.properties?.['globalid'];
|
|
17312
|
-
this.popup = new Popup({ maxWidth: '400px' })
|
|
17313
|
-
.setLngLat(coordinates)
|
|
17314
|
-
.setHTML(`<strong>Hardiness:</strong> ${name}<hr /><br/>${fields}`)
|
|
17315
|
-
.addTo(map);
|
|
17316
|
-
}
|
|
17317
|
-
});
|
|
17356
|
+
}
|
|
17357
|
+
renderPopup(feature) {
|
|
17358
|
+
if (!this.map) {
|
|
17359
|
+
return undefined;
|
|
17360
|
+
}
|
|
17361
|
+
if (feature.layer.id !== this.LAYER_ID) {
|
|
17362
|
+
return undefined;
|
|
17363
|
+
}
|
|
17364
|
+
const name = feature.properties
|
|
17365
|
+
? feature.properties['zone']
|
|
17366
|
+
: 'Unknown';
|
|
17367
|
+
// Ensure that if the popup is already open, we don't create a new one
|
|
17368
|
+
if (this.popup) {
|
|
17369
|
+
this.popup.remove();
|
|
17318
17370
|
}
|
|
17371
|
+
const fields = feature.properties
|
|
17372
|
+
? Object.entries(feature.properties)
|
|
17373
|
+
.map(([key, value]) => `<strong>${key}:</strong> ${value}`)
|
|
17374
|
+
.join('<br/>')
|
|
17375
|
+
: '';
|
|
17376
|
+
return `<strong>Hardiness:</strong> ${name}<hr /><br/>${fields}`;
|
|
17319
17377
|
}
|
|
17320
17378
|
update(newSettings) {
|
|
17321
17379
|
this.settings.set({ ...this.settings(), ...newSettings });
|
|
@@ -21357,8 +21415,8 @@ class NAASMapper {
|
|
|
21357
21415
|
return ds.name;
|
|
21358
21416
|
}
|
|
21359
21417
|
if (ds) {
|
|
21360
|
-
const commodity = DataSetFieldValue(ds, -1, "COMMODITY_DESC") || 'UNKNOWN';
|
|
21361
|
-
const year = DataSetFieldValue(ds, -1, "YEAR");
|
|
21418
|
+
const commodity = DataSetFieldValue$1(ds, -1, "COMMODITY_DESC") || 'UNKNOWN';
|
|
21419
|
+
const year = DataSetFieldValue$1(ds, -1, "YEAR");
|
|
21362
21420
|
if (year) {
|
|
21363
21421
|
return `${commodity} (${year})`;
|
|
21364
21422
|
}
|
|
@@ -21378,8 +21436,8 @@ class NAASMapper {
|
|
|
21378
21436
|
return ds.name;
|
|
21379
21437
|
}
|
|
21380
21438
|
if (ds) {
|
|
21381
|
-
const commodity = DataSetFieldValue(ds, -1, "PRODN_PRACTICE_DESC") || '';
|
|
21382
|
-
const units = DataSetFieldValue(ds, -1, "UNIT_DESC") || '';
|
|
21439
|
+
const commodity = DataSetFieldValue$1(ds, -1, "PRODN_PRACTICE_DESC") || '';
|
|
21440
|
+
const units = DataSetFieldValue$1(ds, -1, "UNIT_DESC") || '';
|
|
21383
21441
|
return `${commodity} (${units})`;
|
|
21384
21442
|
}
|
|
21385
21443
|
return 'NASS Data';
|
|
@@ -21418,7 +21476,7 @@ class NAASMapper {
|
|
|
21418
21476
|
if (!row || !row.cells) {
|
|
21419
21477
|
continue;
|
|
21420
21478
|
}
|
|
21421
|
-
const fips = FipsFromDataSet(dataSet, i);
|
|
21479
|
+
const fips = FipsFromDataSet$1(dataSet, i);
|
|
21422
21480
|
if (!fips || fips.endsWith("998") || fips.endsWith("999")) {
|
|
21423
21481
|
// Skip invalid or unknown FIPS
|
|
21424
21482
|
continue;
|
|
@@ -21541,8 +21599,6 @@ class NAASMapper {
|
|
|
21541
21599
|
visibility: 'none',
|
|
21542
21600
|
},
|
|
21543
21601
|
}, StandardLayersMapper.POLYGONS_BACKGROUND);
|
|
21544
|
-
map.off('click', this.LAYER_ID, this.onClick);
|
|
21545
|
-
map.on('click', this.LAYER_ID, this.onClick);
|
|
21546
21602
|
}
|
|
21547
21603
|
setFeatureStates(settings, fs) {
|
|
21548
21604
|
if (!this.map) {
|
|
@@ -21661,76 +21717,72 @@ class NAASMapper {
|
|
|
21661
21717
|
}
|
|
21662
21718
|
clear() {
|
|
21663
21719
|
if (this.map) {
|
|
21664
|
-
this.map.off('click', this.LAYER_ID, this.onClick);
|
|
21665
21720
|
RemoveLayer(this.map, this.LAYER_ID);
|
|
21666
21721
|
RemoveLayer(this.map, this.SOURCE_ID);
|
|
21667
21722
|
}
|
|
21668
21723
|
}
|
|
21669
|
-
|
|
21724
|
+
renderPopup(feature) {
|
|
21725
|
+
// Determine if this is mine
|
|
21670
21726
|
if (!this.map) {
|
|
21671
|
-
return;
|
|
21727
|
+
return undefined;
|
|
21728
|
+
}
|
|
21729
|
+
if (feature.layer.id !== this.LAYER_ID) {
|
|
21730
|
+
return undefined;
|
|
21672
21731
|
}
|
|
21673
21732
|
const settings = this.settings();
|
|
21674
21733
|
const src = Layers.FindVector(settings.areaType);
|
|
21675
21734
|
if (!src) {
|
|
21676
21735
|
console.warn('ChoroplethMapper: No source found for area type ', settings.areaType);
|
|
21677
|
-
return;
|
|
21736
|
+
return undefined;
|
|
21678
21737
|
}
|
|
21679
|
-
const
|
|
21680
|
-
|
|
21738
|
+
const state = this.map.getFeatureState({
|
|
21739
|
+
source: this.SOURCE_ID,
|
|
21740
|
+
sourceLayer: src.Source,
|
|
21741
|
+
id: feature.id
|
|
21681
21742
|
});
|
|
21682
|
-
|
|
21683
|
-
|
|
21684
|
-
if (this.current) {
|
|
21685
|
-
this.current.remove();
|
|
21686
|
-
this.current = null;
|
|
21687
|
-
}
|
|
21688
|
-
const f = features[0];
|
|
21689
|
-
const state = this.map.getFeatureState({
|
|
21690
|
-
source: this.SOURCE_ID,
|
|
21691
|
-
sourceLayer: src.Source,
|
|
21692
|
-
id: f.id
|
|
21693
|
-
});
|
|
21694
|
-
const html = await this.RenderPopup(f, state);
|
|
21695
|
-
if (html) {
|
|
21696
|
-
this.current = new Popup().setLngLat(e.lngLat).setHTML(html).addTo(this.map);
|
|
21697
|
-
}
|
|
21698
|
-
}
|
|
21699
|
-
};
|
|
21743
|
+
return this.RenderPopup(feature, state);
|
|
21744
|
+
}
|
|
21700
21745
|
RenderPopup(feature, state) {
|
|
21701
21746
|
const nState = state;
|
|
21702
21747
|
if (!nState) {
|
|
21703
|
-
return
|
|
21748
|
+
return undefined;
|
|
21704
21749
|
}
|
|
21705
21750
|
const ds = nState.dataset;
|
|
21706
21751
|
if (!ds) {
|
|
21707
|
-
return
|
|
21752
|
+
return undefined;
|
|
21708
21753
|
}
|
|
21709
21754
|
const tab = new TableBuilder();
|
|
21710
|
-
tab.add("Source", DataSetFieldValue(ds, nState.row, "SOURCE_DESC") || "");
|
|
21711
|
-
tab.add("Sector", DataSetFieldValue(ds, nState.row, "SECTOR_DESC") || "");
|
|
21712
|
-
tab.add("Group", DataSetFieldValue(ds, nState.row, "GROUP_DESC") || "");
|
|
21713
|
-
tab.add("Commodity", DataSetFieldValue(ds, nState.row, "COMMODITY_DESC") || "");
|
|
21714
|
-
tab.add("Production", DataSetFieldValue(ds, nState.row, "PRODN_PRACTICE_DESC") || "");
|
|
21715
|
-
tab.add("Utilization", DataSetFieldValue(ds, nState.row, "UTIL_PRACTICE_DESC") || "");
|
|
21716
|
-
tab.add("Statistic", DataSetFieldValue(ds, nState.row, "STATISTICCAT_DESC") || "");
|
|
21717
|
-
tab.add("Unit", DataSetFieldValue(ds, nState.row, "UNIT_DESC") || "");
|
|
21718
|
-
tab.add("State", DataSetFieldValue(ds, nState.row, "STATE_ABBR") || "")
|
|
21719
|
-
tab.add("County", DataSetFieldValue(ds, nState.row, "COUNTY_CODE") || "")
|
|
21720
|
-
tab.add("Year", DataSetFieldValue(ds, nState.row, "YEAR") || "")
|
|
21721
|
-
tab.add("Value", nState?.value)
|
|
21722
|
-
|
|
21723
|
-
|
|
21724
|
-
|
|
21725
|
-
|
|
21755
|
+
tab.add("Source", DataSetFieldValue$1(ds, nState.row, "SOURCE_DESC") || "");
|
|
21756
|
+
tab.add("Sector", DataSetFieldValue$1(ds, nState.row, "SECTOR_DESC") || "");
|
|
21757
|
+
tab.add("Group", DataSetFieldValue$1(ds, nState.row, "GROUP_DESC") || "");
|
|
21758
|
+
tab.add("Commodity", DataSetFieldValue$1(ds, nState.row, "COMMODITY_DESC") || "");
|
|
21759
|
+
tab.add("Production", DataSetFieldValue$1(ds, nState.row, "PRODN_PRACTICE_DESC") || "");
|
|
21760
|
+
tab.add("Utilization", DataSetFieldValue$1(ds, nState.row, "UTIL_PRACTICE_DESC") || "");
|
|
21761
|
+
tab.add("Statistic", DataSetFieldValue$1(ds, nState.row, "STATISTICCAT_DESC") || "");
|
|
21762
|
+
tab.add("Unit", DataSetFieldValue$1(ds, nState.row, "UNIT_DESC") || "");
|
|
21763
|
+
// tab.add("State", DataSetFieldValue(ds, nState.row, "STATE_ABBR") || "")
|
|
21764
|
+
// tab.add("County", DataSetFieldValue(ds, nState.row, "COUNTY_CODE") || "")
|
|
21765
|
+
// tab.add("Year", DataSetFieldValue(ds, nState.row, "YEAR") || "")
|
|
21766
|
+
// tab.add("Value", nState?.value)
|
|
21767
|
+
if (nState.raw !== undefined) {
|
|
21768
|
+
tab.add("Value", nState.raw.toLocaleString());
|
|
21769
|
+
}
|
|
21770
|
+
if (nState.min !== undefined) {
|
|
21771
|
+
tab.add("MIN Value", nState.min.toLocaleString());
|
|
21772
|
+
}
|
|
21773
|
+
if (nState.max !== undefined) {
|
|
21774
|
+
tab.add("MAX Value", nState.max.toLocaleString());
|
|
21775
|
+
}
|
|
21776
|
+
tab.add("GEOID", nState.id);
|
|
21777
|
+
return tab.toHtml();
|
|
21726
21778
|
}
|
|
21727
21779
|
}
|
|
21728
|
-
function FipsFromDataSet(ds, rowIndex) {
|
|
21780
|
+
function FipsFromDataSet$1(ds, rowIndex) {
|
|
21729
21781
|
if (!ds.schema || !ds.schema.fields) {
|
|
21730
21782
|
return null;
|
|
21731
21783
|
}
|
|
21732
|
-
const state = DataSetFieldValue(ds, rowIndex, "STATE_FIPS_CODE");
|
|
21733
|
-
const county = DataSetFieldValue(ds, rowIndex, "COUNTY_CODE");
|
|
21784
|
+
const state = DataSetFieldValue$1(ds, rowIndex, "STATE_FIPS_CODE");
|
|
21785
|
+
const county = DataSetFieldValue$1(ds, rowIndex, "COUNTY_CODE");
|
|
21734
21786
|
if (county) {
|
|
21735
21787
|
return county;
|
|
21736
21788
|
}
|
|
@@ -21739,7 +21791,7 @@ function FipsFromDataSet(ds, rowIndex) {
|
|
|
21739
21791
|
}
|
|
21740
21792
|
return null;
|
|
21741
21793
|
}
|
|
21742
|
-
function DataSetFieldValue(ds, rowIndex, field) {
|
|
21794
|
+
function DataSetFieldValue$1(ds, rowIndex, field) {
|
|
21743
21795
|
if (!ds.schema || !ds.data) {
|
|
21744
21796
|
return null;
|
|
21745
21797
|
}
|
|
@@ -22059,10 +22111,6 @@ class NaicsMapper {
|
|
|
22059
22111
|
RemoveLayer(this.map, this.CIRCLE_LAYER_ID);
|
|
22060
22112
|
RemoveLayer(this.map, this.ICON_LAYER_ID);
|
|
22061
22113
|
RemoveLayer(this.map, this.HEATMAP_LAYER_ID);
|
|
22062
|
-
this.map.off('click', this.CIRCLE_LAYER_ID, this.onClick);
|
|
22063
|
-
this.map.off('click', this.ICON_LAYER_ID, this.onClick);
|
|
22064
|
-
this.map.off('touchend', this.CIRCLE_LAYER_ID, this.onClick);
|
|
22065
|
-
this.map.off('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
22066
22114
|
const svc = this.svc();
|
|
22067
22115
|
if (svc) {
|
|
22068
22116
|
svc.UpdateLegend(this.id, undefined);
|
|
@@ -22140,15 +22188,6 @@ class NaicsMapper {
|
|
|
22140
22188
|
// this.addClusterLayers(map);
|
|
22141
22189
|
}
|
|
22142
22190
|
console.log('NAICS Mapper created/updated:', this.id, settings);
|
|
22143
|
-
// Add popup on click
|
|
22144
|
-
this.map.off('click', this.CIRCLE_LAYER_ID, this.onClick);
|
|
22145
|
-
this.map.off('click', this.ICON_LAYER_ID, this.onClick);
|
|
22146
|
-
this.map.off('touchend', this.CIRCLE_LAYER_ID, this.onClick);
|
|
22147
|
-
this.map.off('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
22148
|
-
map.on('click', this.CIRCLE_LAYER_ID, this.onClick);
|
|
22149
|
-
map.on('click', this.ICON_LAYER_ID, this.onClick);
|
|
22150
|
-
map.on('touchend', this.CIRCLE_LAYER_ID, this.onClick);
|
|
22151
|
-
map.on('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
22152
22191
|
this.filter(map, settings);
|
|
22153
22192
|
untracked(() => this.updateLegend(settings));
|
|
22154
22193
|
}
|
|
@@ -22372,37 +22411,16 @@ class NaicsMapper {
|
|
|
22372
22411
|
zoom: 12,
|
|
22373
22412
|
});
|
|
22374
22413
|
}
|
|
22375
|
-
|
|
22376
|
-
if (!this.map) {
|
|
22377
|
-
return;
|
|
22378
|
-
}
|
|
22379
|
-
const map = this.map;
|
|
22380
|
-
let features;
|
|
22381
|
-
const settings = this.settings();
|
|
22382
|
-
if (settings.type == 'circle') {
|
|
22383
|
-
features = this.map.queryRenderedFeatures(e.point, {
|
|
22384
|
-
layers: [this.CIRCLE_LAYER_ID],
|
|
22385
|
-
});
|
|
22386
|
-
}
|
|
22387
|
-
else if (settings.type == 'icon') {
|
|
22388
|
-
features = this.map.queryRenderedFeatures(e.point, {
|
|
22389
|
-
layers: [this.ICON_LAYER_ID],
|
|
22390
|
-
});
|
|
22391
|
-
}
|
|
22392
|
-
if (!features || features.length == 0) {
|
|
22393
|
-
return;
|
|
22394
|
-
}
|
|
22395
|
-
e.preventDefault();
|
|
22396
|
-
if (this.current) {
|
|
22397
|
-
this.current.remove();
|
|
22398
|
-
this.current = null;
|
|
22414
|
+
renderPopup(f) {
|
|
22415
|
+
if (!this.map || !f || !f.layer) {
|
|
22416
|
+
return undefined;
|
|
22399
22417
|
}
|
|
22400
|
-
|
|
22401
|
-
|
|
22402
|
-
this.current = new Popup().setLngLat(e.lngLat).setHTML(html).addTo(this.map);
|
|
22418
|
+
if (f.layer.id !== this.CIRCLE_LAYER_ID && f.layer.id !== this.ICON_LAYER_ID && f.layer.id !== this.HEATMAP_LAYER_ID) {
|
|
22419
|
+
return undefined;
|
|
22403
22420
|
}
|
|
22404
|
-
|
|
22405
|
-
|
|
22421
|
+
return this.renderInfo(f);
|
|
22422
|
+
}
|
|
22423
|
+
renderInfo(f) {
|
|
22406
22424
|
if (!f || !f.properties) {
|
|
22407
22425
|
return undefined;
|
|
22408
22426
|
}
|
|
@@ -23845,6 +23863,7 @@ class PointDataMapperSettings {
|
|
|
23845
23863
|
filterState;
|
|
23846
23864
|
filterStates = [];
|
|
23847
23865
|
showLegend = false;
|
|
23866
|
+
externalLoad = true; // If true, the mapper will load data from the provided source URL instead of relying on mapbox source loading. This allows for better handling of large datasets and loading states.
|
|
23848
23867
|
}
|
|
23849
23868
|
class PointDataMapper {
|
|
23850
23869
|
static CLUSTERS = [
|
|
@@ -23885,6 +23904,7 @@ class PointDataMapper {
|
|
|
23885
23904
|
itemsFC;
|
|
23886
23905
|
popupRenderer;
|
|
23887
23906
|
id;
|
|
23907
|
+
watcher = new SourceLoadWatcher();
|
|
23888
23908
|
POINT_LAYER_ID;
|
|
23889
23909
|
HEAT_LAYER_ID;
|
|
23890
23910
|
ICON_LAYER_ID;
|
|
@@ -23897,6 +23917,7 @@ class PointDataMapper {
|
|
|
23897
23917
|
return settings.source;
|
|
23898
23918
|
}, ...(ngDevMode ? [{ debugName: "geoJsonUrl" }] : []));
|
|
23899
23919
|
geoJsonResource = httpResource(() => this.geoJsonUrl() || undefined);
|
|
23920
|
+
dataCnt = 0;
|
|
23900
23921
|
constructor(popupRenderer, settings) {
|
|
23901
23922
|
this.id = 'points-' + Math.random().toString(36).substring(2, 15);
|
|
23902
23923
|
this.popupRenderer = popupRenderer;
|
|
@@ -23932,34 +23953,56 @@ class PointDataMapper {
|
|
|
23932
23953
|
this._update(this.settings());
|
|
23933
23954
|
}, ...(ngDevMode ? [{ debugName: "_updateGlobal" }] : []));
|
|
23934
23955
|
}
|
|
23935
|
-
|
|
23936
|
-
|
|
23937
|
-
|
|
23938
|
-
|
|
23939
|
-
|
|
23940
|
-
|
|
23941
|
-
|
|
23942
|
-
|
|
23943
|
-
|
|
23944
|
-
|
|
23945
|
-
|
|
23946
|
-
|
|
23947
|
-
|
|
23948
|
-
|
|
23949
|
-
|
|
23950
|
-
|
|
23951
|
-
|
|
23952
|
-
|
|
23953
|
-
|
|
23954
|
-
|
|
23955
|
-
|
|
23956
|
-
|
|
23957
|
-
|
|
23958
|
-
|
|
23959
|
-
|
|
23960
|
-
|
|
23961
|
-
|
|
23962
|
-
|
|
23956
|
+
data = computed(() => {
|
|
23957
|
+
this.dataCnt++;
|
|
23958
|
+
this.watcher.updated(); // depend on source data changes
|
|
23959
|
+
const settings = this.settings();
|
|
23960
|
+
console.log('Data computed for', this.id, 'count', this.dataCnt);
|
|
23961
|
+
if (!this.map) {
|
|
23962
|
+
return [];
|
|
23963
|
+
}
|
|
23964
|
+
const map = this.map;
|
|
23965
|
+
const filter = this.getFilter(settings);
|
|
23966
|
+
if (settings.externalLoad) {
|
|
23967
|
+
// Check if data is still loading or has an error
|
|
23968
|
+
if (this.geoJsonResource.isLoading()) {
|
|
23969
|
+
return [];
|
|
23970
|
+
}
|
|
23971
|
+
if (this.geoJsonResource.error()) {
|
|
23972
|
+
console.error('Failed to load GeoJSON:', this.geoJsonResource.error());
|
|
23973
|
+
return [];
|
|
23974
|
+
}
|
|
23975
|
+
// Check if we have loaded data
|
|
23976
|
+
if (!this.geoJsonResource.hasValue()) {
|
|
23977
|
+
return [];
|
|
23978
|
+
}
|
|
23979
|
+
const geoJsonData = this.geoJsonResource.value();
|
|
23980
|
+
const features = geoJsonData?.features || [];
|
|
23981
|
+
if (!features || features.length === 0) {
|
|
23982
|
+
return [];
|
|
23983
|
+
}
|
|
23984
|
+
const filtered = Filter(features, filter);
|
|
23985
|
+
return filtered || [];
|
|
23986
|
+
}
|
|
23987
|
+
else {
|
|
23988
|
+
const features = map.querySourceFeatures(this.id, {
|
|
23989
|
+
filter: filter ? filter : undefined,
|
|
23990
|
+
});
|
|
23991
|
+
return features || [];
|
|
23992
|
+
}
|
|
23993
|
+
}, ...(ngDevMode ? [{ debugName: "data" }] : []));
|
|
23994
|
+
renderPopup(f) {
|
|
23995
|
+
if (!this.map) {
|
|
23996
|
+
return undefined;
|
|
23997
|
+
}
|
|
23998
|
+
if (f.layer.id !== this.HEAT_LAYER_ID && f.layer.id !== this.ICON_LAYER_ID && f.layer.id !== this.POINT_LAYER_ID) {
|
|
23999
|
+
return undefined;
|
|
24000
|
+
}
|
|
24001
|
+
if (this.popupRenderer) {
|
|
24002
|
+
return this.popupRenderer.RenderPopup(f);
|
|
24003
|
+
}
|
|
24004
|
+
return undefined;
|
|
24005
|
+
}
|
|
23963
24006
|
update(settings) {
|
|
23964
24007
|
this.settings.set({ ...this.settings(), ...settings });
|
|
23965
24008
|
}
|
|
@@ -24039,7 +24082,7 @@ class PointDataMapper {
|
|
|
24039
24082
|
getFilter(settings) {
|
|
24040
24083
|
// Build filter conditions for each field
|
|
24041
24084
|
const conditions = ['all'];
|
|
24042
|
-
const fipsFilter = this.getFipsFilter();
|
|
24085
|
+
const fipsFilter = this.getFipsFilter(settings);
|
|
24043
24086
|
if (fipsFilter && fipsFilter.length > 0) {
|
|
24044
24087
|
const filter = [
|
|
24045
24088
|
'any',
|
|
@@ -24068,6 +24111,7 @@ class PointDataMapper {
|
|
|
24068
24111
|
}
|
|
24069
24112
|
onReady(map, svc) {
|
|
24070
24113
|
this.map = map;
|
|
24114
|
+
this.watcher.on(map, this.id);
|
|
24071
24115
|
this.svc.set(svc);
|
|
24072
24116
|
this.loadSource();
|
|
24073
24117
|
}
|
|
@@ -24094,10 +24138,10 @@ class PointDataMapper {
|
|
|
24094
24138
|
RemoveLayer(this.map, c.iconLayer);
|
|
24095
24139
|
}
|
|
24096
24140
|
}
|
|
24097
|
-
this.map.off('click', this.POINT_LAYER_ID, this.onClick);
|
|
24098
|
-
this.map.off('touchend', this.POINT_LAYER_ID, this.onClick);
|
|
24099
|
-
this.map.off('click', this.ICON_LAYER_ID, this.onClick);
|
|
24100
|
-
this.map.off('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
24141
|
+
// this.map.off('click', this.POINT_LAYER_ID, this.onClick);
|
|
24142
|
+
// this.map.off('touchend', this.POINT_LAYER_ID, this.onClick);
|
|
24143
|
+
// this.map.off('click', this.ICON_LAYER_ID, this.onClick);
|
|
24144
|
+
// this.map.off('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
24101
24145
|
RemoveSource(this.map, `${this.id}-source`);
|
|
24102
24146
|
}
|
|
24103
24147
|
loadSource() {
|
|
@@ -24117,17 +24161,16 @@ class PointDataMapper {
|
|
|
24117
24161
|
type: 'geojson',
|
|
24118
24162
|
data: sourceURL,
|
|
24119
24163
|
});
|
|
24120
|
-
map.on('click', this.POINT_LAYER_ID, this.onClick);
|
|
24121
|
-
map.on('touchend', this.POINT_LAYER_ID, this.onClick);
|
|
24122
|
-
map.on('click', this.ICON_LAYER_ID, this.onClick);
|
|
24123
|
-
map.on('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
24164
|
+
// map.on('click', this.POINT_LAYER_ID, this.onClick);
|
|
24165
|
+
// map.on('touchend', this.POINT_LAYER_ID, this.onClick);
|
|
24166
|
+
// map.on('click', this.ICON_LAYER_ID, this.onClick);
|
|
24167
|
+
// map.on('touchend', this.ICON_LAYER_ID, this.onClick);
|
|
24124
24168
|
}
|
|
24125
24169
|
else if (currentSource._data !== sourceURL) {
|
|
24126
24170
|
currentSource.setData(sourceURL);
|
|
24127
24171
|
}
|
|
24128
24172
|
}
|
|
24129
|
-
getFipsFilter() {
|
|
24130
|
-
const settings = this.settings();
|
|
24173
|
+
getFipsFilter(settings) {
|
|
24131
24174
|
if (settings.filterOverrideGlobal) {
|
|
24132
24175
|
if (settings.filterStates && settings.filterStates.length > 0) {
|
|
24133
24176
|
return settings.filterStates;
|
|
@@ -24312,32 +24355,31 @@ class PointDataMapper {
|
|
|
24312
24355
|
}, StandardLayersMapper.POINTS);
|
|
24313
24356
|
});
|
|
24314
24357
|
}
|
|
24315
|
-
onClick = async (e) => {
|
|
24316
|
-
|
|
24317
|
-
|
|
24318
|
-
|
|
24319
|
-
|
|
24320
|
-
|
|
24321
|
-
|
|
24322
|
-
|
|
24323
|
-
|
|
24324
|
-
|
|
24325
|
-
|
|
24326
|
-
|
|
24327
|
-
|
|
24328
|
-
|
|
24329
|
-
|
|
24330
|
-
|
|
24331
|
-
|
|
24332
|
-
|
|
24333
|
-
|
|
24334
|
-
|
|
24335
|
-
|
|
24336
|
-
|
|
24337
|
-
|
|
24338
|
-
|
|
24339
|
-
|
|
24340
|
-
};
|
|
24358
|
+
// onClick = async (e: MapLayerMouseEvent | MapLayerTouchEvent) => {
|
|
24359
|
+
// if (!this.map) {
|
|
24360
|
+
// return;
|
|
24361
|
+
// }
|
|
24362
|
+
// let features: GeoJSON.Feature[] = [];
|
|
24363
|
+
// const settings = this.settings();
|
|
24364
|
+
// if (settings.type == 'circle') {
|
|
24365
|
+
// features = this.map.queryRenderedFeatures(e.point, { layers: [this.POINT_LAYER_ID] });
|
|
24366
|
+
// } else if (settings.type == 'icon') {
|
|
24367
|
+
// features = this.map.queryRenderedFeatures(e.point, { layers: [this.ICON_LAYER_ID] });
|
|
24368
|
+
// }
|
|
24369
|
+
// if (!features || features.length == 0) {
|
|
24370
|
+
// return;
|
|
24371
|
+
// }
|
|
24372
|
+
// if (this.current) {
|
|
24373
|
+
// this.current.remove();
|
|
24374
|
+
// this.current = null;
|
|
24375
|
+
// }
|
|
24376
|
+
// if (this.popupRenderer) {
|
|
24377
|
+
// const html = await this.popupRenderer.RenderPopup(features[0]);
|
|
24378
|
+
// if (html) {
|
|
24379
|
+
// this.current = new Popup().setLngLat(e.lngLat).setHTML(html).addTo(this.map);
|
|
24380
|
+
// }
|
|
24381
|
+
// }
|
|
24382
|
+
// };
|
|
24341
24383
|
getSettings() {
|
|
24342
24384
|
return { ...this.settings() };
|
|
24343
24385
|
}
|
|
@@ -24442,40 +24484,30 @@ class RailroadsMapper {
|
|
|
24442
24484
|
console.warn('RailroadsMapper: style has no `glyphs` URL — skipping labels layer to avoid PBF/glyph parse errors. Switch to a style with glyphs to enable labels.');
|
|
24443
24485
|
}
|
|
24444
24486
|
this._update(this.settings());
|
|
24445
|
-
|
|
24446
|
-
|
|
24487
|
+
}
|
|
24488
|
+
renderPopup(feature) {
|
|
24489
|
+
if (!this.map) {
|
|
24490
|
+
return undefined;
|
|
24447
24491
|
}
|
|
24448
|
-
|
|
24449
|
-
|
|
24450
|
-
|
|
24451
|
-
|
|
24452
|
-
|
|
24453
|
-
|
|
24454
|
-
|
|
24455
|
-
|
|
24456
|
-
|
|
24457
|
-
|
|
24458
|
-
|
|
24459
|
-
|
|
24460
|
-
|
|
24461
|
-
|
|
24462
|
-
|
|
24463
|
-
|
|
24464
|
-
|
|
24465
|
-
|
|
24466
|
-
|
|
24467
|
-
let html = "";
|
|
24468
|
-
if (name) {
|
|
24469
|
-
html += `<strong>${name}</strong><br/>`;
|
|
24470
|
-
}
|
|
24471
|
-
html += fieldsHtml;
|
|
24472
|
-
this.currentFeatureID = feature?.properties?.['globalid'];
|
|
24473
|
-
this.popup = new Popup({ maxWidth: '400px' })
|
|
24474
|
-
.setLngLat(coordinates)
|
|
24475
|
-
.setHTML(html)
|
|
24476
|
-
.addTo(map);
|
|
24477
|
-
}
|
|
24478
|
-
});
|
|
24492
|
+
if (feature.layer.id !== this.LINE_LAYER_ID && feature.layer.id !== this.LABEL_LAYER_ID) {
|
|
24493
|
+
return undefined;
|
|
24494
|
+
}
|
|
24495
|
+
const name = feature.properties['name'];
|
|
24496
|
+
const tb = new TableBuilder();
|
|
24497
|
+
tb.add('Length', this.fmtDistance(feature.properties['lengthkm']));
|
|
24498
|
+
tb.add('Owner', feature.properties['railowner'] ?? '');
|
|
24499
|
+
tb.add('Owner Code', feature.properties['railownercode'] ?? '');
|
|
24500
|
+
tb.add('Usage', this.usageLabel(feature.properties['railusage'] ?? 0));
|
|
24501
|
+
tb.add('Source', feature.properties['source_datadesc'] ?? '');
|
|
24502
|
+
tb.add('Originator', feature.properties['source_originator'] ?? '');
|
|
24503
|
+
tb.add('Load Date', feature.properties['loaddate'] ?? '');
|
|
24504
|
+
const fieldsHtml = tb.toHtml();
|
|
24505
|
+
let html = "";
|
|
24506
|
+
if (name) {
|
|
24507
|
+
html += `<strong>${name}</strong><br/>`;
|
|
24508
|
+
}
|
|
24509
|
+
html += fieldsHtml;
|
|
24510
|
+
return html;
|
|
24479
24511
|
}
|
|
24480
24512
|
fmtDistance(km) {
|
|
24481
24513
|
if (!km) {
|
|
@@ -25023,42 +25055,34 @@ class WatershedMapper {
|
|
|
25023
25055
|
}
|
|
25024
25056
|
}
|
|
25025
25057
|
});
|
|
25026
|
-
map.on('mousemove', this.FILL_LAYER_ID, (e) => {
|
|
25027
|
-
this.over.set(e.features && e.features.length > 0 ? e.features[0] : null);
|
|
25028
|
-
});
|
|
25029
|
-
map.on('click', this.FILL_LAYER_ID, (e) => {
|
|
25030
|
-
// Publish
|
|
25031
|
-
this.over.set(e.features && e.features.length > 0 ? e.features[0] : null);
|
|
25032
|
-
if (e.features && e.features.length > 0) {
|
|
25033
|
-
const feature = e.features[0];
|
|
25034
|
-
const coordinates = e.lngLat;
|
|
25035
|
-
console.log('Feature properties:', feature.properties);
|
|
25036
|
-
const name = feature.properties
|
|
25037
|
-
? feature.properties['name']
|
|
25038
|
-
: 'Unknown';
|
|
25039
|
-
// Ensure that if the popup is already open, we don't create a new one
|
|
25040
|
-
if (this.popup) {
|
|
25041
|
-
this.popup.remove();
|
|
25042
|
-
}
|
|
25043
|
-
const fields = feature.properties
|
|
25044
|
-
? Object.entries(feature.properties)
|
|
25045
|
-
.map(([key, value]) => `<strong>${key}:</strong> ${value}`)
|
|
25046
|
-
.join('<br/>')
|
|
25047
|
-
: '';
|
|
25048
|
-
this.currentFeatureID = feature?.properties?.['globalid'];
|
|
25049
|
-
this.popup = new Popup({ maxWidth: '400px' })
|
|
25050
|
-
.setLngLat(coordinates)
|
|
25051
|
-
.setHTML(`<strong>Watershed:</strong> ${name}<hr /><br/>${fields}`)
|
|
25052
|
-
.addTo(map);
|
|
25053
|
-
}
|
|
25054
|
-
});
|
|
25055
|
-
}
|
|
25056
|
-
async onReady(map, svc) {
|
|
25057
|
-
this.map = map;
|
|
25058
|
-
this.create();
|
|
25059
25058
|
}
|
|
25060
|
-
|
|
25061
|
-
|
|
25059
|
+
renderPopup(feature) {
|
|
25060
|
+
if (!this.map) {
|
|
25061
|
+
return undefined;
|
|
25062
|
+
}
|
|
25063
|
+
if (feature.layer.id !== this.FILL_LAYER_ID && feature.layer.id !== this.LINE_LAYER_ID && feature.layer.id !== this.LABEL_LAYER_ID) {
|
|
25064
|
+
return undefined;
|
|
25065
|
+
}
|
|
25066
|
+
const name = feature.properties
|
|
25067
|
+
? feature.properties['name']
|
|
25068
|
+
: 'Unknown';
|
|
25069
|
+
// Ensure that if the popup is already open, we don't create a new one
|
|
25070
|
+
if (this.popup) {
|
|
25071
|
+
this.popup.remove();
|
|
25072
|
+
}
|
|
25073
|
+
const fields = feature.properties
|
|
25074
|
+
? Object.entries(feature.properties)
|
|
25075
|
+
.map(([key, value]) => `<strong>${key}:</strong> ${value}`)
|
|
25076
|
+
.join('<br/>')
|
|
25077
|
+
: '';
|
|
25078
|
+
return `<strong>Watershed:</strong> ${name}<hr /><br/>${fields}`;
|
|
25079
|
+
}
|
|
25080
|
+
async onReady(map, svc) {
|
|
25081
|
+
this.map = map;
|
|
25082
|
+
this.create();
|
|
25083
|
+
}
|
|
25084
|
+
reset() { }
|
|
25085
|
+
clear() {
|
|
25062
25086
|
if (this.map) {
|
|
25063
25087
|
this.map.removeLayer(this.FILL_LAYER_ID);
|
|
25064
25088
|
this.map.removeLayer(this.LINE_LAYER_ID);
|
|
@@ -25637,31 +25661,1491 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImpo
|
|
|
25637
25661
|
` }]
|
|
25638
25662
|
}] });
|
|
25639
25663
|
|
|
25640
|
-
|
|
25641
|
-
|
|
25642
|
-
|
|
25643
|
-
|
|
25644
|
-
|
|
25645
|
-
|
|
25646
|
-
|
|
25664
|
+
function ConsumerSpendingFromPath(path) {
|
|
25665
|
+
const parts = path.split('/');
|
|
25666
|
+
if (parts.length < 3) {
|
|
25667
|
+
throw new Error('Invalid path format');
|
|
25668
|
+
}
|
|
25669
|
+
const year = parts[0];
|
|
25670
|
+
const measure = parts[1];
|
|
25671
|
+
const valueType = parts[2];
|
|
25672
|
+
// A = Avgerage Spending, T = Total Spending, I = Index
|
|
25673
|
+
// Year/Measure/(A|T|I)
|
|
25674
|
+
return { measure, year, valueType };
|
|
25675
|
+
}
|
|
25676
|
+
|
|
25677
|
+
/**
|
|
25678
|
+
* The DataSetMapper is responsible for making a Choropleth Map with
|
|
25679
|
+
* a single DataSet dataset.
|
|
25680
|
+
*/
|
|
25681
|
+
class DataSetMapper {
|
|
25682
|
+
http = inject(HttpClient);
|
|
25683
|
+
ID = Math.random().toString(36).substring(2, 15);
|
|
25684
|
+
LAYER_ID = 'naas-layer-fill-' + this.ID;
|
|
25685
|
+
SOURCE_ID = 'naas-source-' + this.ID;
|
|
25686
|
+
settings = signal(new DataSetSettings(), ...(ngDevMode ? [{ debugName: "settings" }] : []));
|
|
25687
|
+
current = null;
|
|
25688
|
+
currentFeatureID = undefined;
|
|
25689
|
+
over = signal(null, ...(ngDevMode ? [{ debugName: "over" }] : []));
|
|
25690
|
+
map = undefined;
|
|
25691
|
+
svc = signal(null, ...(ngDevMode ? [{ debugName: "svc" }] : []));
|
|
25692
|
+
legends;
|
|
25693
|
+
count = 0;
|
|
25694
|
+
total = 0;
|
|
25695
|
+
// Resource to download and parse the PBF file
|
|
25696
|
+
dataResource = rxResource({
|
|
25697
|
+
params: () => this.settings().path,
|
|
25698
|
+
stream: ({ params }) => {
|
|
25699
|
+
const url = `https://static.foodmarketmaker.com/${params}.pbf`;
|
|
25700
|
+
return this.http.get(url, { responseType: 'arraybuffer' }).pipe(map((buffer) => TabularDataSetP.decode(new Uint8Array(buffer))));
|
|
25701
|
+
}
|
|
25702
|
+
});
|
|
25703
|
+
info = computed(() => {
|
|
25704
|
+
const path = this.settings().path;
|
|
25705
|
+
return this.InfoFromPath(path);
|
|
25706
|
+
}, ...(ngDevMode ? [{ debugName: "info" }] : []));
|
|
25707
|
+
name = computed(() => {
|
|
25708
|
+
if (this.dataResource.isLoading()) {
|
|
25709
|
+
return 'DataSet Loading...';
|
|
25710
|
+
}
|
|
25711
|
+
if (this.dataResource.error()) {
|
|
25712
|
+
return 'DataSet Error...';
|
|
25713
|
+
}
|
|
25714
|
+
const ds = this.dataResource.value();
|
|
25715
|
+
if (ds?.name) {
|
|
25716
|
+
return ds.name;
|
|
25717
|
+
}
|
|
25718
|
+
if (ds) {
|
|
25719
|
+
return this.NameFrom(ds);
|
|
25720
|
+
}
|
|
25721
|
+
return 'Unknown';
|
|
25722
|
+
}, ...(ngDevMode ? [{ debugName: "name" }] : []));
|
|
25723
|
+
desc = computed(() => {
|
|
25724
|
+
if (this.dataResource.isLoading()) {
|
|
25725
|
+
return ' ';
|
|
25726
|
+
}
|
|
25727
|
+
if (this.dataResource.error()) {
|
|
25728
|
+
return ' ';
|
|
25729
|
+
}
|
|
25730
|
+
const ds = this.dataResource.value();
|
|
25731
|
+
if (ds?.description) {
|
|
25732
|
+
return ds.name;
|
|
25733
|
+
}
|
|
25734
|
+
if (ds) {
|
|
25735
|
+
const commodity = DataSetFieldValue(ds, -1, "PRODN_PRACTICE_DESC") || '';
|
|
25736
|
+
const units = DataSetFieldValue(ds, -1, "UNIT_DESC") || '';
|
|
25737
|
+
return `${commodity} (${units})`;
|
|
25738
|
+
}
|
|
25739
|
+
return 'NASS Data';
|
|
25740
|
+
}, ...(ngDevMode ? [{ debugName: "desc" }] : []));
|
|
25741
|
+
// Generate the availble feature states
|
|
25742
|
+
featureStates = computed(() => {
|
|
25743
|
+
const dataSet = this.dataResource.value();
|
|
25744
|
+
if (!dataSet) {
|
|
25745
|
+
return {
|
|
25746
|
+
states: [],
|
|
25747
|
+
min: 0,
|
|
25748
|
+
max: 1,
|
|
25749
|
+
};
|
|
25750
|
+
}
|
|
25751
|
+
const filters = this.svc()?.stateCountyFilter() || [];
|
|
25752
|
+
const fieldState = this.findFirstType(dataSet, TabularFieldUsage.TABULAR_USAGE_FIPS_STATE);
|
|
25753
|
+
const fieldCounty = this.findFirstType(dataSet, TabularFieldUsage.TABULAR_USAGE_FIPS_COUNTY);
|
|
25754
|
+
const fieldValue = this.findFirstType(dataSet, TabularFieldUsage.TABULAR_USAGE_VALUE);
|
|
25755
|
+
let maxV = Number.NEGATIVE_INFINITY;
|
|
25756
|
+
let minV = Number.POSITIVE_INFINITY;
|
|
25757
|
+
// Caclulate min/max if not provided and filter out the rows that are necessary
|
|
25758
|
+
const keep = [];
|
|
25759
|
+
for (let i = 0; i < (dataSet.data?.length || 0); i++) {
|
|
25760
|
+
const row = dataSet.data ? dataSet.data[i] : undefined;
|
|
25761
|
+
if (!row || !row.cells) {
|
|
25762
|
+
continue;
|
|
25763
|
+
}
|
|
25764
|
+
const fips = FipsFromDataSet(dataSet, i);
|
|
25765
|
+
if (!fips || fips.endsWith("998") || fips.endsWith("999")) {
|
|
25766
|
+
// Skip invalid or unknown FIPS
|
|
25767
|
+
continue;
|
|
25768
|
+
}
|
|
25769
|
+
let found = false;
|
|
25770
|
+
for (let f of filters) {
|
|
25771
|
+
if (fips.startsWith(f)) {
|
|
25772
|
+
// Match filter
|
|
25773
|
+
found = true;
|
|
25774
|
+
break;
|
|
25775
|
+
}
|
|
25776
|
+
}
|
|
25777
|
+
if (!found && filters.length > 0) {
|
|
25778
|
+
continue;
|
|
25779
|
+
}
|
|
25780
|
+
const value = row.cells[fieldValue?.index || 0].floatValue || NaN;
|
|
25781
|
+
if (!isNaN(value)) {
|
|
25782
|
+
maxV = Math.max(maxV, value);
|
|
25783
|
+
minV = Math.min(minV, value);
|
|
25784
|
+
keep.push(row);
|
|
25785
|
+
}
|
|
25786
|
+
}
|
|
25787
|
+
// handle edge case
|
|
25788
|
+
if (maxV === Number.NEGATIVE_INFINITY) {
|
|
25789
|
+
maxV = 1;
|
|
25790
|
+
}
|
|
25791
|
+
if (minV === Number.POSITIVE_INFINITY) {
|
|
25792
|
+
minV = 0;
|
|
25793
|
+
}
|
|
25794
|
+
// Set the min max
|
|
25795
|
+
// Feature state is an object with id and value
|
|
25796
|
+
const states = [];
|
|
25797
|
+
for (let i = 0; i < keep.length; i++) {
|
|
25798
|
+
const row = keep[i];
|
|
25799
|
+
if (!row || !row.cells) {
|
|
25800
|
+
continue;
|
|
25801
|
+
}
|
|
25802
|
+
const state = row.cells[fieldState?.index || 0].stringValue;
|
|
25803
|
+
const county = row.cells[fieldCounty?.index || 0].stringValue;
|
|
25804
|
+
const value = row.cells[fieldValue?.index || 0].floatValue || 0.0;
|
|
25805
|
+
const normValue = normalize(value, minV, maxV);
|
|
25806
|
+
const fs = {
|
|
25807
|
+
id: county || state || "UNKNOWN",
|
|
25808
|
+
raw: value || 0.0,
|
|
25809
|
+
value: normValue,
|
|
25810
|
+
row: i,
|
|
25811
|
+
dataset: dataSet,
|
|
25812
|
+
state: state || '',
|
|
25813
|
+
max: maxV,
|
|
25814
|
+
min: minV,
|
|
25815
|
+
};
|
|
25816
|
+
states.push(fs);
|
|
25817
|
+
}
|
|
25818
|
+
return {
|
|
25819
|
+
states: states,
|
|
25820
|
+
min: minV,
|
|
25821
|
+
max: maxV,
|
|
25822
|
+
};
|
|
25823
|
+
}, ...(ngDevMode ? [{ debugName: "featureStates" }] : []));
|
|
25824
|
+
constructor(settings) {
|
|
25825
|
+
if (settings) {
|
|
25826
|
+
this.settings.update(current => ({
|
|
25827
|
+
...current,
|
|
25828
|
+
...settings,
|
|
25829
|
+
}));
|
|
25830
|
+
}
|
|
25831
|
+
const _ = effect(() => {
|
|
25832
|
+
const settings = this.settings();
|
|
25833
|
+
const dataset = this.dataResource.value();
|
|
25834
|
+
const features = this.featureStates();
|
|
25835
|
+
this._update(settings, dataset, features.states);
|
|
25836
|
+
}, ...(ngDevMode ? [{ debugName: "_" }] : []));
|
|
25837
|
+
const _updateGlobal = effect(() => {
|
|
25838
|
+
const svc = this.svc();
|
|
25839
|
+
if (!svc) {
|
|
25840
|
+
return;
|
|
25841
|
+
}
|
|
25842
|
+
const _ = svc.stateCountyFilter(); // depend
|
|
25843
|
+
this._update(this.settings(), this.dataResource.value(), this.featureStates().states);
|
|
25844
|
+
}, ...(ngDevMode ? [{ debugName: "_updateGlobal" }] : []));
|
|
25647
25845
|
}
|
|
25648
|
-
|
|
25649
|
-
|
|
25650
|
-
|
|
25651
|
-
|
|
25652
|
-
|
|
25653
|
-
|
|
25654
|
-
|
|
25846
|
+
update(settings) {
|
|
25847
|
+
this.settings.update(current => ({ ...current, ...settings }));
|
|
25848
|
+
}
|
|
25849
|
+
_update(settings, dataSet, featureStates) {
|
|
25850
|
+
if (!this.map) {
|
|
25851
|
+
return;
|
|
25852
|
+
}
|
|
25853
|
+
const map = this.map;
|
|
25854
|
+
this.create();
|
|
25855
|
+
this.setFeatureStates(this.settings(), featureStates);
|
|
25856
|
+
this.updateStyle(settings);
|
|
25857
|
+
}
|
|
25858
|
+
create() {
|
|
25859
|
+
if (!this.map) {
|
|
25860
|
+
return;
|
|
25861
|
+
}
|
|
25862
|
+
const map = this.map;
|
|
25863
|
+
const area = Layers.FindVector(this.settings().areaType);
|
|
25864
|
+
if (!area) {
|
|
25865
|
+
console.error('NAASMapper: Unknown area type ' + this.settings().areaType);
|
|
25866
|
+
return;
|
|
25867
|
+
}
|
|
25868
|
+
AddSource(this.map, this.SOURCE_ID, {
|
|
25869
|
+
type: area.SourceType || 'vector',
|
|
25870
|
+
tiles: [area.URL],
|
|
25871
|
+
promoteId: area.IDField || "GEOID", // promote field to be used as a foreign key
|
|
25872
|
+
});
|
|
25873
|
+
const addedFill = AddLayer(this.map, {
|
|
25874
|
+
id: this.LAYER_ID,
|
|
25875
|
+
type: 'fill',
|
|
25876
|
+
source: this.SOURCE_ID,
|
|
25877
|
+
'source-layer': area.Source,
|
|
25878
|
+
paint: {
|
|
25879
|
+
'fill-outline-color': '#e5541c',
|
|
25880
|
+
'fill-opacity': this.settings().fillOpacity,
|
|
25881
|
+
'fill-color': this.settings().fillColor,
|
|
25882
|
+
},
|
|
25883
|
+
layout: {
|
|
25884
|
+
visibility: 'none',
|
|
25885
|
+
},
|
|
25886
|
+
}, StandardLayersMapper.POLYGONS_BACKGROUND);
|
|
25887
|
+
map.off('click', this.LAYER_ID, this.onClick);
|
|
25888
|
+
map.on('click', this.LAYER_ID, this.onClick);
|
|
25889
|
+
}
|
|
25890
|
+
setFeatureStates(settings, fs) {
|
|
25891
|
+
if (!this.map) {
|
|
25892
|
+
return;
|
|
25893
|
+
}
|
|
25894
|
+
const map = this.map;
|
|
25895
|
+
const states = fs || [];
|
|
25896
|
+
const dataSet = this.dataResource.value();
|
|
25897
|
+
const src = Layers.FindVector(settings.areaType);
|
|
25898
|
+
if (!src) {
|
|
25899
|
+
console.error('NAASMapper: Unknown area type ' + settings.areaType);
|
|
25900
|
+
return;
|
|
25901
|
+
}
|
|
25902
|
+
// Remove all the previous feature states
|
|
25903
|
+
map.removeFeatureState({
|
|
25904
|
+
source: this.SOURCE_ID,
|
|
25905
|
+
sourceLayer: src.Source,
|
|
25906
|
+
});
|
|
25907
|
+
if (!dataSet || !fs) {
|
|
25908
|
+
return;
|
|
25909
|
+
}
|
|
25910
|
+
for (let state of states) {
|
|
25911
|
+
try {
|
|
25912
|
+
map.setFeatureState({
|
|
25913
|
+
source: this.SOURCE_ID,
|
|
25914
|
+
sourceLayer: src.Source,
|
|
25915
|
+
id: state.id,
|
|
25916
|
+
}, state);
|
|
25917
|
+
}
|
|
25918
|
+
catch (e) {
|
|
25919
|
+
console.warn('NAASMapper: Failed to set feature state for id ' + state.id, e);
|
|
25920
|
+
}
|
|
25921
|
+
}
|
|
25922
|
+
}
|
|
25923
|
+
getFipsFilter() {
|
|
25924
|
+
const settings = this.settings();
|
|
25925
|
+
if (settings.filterOverrideGlobal) {
|
|
25926
|
+
if (settings.filterStates && settings.filterStates.length > 0) {
|
|
25927
|
+
return settings.filterStates;
|
|
25928
|
+
}
|
|
25929
|
+
else if (settings.filterState) {
|
|
25930
|
+
return [settings.filterState];
|
|
25931
|
+
}
|
|
25932
|
+
}
|
|
25933
|
+
return this.svc()?.stateCountyFilter();
|
|
25934
|
+
}
|
|
25935
|
+
updateStyle(settings) {
|
|
25936
|
+
if (!this.map) {
|
|
25937
|
+
return;
|
|
25938
|
+
}
|
|
25939
|
+
const map = this.map;
|
|
25940
|
+
if (settings.visible) {
|
|
25941
|
+
map.setLayoutProperty(this.LAYER_ID, 'visibility', 'visible');
|
|
25942
|
+
}
|
|
25943
|
+
else {
|
|
25944
|
+
map.setLayoutProperty(this.LAYER_ID, 'visibility', 'none');
|
|
25945
|
+
}
|
|
25946
|
+
if (settings.fillType === 'palette') {
|
|
25947
|
+
this.map.setPaintProperty(this.LAYER_ID, 'fill-color', [
|
|
25948
|
+
'interpolate',
|
|
25949
|
+
['linear'],
|
|
25950
|
+
['feature-state', 'value'],
|
|
25951
|
+
...ColorPalettes.fromPalette(settings.fillPalette)
|
|
25952
|
+
]);
|
|
25953
|
+
}
|
|
25954
|
+
else if (settings.fillType === 'gradient') {
|
|
25955
|
+
this.map.setPaintProperty(this.LAYER_ID, 'fill-color', fromGradient(settings.fillGradient, ['feature-state', 'value']));
|
|
25956
|
+
}
|
|
25957
|
+
else if (settings.fillType === 'solid') {
|
|
25958
|
+
this.map.setPaintProperty(this.LAYER_ID, 'fill-color', settings.fillColor);
|
|
25959
|
+
}
|
|
25960
|
+
const filterExpr = prefixMatch(["feature-state", "id"], this.getFipsFilter());
|
|
25961
|
+
if (filterExpr && filterExpr.length > 0) {
|
|
25962
|
+
const conditions = ['all'];
|
|
25963
|
+
conditions.push(['!=', ['feature-state', 'value'], null]),
|
|
25964
|
+
conditions.push(filterExpr);
|
|
25965
|
+
map.setPaintProperty(this.LAYER_ID, 'fill-opacity', [
|
|
25966
|
+
'case',
|
|
25967
|
+
conditions,
|
|
25968
|
+
settings.fillOpacity,
|
|
25969
|
+
0
|
|
25970
|
+
]);
|
|
25971
|
+
}
|
|
25972
|
+
else {
|
|
25973
|
+
map.setPaintProperty(this.LAYER_ID, 'fill-opacity', [
|
|
25974
|
+
'case',
|
|
25975
|
+
['!=', ['feature-state', 'value'], null],
|
|
25976
|
+
settings.fillOpacity,
|
|
25977
|
+
0
|
|
25978
|
+
]);
|
|
25979
|
+
}
|
|
25980
|
+
map.setPaintProperty(this.LAYER_ID, 'fill-outline-color', settings.borderColor);
|
|
25981
|
+
}
|
|
25982
|
+
findFirstType(dataset, usage) {
|
|
25983
|
+
if (!dataset.schema) {
|
|
25984
|
+
return null;
|
|
25985
|
+
}
|
|
25986
|
+
if (!dataset.schema.fields) {
|
|
25987
|
+
return null;
|
|
25988
|
+
}
|
|
25989
|
+
for (let field of Object.keys(dataset.schema?.fields)) {
|
|
25990
|
+
const fieldDef = dataset.schema?.fields[field];
|
|
25991
|
+
if (fieldDef.usage == usage) {
|
|
25992
|
+
return fieldDef;
|
|
25993
|
+
}
|
|
25994
|
+
}
|
|
25995
|
+
return null;
|
|
25996
|
+
}
|
|
25997
|
+
onReady(map, svc) {
|
|
25998
|
+
this.map = map;
|
|
25999
|
+
this.svc.set(svc);
|
|
26000
|
+
this._update(this.settings(), this.dataResource.value(), this.featureStates().states);
|
|
26001
|
+
}
|
|
26002
|
+
reset() {
|
|
26003
|
+
this.clear();
|
|
26004
|
+
}
|
|
26005
|
+
clear() {
|
|
26006
|
+
if (this.map) {
|
|
26007
|
+
this.map.off('click', this.LAYER_ID, this.onClick);
|
|
26008
|
+
RemoveLayer(this.map, this.LAYER_ID);
|
|
26009
|
+
RemoveLayer(this.map, this.SOURCE_ID);
|
|
26010
|
+
}
|
|
26011
|
+
}
|
|
26012
|
+
onClick = async (e) => {
|
|
26013
|
+
if (!this.map) {
|
|
26014
|
+
return;
|
|
26015
|
+
}
|
|
26016
|
+
const settings = this.settings();
|
|
26017
|
+
const src = Layers.FindVector(settings.areaType);
|
|
26018
|
+
if (!src) {
|
|
26019
|
+
console.warn('ChoroplethMapper: No source found for area type ', settings.areaType);
|
|
26020
|
+
return;
|
|
26021
|
+
}
|
|
26022
|
+
const features = this.map.queryRenderedFeatures(e.point, {
|
|
26023
|
+
layers: [this.LAYER_ID],
|
|
26024
|
+
});
|
|
26025
|
+
if (features.length > 0) {
|
|
26026
|
+
e.preventDefault();
|
|
26027
|
+
if (this.current) {
|
|
26028
|
+
this.current.remove();
|
|
26029
|
+
this.current = null;
|
|
26030
|
+
}
|
|
26031
|
+
const f = features[0];
|
|
26032
|
+
const state = this.map.getFeatureState({
|
|
26033
|
+
source: this.SOURCE_ID,
|
|
26034
|
+
sourceLayer: src.Source,
|
|
26035
|
+
id: f.id
|
|
26036
|
+
});
|
|
26037
|
+
const html = await this.RenderPopup(f, state);
|
|
26038
|
+
if (html) {
|
|
26039
|
+
this.current = new Popup().setLngLat(e.lngLat).setHTML(html).addTo(this.map);
|
|
26040
|
+
}
|
|
26041
|
+
}
|
|
26042
|
+
};
|
|
26043
|
+
}
|
|
26044
|
+
function FipsFromDataSet(ds, rowIndex) {
|
|
26045
|
+
if (!ds.schema || !ds.schema.fields) {
|
|
26046
|
+
return null;
|
|
26047
|
+
}
|
|
26048
|
+
const state = DataSetFieldValue(ds, rowIndex, "STATE_FIPS_CODE");
|
|
26049
|
+
const county = DataSetFieldValue(ds, rowIndex, "COUNTY_CODE");
|
|
26050
|
+
if (county) {
|
|
26051
|
+
return county;
|
|
26052
|
+
}
|
|
26053
|
+
if (state) {
|
|
26054
|
+
return state;
|
|
26055
|
+
}
|
|
26056
|
+
return null;
|
|
26057
|
+
}
|
|
26058
|
+
function DataSetFieldValue(ds, rowIndex, field) {
|
|
26059
|
+
if (!ds.schema || !ds.data) {
|
|
26060
|
+
return null;
|
|
26061
|
+
}
|
|
26062
|
+
const fieldDef = ds.schema.fields ? ds.schema.fields[field] : null;
|
|
26063
|
+
if (!fieldDef) {
|
|
26064
|
+
return null;
|
|
26065
|
+
}
|
|
26066
|
+
if (fieldDef.staticvalue) {
|
|
26067
|
+
switch (fieldDef.datatype || 0) {
|
|
26068
|
+
case TabularDatatype.TABULAR_DATATYPE_STRING:
|
|
26069
|
+
return fieldDef.staticvalue.stringValue || null;
|
|
26070
|
+
case TabularDatatype.TABULAR_DATATYPE_FLOAT:
|
|
26071
|
+
return fieldDef.staticvalue.floatValue || null;
|
|
26072
|
+
case TabularDatatype.TABULAR_DATATYPE_INTEGER:
|
|
26073
|
+
return fieldDef.staticvalue.intValue || null;
|
|
26074
|
+
default:
|
|
26075
|
+
return null;
|
|
26076
|
+
}
|
|
26077
|
+
}
|
|
26078
|
+
if (rowIndex < 0) {
|
|
26079
|
+
return null;
|
|
26080
|
+
}
|
|
26081
|
+
const index = fieldDef.index || -1;
|
|
26082
|
+
if (index < 0 || rowIndex < 0 || rowIndex >= ds.data.length) {
|
|
26083
|
+
return null;
|
|
26084
|
+
}
|
|
26085
|
+
const row = ds.data[rowIndex];
|
|
26086
|
+
const cell = row.cells ? row.cells[index] : null;
|
|
26087
|
+
if (!cell) {
|
|
26088
|
+
return null;
|
|
26089
|
+
}
|
|
26090
|
+
switch (fieldDef.datatype || 0) {
|
|
26091
|
+
case TabularDatatype.TABULAR_DATATYPE_STRING:
|
|
26092
|
+
return cell.stringValue || null;
|
|
26093
|
+
case TabularDatatype.TABULAR_DATATYPE_FLOAT:
|
|
26094
|
+
return cell.floatValue || null;
|
|
26095
|
+
case TabularDatatype.TABULAR_DATATYPE_INTEGER:
|
|
26096
|
+
return cell.intValue || null;
|
|
26097
|
+
default:
|
|
26098
|
+
return null;
|
|
26099
|
+
}
|
|
26100
|
+
}
|
|
26101
|
+
class DataSetSettings {
|
|
26102
|
+
path = "";
|
|
26103
|
+
areaType = "county";
|
|
26104
|
+
visible = true;
|
|
26105
|
+
palette = allColors['Spectral']['10'];
|
|
26106
|
+
fillType = 'gradient';
|
|
26107
|
+
fillColor = '#e5541c';
|
|
26108
|
+
fillPalette = ColorPalettes.find('Spectral.10') || ColorPalettes.default();
|
|
26109
|
+
fillGradient = [{ "value": 0.0, "color": "#ffffcc" }, { "value": 1.0, "color": "#000000" }];
|
|
26110
|
+
fillOpacity = 1;
|
|
26111
|
+
filterState = '';
|
|
26112
|
+
filterStates = [];
|
|
26113
|
+
filterOverrideGlobal = false;
|
|
26114
|
+
borderColor = '#e5541c';
|
|
26115
|
+
labelsVisible = true;
|
|
26116
|
+
labelsSize = 10;
|
|
26117
|
+
labelsColor = '#000000';
|
|
26118
|
+
labelsHaloColor = '#ffffff';
|
|
26119
|
+
labelsHaloWidth = 1;
|
|
26120
|
+
labelsOpacity = 1.0;
|
|
26121
|
+
labelOverlap = false;
|
|
26122
|
+
showLegend = false;
|
|
26123
|
+
fipsExcludeSuffixes = ['999', '998', '000'];
|
|
26124
|
+
}
|
|
26125
|
+
|
|
26126
|
+
class ConsumerSpendingMapper extends DataSetMapper {
|
|
26127
|
+
RenderPopup(feature, state) {
|
|
26128
|
+
if (!state.dataset)
|
|
26129
|
+
return undefined;
|
|
26130
|
+
const data = state.dataset;
|
|
26131
|
+
const name = feature.properties?.['name'] || 'Unknown';
|
|
26132
|
+
const totalSpending = 0;
|
|
26133
|
+
const avgSpending = 0;
|
|
26134
|
+
return `
|
|
26135
|
+
<div>
|
|
26136
|
+
<h3>${name}</h3>
|
|
26137
|
+
<p>Total Spending: $${totalSpending.toLocaleString()}</p>
|
|
26138
|
+
<p>Average Spending: $${avgSpending.toLocaleString()}</p>
|
|
26139
|
+
</div>
|
|
26140
|
+
`;
|
|
26141
|
+
}
|
|
26142
|
+
InfoFromPath(path) {
|
|
26143
|
+
return ConsumerSpendingFromPath(path);
|
|
26144
|
+
}
|
|
26145
|
+
NameFrom(ds) {
|
|
26146
|
+
return ds.name || 'Unknown';
|
|
26147
|
+
}
|
|
26148
|
+
}
|
|
26149
|
+
|
|
26150
|
+
class DialogHeader {
|
|
26151
|
+
faTimes = faTimes;
|
|
26152
|
+
dialog = input(...(ngDevMode ? [undefined, { debugName: "dialog" }] : []));
|
|
26153
|
+
close() {
|
|
26154
|
+
// Close the dialog by finding the closest dialog element and calling its close method
|
|
26155
|
+
const d = this.dialog();
|
|
26156
|
+
if (d) {
|
|
26157
|
+
d.close();
|
|
26158
|
+
}
|
|
26159
|
+
}
|
|
26160
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: DialogHeader, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
26161
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "20.3.15", type: DialogHeader, isStandalone: true, selector: "mapag-dialog-header", inputs: { dialog: { classPropertyName: "dialog", publicName: "dialog", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
26162
|
+
<h2><ng-content></ng-content></h2>
|
|
26163
|
+
<button class="btn-icon" (click)="close()"><fa-icon [icon]="faTimes" size="lg"></fa-icon></button>
|
|
26164
|
+
`, isInline: true, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}:host{display:flex;align-items:center}:host:first-child{flex-grow:1}:host h2{margin:0;flex-grow:1}.btn-icon{padding:2px;border:none;background:transparent;cursor:pointer;border-radius:4px;color:gray}.btn-icon:hover{color:#000;background-color:transparent}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "component", type: FaIconComponent, selector: "fa-icon", inputs: ["icon", "title", "animation", "mask", "flip", "size", "pull", "border", "inverse", "symbol", "rotate", "fixedWidth", "transform", "a11yRole"], outputs: ["iconChange", "titleChange", "animationChange", "maskChange", "flipChange", "sizeChange", "pullChange", "borderChange", "inverseChange", "symbolChange", "rotateChange", "fixedWidthChange", "transformChange", "a11yRoleChange"] }] });
|
|
26165
|
+
}
|
|
26166
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: DialogHeader, decorators: [{
|
|
26167
|
+
type: Component,
|
|
26168
|
+
args: [{ selector: 'mapag-dialog-header', imports: [CommonModule, FaIconComponent], template: `
|
|
26169
|
+
<h2><ng-content></ng-content></h2>
|
|
26170
|
+
<button class="btn-icon" (click)="close()"><fa-icon [icon]="faTimes" size="lg"></fa-icon></button>
|
|
26171
|
+
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}:host{display:flex;align-items:center}:host:first-child{flex-grow:1}:host h2{margin:0;flex-grow:1}.btn-icon{padding:2px;border:none;background:transparent;cursor:pointer;border-radius:4px;color:gray}.btn-icon:hover{color:#000;background-color:transparent}\n"] }]
|
|
26172
|
+
}], propDecorators: { dialog: [{ type: i0.Input, args: [{ isSignal: true, alias: "dialog", required: false }] }] } });
|
|
26173
|
+
|
|
26174
|
+
class GradientLegend {
|
|
26175
|
+
topStyle = signal({}, ...(ngDevMode ? [{ debugName: "topStyle" }] : []));
|
|
26176
|
+
bottomStyle = signal({}, ...(ngDevMode ? [{ debugName: "bottomStyle" }] : []));
|
|
26177
|
+
gradientStyle = signal({}, ...(ngDevMode ? [{ debugName: "gradientStyle" }] : []));
|
|
26178
|
+
settings = input(new GradientSettings(), ...(ngDevMode ? [{ debugName: "settings" }] : []));
|
|
26179
|
+
renderer = inject(Renderer2);
|
|
26180
|
+
host = inject((ElementRef));
|
|
26181
|
+
constructor() {
|
|
26182
|
+
const onUpdateSettings = effect(() => {
|
|
26183
|
+
const settings = this.settings();
|
|
26184
|
+
this.topStyle.set({
|
|
26185
|
+
background: settings.minTop ? settings.minColor : settings.maxColor,
|
|
26186
|
+
value: settings.minValue
|
|
26187
|
+
});
|
|
26188
|
+
this.bottomStyle.set({
|
|
26189
|
+
background: settings.minTop ? settings.maxColor : settings.minColor,
|
|
26190
|
+
value: settings.maxValue
|
|
26191
|
+
});
|
|
26192
|
+
this.gradientStyle.set({
|
|
26193
|
+
background: `linear-gradient(${settings.dir === 'horizontal' ? 'to right' : 'to top'}, ${settings.minColor}, ${settings.maxColor})`,
|
|
26194
|
+
height: settings.dir === 'horizontal' ? '30px' : '100%',
|
|
26195
|
+
width: settings.dir === 'horizontal' ? '100%' : '30px'
|
|
26196
|
+
});
|
|
26197
|
+
}, ...(ngDevMode ? [{ debugName: "onUpdateSettings" }] : []));
|
|
26198
|
+
}
|
|
26199
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: GradientLegend, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
26200
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "20.3.15", type: GradientLegend, isStandalone: true, selector: "mapag-gradient-legend", inputs: { settings: { classPropertyName: "settings", publicName: "settings", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
26201
|
+
<div class="top" [ngStyle]="topStyle()"></div>
|
|
26202
|
+
<div>{{settings().unitPrefix}}{{ settings().maxValue | number:"1.0-2" }}{{settings().unitSuffix}}</div>
|
|
26203
|
+
<div class="gradient" [ngStyle]="gradientStyle()"></div>
|
|
26204
|
+
<div></div>
|
|
26205
|
+
<div class="bottom" [ngStyle]="bottomStyle()"></div>
|
|
26206
|
+
<div>{{settings().unitPrefix}}{{ settings().minValue | number:"1.0-2" }}{{settings().unitSuffix}}</div>
|
|
26207
|
+
`, isInline: true, styles: [":host{display:grid;grid-template-rows:auto 1fr auto;grid-template-columns:auto max-content;align-items:center;font-size:.8em;height:var(--legend-height, 150px);column-gap:4px}.h2{margin-bottom:8px}.top,.bottom{height:50%}.top{background:var(--top-color, green);align-self:end}.bottom{background:var(--bottom-color, black);align-self:start}.gradient{width:20px;flex-grow:1;height:100%;align-self:center;justify-self:center}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "ngmodule", type: FormsModule }, { kind: "pipe", type: i1.DecimalPipe, name: "number" }] });
|
|
26208
|
+
}
|
|
26209
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: GradientLegend, decorators: [{
|
|
26210
|
+
type: Component,
|
|
26211
|
+
args: [{ selector: 'mapag-gradient-legend', imports: [CommonModule, FormsModule], template: `
|
|
26212
|
+
<div class="top" [ngStyle]="topStyle()"></div>
|
|
26213
|
+
<div>{{settings().unitPrefix}}{{ settings().maxValue | number:"1.0-2" }}{{settings().unitSuffix}}</div>
|
|
26214
|
+
<div class="gradient" [ngStyle]="gradientStyle()"></div>
|
|
26215
|
+
<div></div>
|
|
26216
|
+
<div class="bottom" [ngStyle]="bottomStyle()"></div>
|
|
26217
|
+
<div>{{settings().unitPrefix}}{{ settings().minValue | number:"1.0-2" }}{{settings().unitSuffix}}</div>
|
|
26218
|
+
`, styles: [":host{display:grid;grid-template-rows:auto 1fr auto;grid-template-columns:auto max-content;align-items:center;font-size:.8em;height:var(--legend-height, 150px);column-gap:4px}.h2{margin-bottom:8px}.top,.bottom{height:50%}.top{background:var(--top-color, green);align-self:end}.bottom{background:var(--bottom-color, black);align-self:start}.gradient{width:20px;flex-grow:1;height:100%;align-self:center;justify-self:center}\n"] }]
|
|
26219
|
+
}], ctorParameters: () => [], propDecorators: { settings: [{ type: i0.Input, args: [{ isSignal: true, alias: "settings", required: false }] }] } });
|
|
26220
|
+
class GradientSettings {
|
|
26221
|
+
minColor = "#000000";
|
|
26222
|
+
maxColor = "#FFFFFF";
|
|
26223
|
+
minValue = 0.0;
|
|
26224
|
+
maxValue = 1.0;
|
|
26225
|
+
height = "100px";
|
|
26226
|
+
width = "30px";
|
|
26227
|
+
minTop = false;
|
|
26228
|
+
dir = 'vertical';
|
|
26229
|
+
unitPrefix = '';
|
|
26230
|
+
unitSuffix = '';
|
|
26231
|
+
}
|
|
26232
|
+
|
|
26233
|
+
class ShowHideBtn {
|
|
26234
|
+
faEye = faEye;
|
|
26235
|
+
faEyeSlash = faEyeSlash;
|
|
26236
|
+
mapper = input.required(...(ngDevMode ? [{ debugName: "mapper" }] : []));
|
|
26237
|
+
toggleShowHide() {
|
|
26238
|
+
const current = this.mapper().settings().visible;
|
|
26239
|
+
this.mapper().update({ visible: !current });
|
|
26240
|
+
}
|
|
26241
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: ShowHideBtn, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
26242
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "20.3.15", type: ShowHideBtn, isStandalone: true, selector: "mapag-show-hide-btn", inputs: { mapper: { classPropertyName: "mapper", publicName: "mapper", isSignal: true, isRequired: true, transformFunction: null } }, ngImport: i0, template: `
|
|
26243
|
+
<button class="btn" (click)="toggleShowHide()">
|
|
26244
|
+
<fa-icon [icon]="mapper().settings().visible ? faEyeSlash : faEye"></fa-icon>
|
|
26245
|
+
{{ mapper().settings().visible ? 'Hide' : 'Show' }}
|
|
26246
|
+
</button>
|
|
26247
|
+
`, isInline: true, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}:host{display:content}.btn{width:12ch}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "component", type: FaIconComponent, selector: "fa-icon", inputs: ["icon", "title", "animation", "mask", "flip", "size", "pull", "border", "inverse", "symbol", "rotate", "fixedWidth", "transform", "a11yRole"], outputs: ["iconChange", "titleChange", "animationChange", "maskChange", "flipChange", "sizeChange", "pullChange", "borderChange", "inverseChange", "symbolChange", "rotateChange", "fixedWidthChange", "transformChange", "a11yRoleChange"] }] });
|
|
26248
|
+
}
|
|
26249
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: ShowHideBtn, decorators: [{
|
|
26250
|
+
type: Component,
|
|
26251
|
+
args: [{ selector: 'mapag-show-hide-btn', imports: [CommonModule, FaIconComponent], template: `
|
|
26252
|
+
<button class="btn" (click)="toggleShowHide()">
|
|
26253
|
+
<fa-icon [icon]="mapper().settings().visible ? faEyeSlash : faEye"></fa-icon>
|
|
26254
|
+
{{ mapper().settings().visible ? 'Hide' : 'Show' }}
|
|
26255
|
+
</button>
|
|
26256
|
+
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}:host{display:content}.btn{width:12ch}\n"] }]
|
|
26257
|
+
}], propDecorators: { mapper: [{ type: i0.Input, args: [{ isSignal: true, alias: "mapper", required: true }] }] } });
|
|
26258
|
+
|
|
26259
|
+
class StdLegend {
|
|
26260
|
+
items = input([], ...(ngDevMode ? [{ debugName: "items" }] : []));
|
|
26261
|
+
columns = input(1, ...(ngDevMode ? [{ debugName: "columns" }] : []));
|
|
26262
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: StdLegend, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
26263
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.15", type: StdLegend, isStandalone: true, selector: "mapag-std-legend", inputs: { items: { classPropertyName: "items", publicName: "items", isSignal: true, isRequired: false, transformFunction: null }, columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
26264
|
+
<div class="legend" [style.grid-template-columns]="'repeat(' + columns() + ',1fr)'">
|
|
26265
|
+
@for (item of items(); track item) {
|
|
26266
|
+
<div class="legend-row">
|
|
26267
|
+
<div class="legend-item" [style.background-color]="item.value" [ngStyle]="item.style"></div>
|
|
26268
|
+
<div>{{ item.label }}</div>
|
|
26269
|
+
</div>
|
|
26270
|
+
}
|
|
26271
|
+
</div>
|
|
26272
|
+
`, isInline: true, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}.legend{display:grid;column-gap:8px;font-size:.8em}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }] });
|
|
26273
|
+
}
|
|
26274
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: StdLegend, decorators: [{
|
|
26275
|
+
type: Component,
|
|
26276
|
+
args: [{ selector: 'mapag-std-legend', imports: [CommonModule], template: `
|
|
26277
|
+
<div class="legend" [style.grid-template-columns]="'repeat(' + columns() + ',1fr)'">
|
|
26278
|
+
@for (item of items(); track item) {
|
|
26279
|
+
<div class="legend-row">
|
|
26280
|
+
<div class="legend-item" [style.background-color]="item.value" [ngStyle]="item.style"></div>
|
|
26281
|
+
<div>{{ item.label }}</div>
|
|
26282
|
+
</div>
|
|
26283
|
+
}
|
|
26284
|
+
</div>
|
|
26285
|
+
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}.legend{display:grid;column-gap:8px;font-size:.8em}\n"] }]
|
|
26286
|
+
}], propDecorators: { items: [{ type: i0.Input, args: [{ isSignal: true, alias: "items", required: false }] }], columns: [{ type: i0.Input, args: [{ isSignal: true, alias: "columns", required: false }] }] } });
|
|
26287
|
+
|
|
26288
|
+
class TextPipe {
|
|
26289
|
+
transform(value, ...args) {
|
|
26290
|
+
if (value === null || value === undefined) {
|
|
26291
|
+
return '';
|
|
26292
|
+
}
|
|
26293
|
+
if (typeof value === 'string') {
|
|
26294
|
+
return fixText(value);
|
|
26295
|
+
}
|
|
26296
|
+
return value;
|
|
26297
|
+
}
|
|
26298
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: TextPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
|
|
26299
|
+
static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "20.3.15", ngImport: i0, type: TextPipe, isStandalone: true, name: "text" });
|
|
26300
|
+
}
|
|
26301
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: TextPipe, decorators: [{
|
|
26302
|
+
type: Pipe,
|
|
26303
|
+
args: [{
|
|
26304
|
+
name: 'text'
|
|
26305
|
+
}]
|
|
26306
|
+
}] });
|
|
26307
|
+
|
|
26308
|
+
class ConsumerSpendingPanel {
|
|
26309
|
+
map = input(...(ngDevMode ? [undefined, { debugName: "map" }] : []));
|
|
26310
|
+
mapper = new ConsumerSpendingMapper();
|
|
26311
|
+
customizeDialog = viewChild('customizeDialog', ...(ngDevMode ? [{ debugName: "customizeDialog" }] : []));
|
|
26312
|
+
legendDialog = viewChild('legendDialog', ...(ngDevMode ? [{ debugName: "legendDialog" }] : []));
|
|
26313
|
+
onRemove = output();
|
|
26314
|
+
settings = input(new DataSetSettings(), ...(ngDevMode ? [{ debugName: "settings" }] : []));
|
|
26315
|
+
USStates = states;
|
|
26316
|
+
constructor() {
|
|
26317
|
+
const _mapInit = effect(() => {
|
|
26318
|
+
const mapComp = this.map();
|
|
26319
|
+
if (mapComp) {
|
|
26320
|
+
mapComp.mapper().set(this.mapper.ID, this.mapper);
|
|
26321
|
+
}
|
|
26322
|
+
}, ...(ngDevMode ? [{ debugName: "_mapInit" }] : []));
|
|
26323
|
+
const _item = effect(() => {
|
|
26324
|
+
const item = this.settings();
|
|
26325
|
+
untracked(() => this.mapper.update(item));
|
|
26326
|
+
}, ...(ngDevMode ? [{ debugName: "_item" }] : []));
|
|
26327
|
+
}
|
|
26328
|
+
setVisible(visible) {
|
|
26329
|
+
this.mapper.update({ visible: visible });
|
|
26330
|
+
}
|
|
26331
|
+
updateGradient(v1, v2) {
|
|
26332
|
+
const current = this.mapper.settings().fillGradient;
|
|
26333
|
+
if (v1) {
|
|
26334
|
+
current[0].color = v1;
|
|
26335
|
+
}
|
|
26336
|
+
if (v2) {
|
|
26337
|
+
current[1].color = v2;
|
|
26338
|
+
}
|
|
26339
|
+
this.mapper.update({
|
|
26340
|
+
fillGradient: current,
|
|
26341
|
+
});
|
|
26342
|
+
}
|
|
26343
|
+
paletteLegend = computed(() => {
|
|
26344
|
+
const info = this.mapper.info();
|
|
26345
|
+
const minmax = this.mapper.featureStates();
|
|
26346
|
+
const palette = this.mapper.settings().fillPalette;
|
|
26347
|
+
return ColorPalettes.ToLegend(palette, minmax.min || 0, minmax.max || 1, { unitSuffix: " " + fixText(info.Unit) });
|
|
26348
|
+
}, ...(ngDevMode ? [{ debugName: "paletteLegend" }] : []));
|
|
26349
|
+
gradientSettings = computed(() => {
|
|
26350
|
+
const info = this.mapper.info();
|
|
26351
|
+
const minmax = this.mapper.featureStates();
|
|
26352
|
+
return {
|
|
26353
|
+
minColor: this.mapper.settings().fillGradient[0].color,
|
|
26354
|
+
maxColor: this.mapper.settings().fillGradient[1].color,
|
|
26355
|
+
minValue: minmax.min || 0,
|
|
26356
|
+
maxValue: minmax.max || 1,
|
|
26357
|
+
dir: 'vertical',
|
|
26358
|
+
height: '150px',
|
|
26359
|
+
width: '30px',
|
|
26360
|
+
unitPrefix: " ",
|
|
26361
|
+
unitSuffix: " " + fixText(info.Unit)
|
|
26362
|
+
};
|
|
26363
|
+
}, ...(ngDevMode ? [{ debugName: "gradientSettings" }] : []));
|
|
26364
|
+
toggleDialog() {
|
|
26365
|
+
const dialog = this.customizeDialog();
|
|
26366
|
+
if (!dialog) {
|
|
26367
|
+
return;
|
|
26368
|
+
}
|
|
26369
|
+
const dialogElement = dialog.nativeElement;
|
|
26370
|
+
if (dialogElement.open) {
|
|
26371
|
+
dialogElement.close();
|
|
26372
|
+
}
|
|
26373
|
+
else {
|
|
26374
|
+
dialogElement.show();
|
|
26375
|
+
}
|
|
26376
|
+
// Implement dialog toggle logic here
|
|
26377
|
+
}
|
|
26378
|
+
toggleLegend() {
|
|
26379
|
+
const dialog = this.legendDialog();
|
|
26380
|
+
if (!dialog) {
|
|
26381
|
+
return;
|
|
26382
|
+
}
|
|
26383
|
+
const dialogElement = dialog.nativeElement;
|
|
26384
|
+
if (dialogElement.open) {
|
|
26385
|
+
dialogElement.close();
|
|
26386
|
+
}
|
|
26387
|
+
else {
|
|
26388
|
+
dialogElement.show();
|
|
26389
|
+
}
|
|
26390
|
+
// Implement dialog toggle logic here
|
|
26391
|
+
}
|
|
26392
|
+
update(field, value) {
|
|
26393
|
+
this.mapper.update({
|
|
26394
|
+
[field]: value,
|
|
26395
|
+
});
|
|
26396
|
+
}
|
|
26397
|
+
reset() {
|
|
26398
|
+
this.mapper.update(new DataSetSettings());
|
|
26399
|
+
}
|
|
26400
|
+
remove() {
|
|
26401
|
+
this.mapper.update({ visible: false });
|
|
26402
|
+
this.toggleDialog();
|
|
26403
|
+
this.onRemove.emit();
|
|
26404
|
+
}
|
|
26405
|
+
ngOnDestroy() {
|
|
26406
|
+
this.mapper.clear();
|
|
26407
|
+
}
|
|
26408
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: ConsumerSpendingPanel, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
26409
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.15", type: ConsumerSpendingPanel, isStandalone: true, selector: "mapag-consumer-spending-panel", inputs: { map: { classPropertyName: "map", publicName: "map", isSignal: true, isRequired: false, transformFunction: null }, settings: { classPropertyName: "settings", publicName: "settings", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { onRemove: "onRemove" }, viewQueries: [{ propertyName: "customizeDialog", first: true, predicate: ["customizeDialog"], descendants: true, isSignal: true }, { propertyName: "legendDialog", first: true, predicate: ["legendDialog"], descendants: true, isSignal: true }], ngImport: i0, template: `
|
|
26410
|
+
<hub-data-layer
|
|
26411
|
+
[visible]="mapper.settings().visible"
|
|
26412
|
+
[name]="mapper.info().Commodity + ' (' + mapper.info().Year + ')'"
|
|
26413
|
+
[desc]="mapper.desc()"
|
|
26414
|
+
shape="area"
|
|
26415
|
+
(onCheck)="setVisible($event)"
|
|
26416
|
+
(onCustomize)="toggleDialog()"
|
|
26417
|
+
>
|
|
26418
|
+
<area-icon></area-icon>
|
|
26419
|
+
</hub-data-layer>
|
|
26420
|
+
|
|
26421
|
+
<dialog draggable mapagBringToFront onBody #customizeDialog>
|
|
26422
|
+
<h2>{{ mapper.name() }}</h2>
|
|
26423
|
+
|
|
26424
|
+
<div class="dlg-body">
|
|
26425
|
+
<p>
|
|
26426
|
+
The Consumer Spending dataset from Esri provides a rigorously modeled representation of how U.S. households
|
|
26427
|
+
allocate their budgets across a wide spectrum of goods and services, integrating source data from the U.S.
|
|
26428
|
+
Bureau of Labor Statistics’ Consumer Expenditure and Diary Surveys to estimate both current spending patterns
|
|
26429
|
+
and five‑year forecasts. It offers detailed, category‑level insights into consumer purchasing behavior,
|
|
26430
|
+
enabling analysts to understand market demand, evaluate economic conditions, and support data‑driven
|
|
26431
|
+
decision‑making within geographic contexts.
|
|
26432
|
+
</p>
|
|
26433
|
+
<h3>Information</h3>
|
|
26434
|
+
<div class="info-grid">
|
|
26435
|
+
<div class="info">
|
|
26436
|
+
<div class="info-label">Source</div>
|
|
26437
|
+
<div class="info-value">{{ mapper.info().Source | text }}</div>
|
|
26438
|
+
</div>
|
|
26439
|
+
<div class="info">
|
|
26440
|
+
<div class="info-label">Sector</div>
|
|
26441
|
+
<div class="info-value">{{ mapper.info().Sector | text }}</div>
|
|
26442
|
+
</div>
|
|
26443
|
+
<div class="info">
|
|
26444
|
+
<div class="info-label">Group</div>
|
|
26445
|
+
<div class="info-value">{{ mapper.info().Group | text }}</div>
|
|
26446
|
+
</div>
|
|
26447
|
+
<div class="info">
|
|
26448
|
+
<div class="info-label">Commodity</div>
|
|
26449
|
+
<div class="info-value">{{ mapper.info().Commodity | text }}</div>
|
|
26450
|
+
</div>
|
|
26451
|
+
<div class="info">
|
|
26452
|
+
<div class="info-label">Class</div>
|
|
26453
|
+
<div class="info-value">{{ mapper.info().Class | text }}</div>
|
|
26454
|
+
</div>
|
|
26455
|
+
<div class="info">
|
|
26456
|
+
<div class="info-label">Statistic</div>
|
|
26457
|
+
<div class="info-value">{{ mapper.info().Statistic | text }}</div>
|
|
26458
|
+
</div>
|
|
26459
|
+
<div class="info">
|
|
26460
|
+
<div class="info-label">Production</div>
|
|
26461
|
+
<div class="info-value">{{ mapper.info().Production | text }}</div>
|
|
26462
|
+
</div>
|
|
26463
|
+
<div class="info">
|
|
26464
|
+
<div class="info-label">Utilization</div>
|
|
26465
|
+
<div class="info-value">{{ mapper.info().Utilization | text }}</div>
|
|
26466
|
+
</div>
|
|
26467
|
+
<div class="info">
|
|
26468
|
+
<div class="info-label">Unit</div>
|
|
26469
|
+
<div class="info-value">{{ mapper.info().Unit | text }}</div>
|
|
26470
|
+
</div>
|
|
26471
|
+
</div>
|
|
26472
|
+
<h3>Customize Display Settings</h3>
|
|
26473
|
+
<div class="zones">
|
|
26474
|
+
<div class="ctrl-group">
|
|
26475
|
+
<div class="radio-tabs">
|
|
26476
|
+
<label>
|
|
26477
|
+
<input
|
|
26478
|
+
type="radio"
|
|
26479
|
+
name="fillType"
|
|
26480
|
+
value="solid"
|
|
26481
|
+
[checked]="mapper.settings().fillType == 'solid'"
|
|
26482
|
+
(change)="update('fillType', 'solid')"
|
|
26483
|
+
/>
|
|
26484
|
+
Solid
|
|
26485
|
+
</label>
|
|
26486
|
+
<label>
|
|
26487
|
+
<input
|
|
26488
|
+
type="radio"
|
|
26489
|
+
name="fillType"
|
|
26490
|
+
value="gradient"
|
|
26491
|
+
[checked]="mapper.settings().fillType == 'gradient'"
|
|
26492
|
+
(change)="update('fillType', 'gradient')"
|
|
26493
|
+
/>
|
|
26494
|
+
Gradient
|
|
26495
|
+
</label>
|
|
26496
|
+
<label>
|
|
26497
|
+
<input
|
|
26498
|
+
type="radio"
|
|
26499
|
+
name="fillType"
|
|
26500
|
+
value="palette"
|
|
26501
|
+
[checked]="mapper.settings().fillType == 'palette'"
|
|
26502
|
+
(change)="update('fillType', 'palette')"
|
|
26503
|
+
/>
|
|
26504
|
+
Palette
|
|
26505
|
+
</label>
|
|
26506
|
+
</div>
|
|
26507
|
+
<div class="ctrl-row">
|
|
26508
|
+
@switch (mapper.settings().fillType) { @case ('solid') {
|
|
26509
|
+
<label for="colorPicker">Color:</label>
|
|
26510
|
+
<input
|
|
26511
|
+
type="color"
|
|
26512
|
+
id="colorPicker"
|
|
26513
|
+
[ngModel]="mapper.settings().fillColor"
|
|
26514
|
+
(ngModelChange)="update('fillColor', $event)"
|
|
26515
|
+
/>
|
|
26516
|
+
} @case ('gradient') {
|
|
26517
|
+
<label for="gradientSelect">Gradient:</label>
|
|
26518
|
+
<input
|
|
26519
|
+
type="color"
|
|
26520
|
+
[ngModel]="mapper.settings().fillGradient[0].color"
|
|
26521
|
+
(ngModelChange)="updateGradient($event, undefined)"
|
|
26522
|
+
/>
|
|
26523
|
+
<input
|
|
26524
|
+
type="color"
|
|
26525
|
+
[ngModel]="mapper.settings().fillGradient[1].color"
|
|
26526
|
+
(ngModelChange)="updateGradient(undefined, $event)"
|
|
26527
|
+
/>
|
|
26528
|
+
} @case ('palette') {
|
|
26529
|
+
<label for="paletteSelect">Palette:</label>
|
|
26530
|
+
<mapag-palette-select
|
|
26531
|
+
[palette]="mapper.settings().fillPalette"
|
|
26532
|
+
(paletteChange)="update('fillPalette', $event)"
|
|
26533
|
+
>
|
|
26534
|
+
</mapag-palette-select>
|
|
26535
|
+
} }
|
|
26536
|
+
</div>
|
|
26537
|
+
<div class="ctrl-row">
|
|
26538
|
+
<label for="fillOpacity">Opacity:</label>
|
|
26539
|
+
<input
|
|
26540
|
+
type="range"
|
|
26541
|
+
id="fillOpacity"
|
|
26542
|
+
min="0"
|
|
26543
|
+
max="1"
|
|
26544
|
+
step="0.01"
|
|
26545
|
+
[ngModel]="mapper.settings().fillOpacity"
|
|
26546
|
+
(ngModelChange)="update('fillOpacity', $event)"
|
|
26547
|
+
/>
|
|
26548
|
+
</div>
|
|
26549
|
+
<div class="ctrl-row">
|
|
26550
|
+
<label for="borderColor">Border Color:</label>
|
|
26551
|
+
<input
|
|
26552
|
+
type="color"
|
|
26553
|
+
id="borderColor"
|
|
26554
|
+
[ngModel]="mapper.settings().borderColor"
|
|
26555
|
+
(ngModelChange)="update('borderColor', $event)"
|
|
26556
|
+
/>
|
|
26557
|
+
</div>
|
|
26558
|
+
</div>
|
|
26559
|
+
<div class="ctrl-group">
|
|
26560
|
+
<h4>Filters</h4>
|
|
26561
|
+
<h5>State</h5>
|
|
26562
|
+
<div class="filter-row" style="padding: 3px;">
|
|
26563
|
+
<ng-select
|
|
26564
|
+
[items]="USStates"
|
|
26565
|
+
bindLabel="Name"
|
|
26566
|
+
bindValue="Abbr"
|
|
26567
|
+
[ngModel]="mapper.settings().filterStates"
|
|
26568
|
+
[multiple]="true"
|
|
26569
|
+
appendTo="body"
|
|
26570
|
+
(ngModelChange)="update('filterStates', $event)"
|
|
26571
|
+
>
|
|
26572
|
+
</ng-select>
|
|
26573
|
+
</div>
|
|
26574
|
+
</div>
|
|
26575
|
+
</div>
|
|
26576
|
+
|
|
26577
|
+
<h3>References</h3>
|
|
26578
|
+
<div style="display: flex; flex-direction: column;">
|
|
26579
|
+
<a href="https://www.nass.usda.gov/" target="_blank">USDA NASS</a>
|
|
26580
|
+
<a href="https://quickstats.nass.usda.gov/" target="_blank">USDA NASS Quick Stats</a>
|
|
26581
|
+
</div>
|
|
26582
|
+
</div>
|
|
26583
|
+
<div class="dlg-buttons">
|
|
26584
|
+
<button class="btn" (click)="toggleLegend()">Legend</button>
|
|
26585
|
+
<button class="btn" (click)="remove()">Remove</button>
|
|
26586
|
+
<button class="btn" (click)="reset()">Reset</button>
|
|
26587
|
+
<mapag-show-hide-btn [mapper]="mapper"></mapag-show-hide-btn>
|
|
26588
|
+
<button class="btn" (click)="toggleDialog()">Close</button>
|
|
26589
|
+
</div>
|
|
26590
|
+
</dialog>
|
|
26591
|
+
|
|
26592
|
+
<dialog class="legend" #legendDialog draggable mapagBringToFront onbody>
|
|
26593
|
+
<mapag-dialog-header class="drag-handle"[dialog]="legendDialog">{{ mapper.name() }}</mapag-dialog-header>
|
|
26594
|
+
@switch (mapper.settings().fillType) {
|
|
26595
|
+
@case ('solid') {
|
|
26596
|
+
<div style="width: 30px; height: 30px; background-color: {{ mapper.settings().fillColor }}; border: 1px solid #000;"></div>
|
|
26597
|
+
}
|
|
26598
|
+
@case ('gradient') {
|
|
26599
|
+
<mapag-gradient-legend [settings]="gradientSettings()"> </mapag-gradient-legend>
|
|
26600
|
+
}
|
|
26601
|
+
@case ('palette') {
|
|
26602
|
+
<mapag-std-legend [items]="paletteLegend()"></mapag-std-legend>
|
|
26603
|
+
}
|
|
26604
|
+
}
|
|
26605
|
+
</dialog>
|
|
26606
|
+
`, isInline: true, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}.ctrl-group{display:flex;flex-direction:column;gap:8px}.filter-row{display:flex;flex-direction:column;margin-bottom:8px;font-size:.8em}.filter-row-cols{display:block;column-count:2}.zone{display:flex;align-items:center;gap:8px;margin:0;padding:0}.zones{display:grid;grid-template-columns:1fr 1fr;column-gap:24px;row-gap:8px;overflow-y:auto;max-height:420px}.svgicon{height:30px;width:30px;-webkit-mask-size:contain;mask-size:contain}h4,label{display:flex;align-items:center;gap:4px}.info-grid{display:grid;grid-template-columns:1fr 1fr 1fr;gap:8px;margin-bottom:16px}.info{display:flex;flex-direction:column}.info-label{font-weight:600;font-size:.7em;color:#333}.info-value{font-size:.8em;color:#555}@media (max-width: 600px){.zones{grid-template-columns:1fr}}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$1.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$1.RangeValueAccessor, selector: "input[type=range][formControlName],input[type=range][formControl],input[type=range][ngModel]" }, { kind: "directive", type: i1$1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "component", type: HubDataLayer, selector: "hub-data-layer", inputs: ["visible", "name", "desc", "icon", "shape"], outputs: ["onCustomize", "onCheck"] }, { kind: "directive", type: DraggableDialogDirective, selector: "dialog[draggable]" }, { kind: "component", type: AreaIcon, selector: "area-icon" }, { kind: "component", type: PaletteSelect, selector: "mapag-palette-select", inputs: ["palettes", "palette"], outputs: ["paletteChange"] }, { kind: "directive", type: BringToFrontDirective, selector: "[mapagBringToFront]" }, { kind: "component", type: NgSelectComponent, selector: "ng-select", inputs: ["bindLabel", "bindValue", "appearance", "ariaLabelDropdown", "ariaLabel", "markFirst", "placeholder", "fixedPlaceholder", "notFoundText", "typeToSearchText", "preventToggleOnRightClick", "addTagText", "loadingText", "clearAllText", "dropdownPosition", "appendTo", "loading", "closeOnSelect", "hideSelected", "selectOnTab", "openOnEnter", "maxSelectedItems", "groupBy", "groupValue", "bufferAmount", "virtualScroll", "selectableGroup", "tabFocusOnClearButton", "selectableGroupAsModel", "searchFn", "trackByFn", "clearOnBackspace", "labelForId", "inputAttrs", "tabIndex", "readonly", "searchWhileComposing", "minTermLength", "editableSearchTerm", "ngClass", "typeahead", "multiple", "addTag", "searchable", "clearable", "isOpen", "items", "compareWith", "clearSearchOnAdd", "deselectOnClick", "keyDownFn"], outputs: ["bindLabelChange", "bindValueChange", "appearanceChange", "isOpenChange", "blur", "focus", "change", "open", "close", "search", "clear", "add", "remove", "scroll", "scrollToEnd", "itemsChange"] }, { kind: "component", type: ShowHideBtn, selector: "mapag-show-hide-btn", inputs: ["mapper"] }, { kind: "component", type: GradientLegend, selector: "mapag-gradient-legend", inputs: ["settings"] }, { kind: "component", type: StdLegend, selector: "mapag-std-legend", inputs: ["items", "columns"] }, { kind: "component", type: DialogHeader, selector: "mapag-dialog-header", inputs: ["dialog"] }, { kind: "directive", type: OnBodyDirective, selector: "dialog[onBody]" }, { kind: "pipe", type: TextPipe, name: "text" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
26607
|
+
}
|
|
26608
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: ConsumerSpendingPanel, decorators: [{
|
|
26609
|
+
type: Component,
|
|
26610
|
+
args: [{ selector: 'mapag-consumer-spending-panel', changeDetection: ChangeDetectionStrategy.OnPush, imports: [
|
|
26611
|
+
CommonModule,
|
|
26612
|
+
FormsModule,
|
|
26613
|
+
HubDataLayer,
|
|
26614
|
+
DraggableDialogDirective,
|
|
26615
|
+
AreaIcon,
|
|
26616
|
+
PaletteSelect,
|
|
26617
|
+
BringToFrontDirective,
|
|
26618
|
+
NgSelectComponent,
|
|
26619
|
+
ShowHideBtn,
|
|
26620
|
+
GradientLegend,
|
|
26621
|
+
StdLegend,
|
|
26622
|
+
DialogHeader,
|
|
26623
|
+
TextPipe,
|
|
26624
|
+
OnBodyDirective
|
|
26625
|
+
], template: `
|
|
26626
|
+
<hub-data-layer
|
|
26627
|
+
[visible]="mapper.settings().visible"
|
|
26628
|
+
[name]="mapper.info().Commodity + ' (' + mapper.info().Year + ')'"
|
|
26629
|
+
[desc]="mapper.desc()"
|
|
26630
|
+
shape="area"
|
|
26631
|
+
(onCheck)="setVisible($event)"
|
|
26632
|
+
(onCustomize)="toggleDialog()"
|
|
26633
|
+
>
|
|
26634
|
+
<area-icon></area-icon>
|
|
26635
|
+
</hub-data-layer>
|
|
26636
|
+
|
|
26637
|
+
<dialog draggable mapagBringToFront onBody #customizeDialog>
|
|
26638
|
+
<h2>{{ mapper.name() }}</h2>
|
|
26639
|
+
|
|
26640
|
+
<div class="dlg-body">
|
|
26641
|
+
<p>
|
|
26642
|
+
The Consumer Spending dataset from Esri provides a rigorously modeled representation of how U.S. households
|
|
26643
|
+
allocate their budgets across a wide spectrum of goods and services, integrating source data from the U.S.
|
|
26644
|
+
Bureau of Labor Statistics’ Consumer Expenditure and Diary Surveys to estimate both current spending patterns
|
|
26645
|
+
and five‑year forecasts. It offers detailed, category‑level insights into consumer purchasing behavior,
|
|
26646
|
+
enabling analysts to understand market demand, evaluate economic conditions, and support data‑driven
|
|
26647
|
+
decision‑making within geographic contexts.
|
|
26648
|
+
</p>
|
|
26649
|
+
<h3>Information</h3>
|
|
26650
|
+
<div class="info-grid">
|
|
26651
|
+
<div class="info">
|
|
26652
|
+
<div class="info-label">Source</div>
|
|
26653
|
+
<div class="info-value">{{ mapper.info().Source | text }}</div>
|
|
26654
|
+
</div>
|
|
26655
|
+
<div class="info">
|
|
26656
|
+
<div class="info-label">Sector</div>
|
|
26657
|
+
<div class="info-value">{{ mapper.info().Sector | text }}</div>
|
|
26658
|
+
</div>
|
|
26659
|
+
<div class="info">
|
|
26660
|
+
<div class="info-label">Group</div>
|
|
26661
|
+
<div class="info-value">{{ mapper.info().Group | text }}</div>
|
|
26662
|
+
</div>
|
|
26663
|
+
<div class="info">
|
|
26664
|
+
<div class="info-label">Commodity</div>
|
|
26665
|
+
<div class="info-value">{{ mapper.info().Commodity | text }}</div>
|
|
26666
|
+
</div>
|
|
26667
|
+
<div class="info">
|
|
26668
|
+
<div class="info-label">Class</div>
|
|
26669
|
+
<div class="info-value">{{ mapper.info().Class | text }}</div>
|
|
26670
|
+
</div>
|
|
26671
|
+
<div class="info">
|
|
26672
|
+
<div class="info-label">Statistic</div>
|
|
26673
|
+
<div class="info-value">{{ mapper.info().Statistic | text }}</div>
|
|
26674
|
+
</div>
|
|
26675
|
+
<div class="info">
|
|
26676
|
+
<div class="info-label">Production</div>
|
|
26677
|
+
<div class="info-value">{{ mapper.info().Production | text }}</div>
|
|
26678
|
+
</div>
|
|
26679
|
+
<div class="info">
|
|
26680
|
+
<div class="info-label">Utilization</div>
|
|
26681
|
+
<div class="info-value">{{ mapper.info().Utilization | text }}</div>
|
|
26682
|
+
</div>
|
|
26683
|
+
<div class="info">
|
|
26684
|
+
<div class="info-label">Unit</div>
|
|
26685
|
+
<div class="info-value">{{ mapper.info().Unit | text }}</div>
|
|
26686
|
+
</div>
|
|
26687
|
+
</div>
|
|
26688
|
+
<h3>Customize Display Settings</h3>
|
|
26689
|
+
<div class="zones">
|
|
26690
|
+
<div class="ctrl-group">
|
|
26691
|
+
<div class="radio-tabs">
|
|
26692
|
+
<label>
|
|
26693
|
+
<input
|
|
26694
|
+
type="radio"
|
|
26695
|
+
name="fillType"
|
|
26696
|
+
value="solid"
|
|
26697
|
+
[checked]="mapper.settings().fillType == 'solid'"
|
|
26698
|
+
(change)="update('fillType', 'solid')"
|
|
26699
|
+
/>
|
|
26700
|
+
Solid
|
|
26701
|
+
</label>
|
|
26702
|
+
<label>
|
|
26703
|
+
<input
|
|
26704
|
+
type="radio"
|
|
26705
|
+
name="fillType"
|
|
26706
|
+
value="gradient"
|
|
26707
|
+
[checked]="mapper.settings().fillType == 'gradient'"
|
|
26708
|
+
(change)="update('fillType', 'gradient')"
|
|
26709
|
+
/>
|
|
26710
|
+
Gradient
|
|
26711
|
+
</label>
|
|
26712
|
+
<label>
|
|
26713
|
+
<input
|
|
26714
|
+
type="radio"
|
|
26715
|
+
name="fillType"
|
|
26716
|
+
value="palette"
|
|
26717
|
+
[checked]="mapper.settings().fillType == 'palette'"
|
|
26718
|
+
(change)="update('fillType', 'palette')"
|
|
26719
|
+
/>
|
|
26720
|
+
Palette
|
|
26721
|
+
</label>
|
|
26722
|
+
</div>
|
|
26723
|
+
<div class="ctrl-row">
|
|
26724
|
+
@switch (mapper.settings().fillType) { @case ('solid') {
|
|
26725
|
+
<label for="colorPicker">Color:</label>
|
|
26726
|
+
<input
|
|
26727
|
+
type="color"
|
|
26728
|
+
id="colorPicker"
|
|
26729
|
+
[ngModel]="mapper.settings().fillColor"
|
|
26730
|
+
(ngModelChange)="update('fillColor', $event)"
|
|
26731
|
+
/>
|
|
26732
|
+
} @case ('gradient') {
|
|
26733
|
+
<label for="gradientSelect">Gradient:</label>
|
|
26734
|
+
<input
|
|
26735
|
+
type="color"
|
|
26736
|
+
[ngModel]="mapper.settings().fillGradient[0].color"
|
|
26737
|
+
(ngModelChange)="updateGradient($event, undefined)"
|
|
26738
|
+
/>
|
|
26739
|
+
<input
|
|
26740
|
+
type="color"
|
|
26741
|
+
[ngModel]="mapper.settings().fillGradient[1].color"
|
|
26742
|
+
(ngModelChange)="updateGradient(undefined, $event)"
|
|
26743
|
+
/>
|
|
26744
|
+
} @case ('palette') {
|
|
26745
|
+
<label for="paletteSelect">Palette:</label>
|
|
26746
|
+
<mapag-palette-select
|
|
26747
|
+
[palette]="mapper.settings().fillPalette"
|
|
26748
|
+
(paletteChange)="update('fillPalette', $event)"
|
|
26749
|
+
>
|
|
26750
|
+
</mapag-palette-select>
|
|
26751
|
+
} }
|
|
26752
|
+
</div>
|
|
26753
|
+
<div class="ctrl-row">
|
|
26754
|
+
<label for="fillOpacity">Opacity:</label>
|
|
26755
|
+
<input
|
|
26756
|
+
type="range"
|
|
26757
|
+
id="fillOpacity"
|
|
26758
|
+
min="0"
|
|
26759
|
+
max="1"
|
|
26760
|
+
step="0.01"
|
|
26761
|
+
[ngModel]="mapper.settings().fillOpacity"
|
|
26762
|
+
(ngModelChange)="update('fillOpacity', $event)"
|
|
26763
|
+
/>
|
|
26764
|
+
</div>
|
|
26765
|
+
<div class="ctrl-row">
|
|
26766
|
+
<label for="borderColor">Border Color:</label>
|
|
26767
|
+
<input
|
|
26768
|
+
type="color"
|
|
26769
|
+
id="borderColor"
|
|
26770
|
+
[ngModel]="mapper.settings().borderColor"
|
|
26771
|
+
(ngModelChange)="update('borderColor', $event)"
|
|
26772
|
+
/>
|
|
26773
|
+
</div>
|
|
26774
|
+
</div>
|
|
26775
|
+
<div class="ctrl-group">
|
|
26776
|
+
<h4>Filters</h4>
|
|
26777
|
+
<h5>State</h5>
|
|
26778
|
+
<div class="filter-row" style="padding: 3px;">
|
|
26779
|
+
<ng-select
|
|
26780
|
+
[items]="USStates"
|
|
26781
|
+
bindLabel="Name"
|
|
26782
|
+
bindValue="Abbr"
|
|
26783
|
+
[ngModel]="mapper.settings().filterStates"
|
|
26784
|
+
[multiple]="true"
|
|
26785
|
+
appendTo="body"
|
|
26786
|
+
(ngModelChange)="update('filterStates', $event)"
|
|
26787
|
+
>
|
|
26788
|
+
</ng-select>
|
|
26789
|
+
</div>
|
|
26790
|
+
</div>
|
|
26791
|
+
</div>
|
|
26792
|
+
|
|
26793
|
+
<h3>References</h3>
|
|
26794
|
+
<div style="display: flex; flex-direction: column;">
|
|
26795
|
+
<a href="https://www.nass.usda.gov/" target="_blank">USDA NASS</a>
|
|
26796
|
+
<a href="https://quickstats.nass.usda.gov/" target="_blank">USDA NASS Quick Stats</a>
|
|
26797
|
+
</div>
|
|
26798
|
+
</div>
|
|
26799
|
+
<div class="dlg-buttons">
|
|
26800
|
+
<button class="btn" (click)="toggleLegend()">Legend</button>
|
|
26801
|
+
<button class="btn" (click)="remove()">Remove</button>
|
|
26802
|
+
<button class="btn" (click)="reset()">Reset</button>
|
|
26803
|
+
<mapag-show-hide-btn [mapper]="mapper"></mapag-show-hide-btn>
|
|
26804
|
+
<button class="btn" (click)="toggleDialog()">Close</button>
|
|
26805
|
+
</div>
|
|
26806
|
+
</dialog>
|
|
26807
|
+
|
|
26808
|
+
<dialog class="legend" #legendDialog draggable mapagBringToFront onbody>
|
|
26809
|
+
<mapag-dialog-header class="drag-handle"[dialog]="legendDialog">{{ mapper.name() }}</mapag-dialog-header>
|
|
26810
|
+
@switch (mapper.settings().fillType) {
|
|
26811
|
+
@case ('solid') {
|
|
26812
|
+
<div style="width: 30px; height: 30px; background-color: {{ mapper.settings().fillColor }}; border: 1px solid #000;"></div>
|
|
26813
|
+
}
|
|
26814
|
+
@case ('gradient') {
|
|
26815
|
+
<mapag-gradient-legend [settings]="gradientSettings()"> </mapag-gradient-legend>
|
|
26816
|
+
}
|
|
26817
|
+
@case ('palette') {
|
|
26818
|
+
<mapag-std-legend [items]="paletteLegend()"></mapag-std-legend>
|
|
26819
|
+
}
|
|
26820
|
+
}
|
|
26821
|
+
</dialog>
|
|
26822
|
+
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}.ctrl-group{display:flex;flex-direction:column;gap:8px}.filter-row{display:flex;flex-direction:column;margin-bottom:8px;font-size:.8em}.filter-row-cols{display:block;column-count:2}.zone{display:flex;align-items:center;gap:8px;margin:0;padding:0}.zones{display:grid;grid-template-columns:1fr 1fr;column-gap:24px;row-gap:8px;overflow-y:auto;max-height:420px}.svgicon{height:30px;width:30px;-webkit-mask-size:contain;mask-size:contain}h4,label{display:flex;align-items:center;gap:4px}.info-grid{display:grid;grid-template-columns:1fr 1fr 1fr;gap:8px;margin-bottom:16px}.info{display:flex;flex-direction:column}.info-label{font-weight:600;font-size:.7em;color:#333}.info-value{font-size:.8em;color:#555}@media (max-width: 600px){.zones{grid-template-columns:1fr}}\n"] }]
|
|
26823
|
+
}], ctorParameters: () => [], propDecorators: { map: [{ type: i0.Input, args: [{ isSignal: true, alias: "map", required: false }] }], customizeDialog: [{ type: i0.ViewChild, args: ['customizeDialog', { isSignal: true }] }], legendDialog: [{ type: i0.ViewChild, args: ['legendDialog', { isSignal: true }] }], onRemove: [{ type: i0.Output, args: ["onRemove"] }], settings: [{ type: i0.Input, args: [{ isSignal: true, alias: "settings", required: false }] }] } });
|
|
26824
|
+
|
|
26825
|
+
class ConsumerSpendingGroups {
|
|
26826
|
+
static DairyFruitVegetables = [
|
|
26827
|
+
{ ID: "X1053", Name: "Dairy Products", Level: 0 },
|
|
26828
|
+
{ ID: "X1054", Name: "Fresh Milk (All Types)", Level: 1 },
|
|
26829
|
+
{ ID: "X1055", Name: "Cream", Level: 1 },
|
|
26830
|
+
{ ID: "X1056", Name: "Butter", Level: 1 },
|
|
26831
|
+
{ ID: "X1057", Name: "Cheese", Level: 1 },
|
|
26832
|
+
{ ID: "X1058", Name: "Ice Cream & Rel Prod", Level: 1 },
|
|
26833
|
+
{ ID: "X1059", Name: "Other Dairy Products", Level: 1 },
|
|
26834
|
+
{ ID: "X1060", Name: "Fruit & Vegetables", Level: 0 },
|
|
26835
|
+
{ ID: "X1061", Name: "Fresh Fruit", Level: 1 },
|
|
26836
|
+
{ ID: "X1062", Name: "Apples", Level: 2 },
|
|
26837
|
+
{ ID: "X1063", Name: "Bananas", Level: 2 },
|
|
26838
|
+
{ ID: "X1064", Name: "Oranges", Level: 2 },
|
|
26839
|
+
{ ID: "X1065", Name: "Citrus Fruit excluding Oranges", Level: 2 },
|
|
26840
|
+
{ ID: "X1066", Name: "Other Fresh Fruit", Level: 2 },
|
|
26841
|
+
{ ID: "X1067", Name: "Fresh Vegetables", Level: 1 },
|
|
26842
|
+
{ ID: "X1068", Name: "Potatoes", Level: 2 },
|
|
26843
|
+
{ ID: "X1069", Name: "Lettuce", Level: 2 },
|
|
26844
|
+
{ ID: "X1070", Name: "Tomatoes", Level: 2 },
|
|
26845
|
+
{ ID: "X1071", Name: "Other Fresh Vegetables", Level: 2 },
|
|
26846
|
+
{ ID: "X1072", Name: "Processed Fruit", Level: 1 },
|
|
26847
|
+
{ ID: "X1073", Name: "Frozen Fruit & Juice", Level: 2 },
|
|
26848
|
+
{ ID: "X1074", Name: "Frozen Orange Juice", Level: 2 },
|
|
26849
|
+
{ ID: "X1075", Name: "Frozen Fruit", Level: 2 },
|
|
26850
|
+
{ ID: "X1076", Name: "Frozen Fruit Juice", Level: 2 },
|
|
26851
|
+
{ ID: "X1077", Name: "Canned Fruit", Level: 2 },
|
|
26852
|
+
{ ID: "X1078", Name: "Dried Fruit", Level: 2 },
|
|
26853
|
+
{ ID: "X1079", Name: "Fresh Fruit Juice", Level: 2 },
|
|
26854
|
+
{ ID: "X1080", Name: "Canned/Bottled Fruit Juice", Level: 2 },
|
|
26855
|
+
{ ID: "X1081", Name: "Processed Vegetables", Level: 2 },
|
|
26856
|
+
{ ID: "X1082", Name: "Frozen Vegetables", Level: 2 },
|
|
26857
|
+
{ ID: "X1083", Name: "Vegetables: Canned/Dried/Juice", Level: 2 },
|
|
26858
|
+
{ ID: "X1084", Name: "Canned Beans", Level: 3 },
|
|
26859
|
+
{ ID: "X1085", Name: "Canned Corn", Level: 3 },
|
|
26860
|
+
{ ID: "X1086", Name: "Misc Canned Vegetables", Level: 3 },
|
|
26861
|
+
{ ID: "X1087", Name: "Dried Beans & Peas", Level: 3 },
|
|
26862
|
+
{ ID: "X1088", Name: "Misc Dried Vegetables", Level: 3 },
|
|
26863
|
+
{ ID: "X1089", Name: "Vegetable Juice", Level: 3 },
|
|
26864
|
+
];
|
|
26865
|
+
static Alcoholic = [
|
|
26866
|
+
{ ID: "X2001", Name: "Alcoholic Beverages" },
|
|
26867
|
+
{ ID: "X2002", Name: "Alcoholic Beverage at Home", Level: 1 },
|
|
26868
|
+
{ ID: "X2003", Name: "Beer & Ale", Level: 2 },
|
|
26869
|
+
{ ID: "X2004", Name: "Whiskey", Level: 2 },
|
|
26870
|
+
{ ID: "X2005", Name: "Wine", Level: 2 },
|
|
26871
|
+
{ ID: "X2006", Name: "Other Alcoholic Beverages", Level: 2 },
|
|
26872
|
+
{ ID: "X2007", Name: "Alcoholic Beverage Away from Home", Level: 1 },
|
|
26873
|
+
{ ID: "X2008", Name: "Beer & Ale Away from Home", Level: 2 },
|
|
26874
|
+
{ ID: "X2009", Name: "Beer at Full Service Restaurants", Level: 3 },
|
|
26875
|
+
{ ID: "X2010", Name: "Beer at Fast Food Restaurants/Other", Level: 3 },
|
|
26876
|
+
{ ID: "X2011", Name: "Wine Away from Home", Level: 2 },
|
|
26877
|
+
{ ID: "X2012", Name: "Wine at Full Service Restaurants", Level: 3 },
|
|
26878
|
+
{ ID: "X2013", Name: "Wine at Fast Food Restaurants", Level: 3 },
|
|
26879
|
+
{ ID: "X2014", Name: "Other Alcohol Away from Home", Level: 2 },
|
|
26880
|
+
{ ID: "X2015", Name: "Other Alcohol at Full Service Restaurants", Level: 3 },
|
|
26881
|
+
{ ID: "X2016", Name: "Other Alcohol at Fast Food Restaurants", Level: 3 },
|
|
26882
|
+
];
|
|
26883
|
+
static BakedGoods = [
|
|
26884
|
+
{ ID: "X1004", Name: "Bakery & Cereal Prod" },
|
|
26885
|
+
{ ID: "X1005", Name: "Flour" },
|
|
26886
|
+
{ ID: "X1006", Name: "Prepared Flour Mixes" },
|
|
26887
|
+
{ ID: "X1007", Name: "Ready-to-eat & Cooked Cereal" },
|
|
26888
|
+
{ ID: "X1008", Name: "Rice" },
|
|
26889
|
+
{ ID: "X1009", Name: "Pasta/Cornmeal/Other Cereal" },
|
|
26890
|
+
{ ID: "X1010", Name: "Bread" },
|
|
26891
|
+
{ ID: "X1011", Name: "White Bread" },
|
|
26892
|
+
{ ID: "X1012", Name: "Bread excluding White" },
|
|
26893
|
+
{ ID: "X1013", Name: "Crackers & Cookies" },
|
|
26894
|
+
{ ID: "X1014", Name: "Cookies" },
|
|
26895
|
+
{ ID: "X1015", Name: "Crackers" },
|
|
26896
|
+
{ ID: "X1016", Name: "Frozen & Refrigerated Bakery Goods" },
|
|
26897
|
+
{ ID: "X1017", Name: "Other Bakery Products" },
|
|
26898
|
+
{ ID: "X1018", Name: "Fresh Biscuits/Rolls/Muffins" },
|
|
26899
|
+
{ ID: "X1019", Name: "Fresh Cakes & Cupcakes" },
|
|
26900
|
+
{ ID: "X1020", Name: "Bread & Cracker Products" },
|
|
26901
|
+
{ ID: "X1021", Name: "Sweet Rolls/Coffee Cakes/Donuts" },
|
|
26902
|
+
{ ID: "X1022", Name: "Fresh Pies/Tarts/Turnovers" },
|
|
26903
|
+
];
|
|
26904
|
+
static MeatPoultryFishEggs = [
|
|
26905
|
+
{ ID: "X1023", Name: "Meat/Poultry/Fish/Eggs" },
|
|
26906
|
+
{ ID: "X1024", Name: "Beef", Level: 1 },
|
|
26907
|
+
{ ID: "X1025", Name: "Ground Beef", Level: 2 },
|
|
26908
|
+
{ ID: "X1026", Name: "Chuck Roast", Level: 2 },
|
|
26909
|
+
{ ID: "X1027", Name: "Round Roast", Level: 2 },
|
|
26910
|
+
{ ID: "X1028", Name: "Other Roast", Level: 2 },
|
|
26911
|
+
{ ID: "X1029", Name: "Round Steak", Level: 2 },
|
|
26912
|
+
{ ID: "X1030", Name: "Sirloin Steak", Level: 2 },
|
|
26913
|
+
{ ID: "X1031", Name: "Other Steak", Level: 2 },
|
|
26914
|
+
{ ID: "X1032", Name: "Other Beef", Level: 2 },
|
|
26915
|
+
{ ID: "X1033", Name: "Pork", Level: 1 },
|
|
26916
|
+
{ ID: "X1034", Name: "Bacon", Level: 2 },
|
|
26917
|
+
{ ID: "X1035", Name: "Pork Chops", Level: 2 },
|
|
26918
|
+
{ ID: "X1036", Name: "Ham", Level: 2 },
|
|
26919
|
+
{ ID: "X1037", Name: "Pork Sausage", Level: 2 },
|
|
26920
|
+
{ ID: "X1038", Name: "Other Pork", Level: 2 },
|
|
26921
|
+
{ ID: "X1039", Name: "Other Meat", Level: 1 },
|
|
26922
|
+
{ ID: "X1040", Name: "Frankfurters", Level: 2 },
|
|
26923
|
+
{ ID: "X1041", Name: "Bologna/Liverwurst/Salami", Level: 2 },
|
|
26924
|
+
{ ID: "X1042", Name: "Other Lunchmeat", Level: 2 },
|
|
26925
|
+
{ ID: "X1043", Name: "Lamb & Other Meat", Level: 2 },
|
|
26926
|
+
{ ID: "X1044", Name: "Poultry", Level: 1 },
|
|
26927
|
+
{ ID: "X1045", Name: "Whole Chickens", Level: 2 },
|
|
26928
|
+
{ ID: "X1046", Name: "Chicken Parts", Level: 2 },
|
|
26929
|
+
{ ID: "X1047", Name: "Other Poultry", Level: 2 },
|
|
26930
|
+
{ ID: "X1048", Name: "Seafood", Level: 1 },
|
|
26931
|
+
{ ID: "X1049", Name: "Canned Fish & Shellfish", Level: 2 },
|
|
26932
|
+
{ ID: "X1050", Name: "Fresh Fish & Shellfish", Level: 2 },
|
|
26933
|
+
{ ID: "X1051", Name: "Frozen Fish & Shellfish", Level: 2 },
|
|
26934
|
+
{ ID: "X1052", Name: "Eggs", Level: 1 },
|
|
26935
|
+
];
|
|
26936
|
+
static Groups = [
|
|
26937
|
+
{ ID: "dairy", Name: "Dairy / Fruit and Vegetables", Children: ConsumerSpendingGroups.DairyFruitVegetables },
|
|
26938
|
+
{ ID: "alcholoic", Name: "Alcoholic Beverages", Children: ConsumerSpendingGroups.Alcoholic },
|
|
26939
|
+
{ ID: "baked", Name: "Bakery & Cereal Prod", Children: ConsumerSpendingGroups.BakedGoods },
|
|
26940
|
+
{ ID: "meat", Name: "Meat / Poultry / Fish / Eggs", Children: ConsumerSpendingGroups.MeatPoultryFishEggs }
|
|
26941
|
+
];
|
|
26942
|
+
static All() {
|
|
26943
|
+
const all = [];
|
|
26944
|
+
const dairy = ConsumerSpendingGroups.DairyFruitVegetables.map(i => {
|
|
26945
|
+
return {
|
|
26946
|
+
ID: i.ID,
|
|
26947
|
+
Name: i.Name,
|
|
26948
|
+
Level: i.Level,
|
|
26949
|
+
Parent: "Dairy / Fruit and Vegetables"
|
|
26950
|
+
};
|
|
26951
|
+
});
|
|
26952
|
+
const alcholoic = ConsumerSpendingGroups.Alcoholic.map(i => {
|
|
26953
|
+
return {
|
|
26954
|
+
ID: i.ID,
|
|
26955
|
+
Name: i.Name,
|
|
26956
|
+
Level: i.Level,
|
|
26957
|
+
Parent: "Alcoholic Beverages"
|
|
26958
|
+
};
|
|
26959
|
+
});
|
|
26960
|
+
const baked = ConsumerSpendingGroups.BakedGoods.map(i => {
|
|
26961
|
+
return {
|
|
26962
|
+
ID: i.ID,
|
|
26963
|
+
Name: i.Name,
|
|
26964
|
+
Level: i.Level,
|
|
26965
|
+
Parent: "Bakery & Cereal Prod"
|
|
26966
|
+
};
|
|
26967
|
+
});
|
|
26968
|
+
const meat = ConsumerSpendingGroups.MeatPoultryFishEggs.map(i => {
|
|
26969
|
+
return {
|
|
26970
|
+
ID: i.ID,
|
|
26971
|
+
Name: i.Name,
|
|
26972
|
+
Level: i.Level,
|
|
26973
|
+
Parent: "Meat / Poultry / Fish / Eggs"
|
|
26974
|
+
};
|
|
26975
|
+
});
|
|
26976
|
+
return [...dairy, ...alcholoic, ...baked, ...meat];
|
|
26977
|
+
}
|
|
26978
|
+
}
|
|
26979
|
+
|
|
26980
|
+
class ConsumerSpendingSelectPanel {
|
|
26981
|
+
faCircle = faCircle;
|
|
26982
|
+
faFire = faFire;
|
|
26983
|
+
faThLarge = faThLarge;
|
|
26984
|
+
faList = faList;
|
|
26985
|
+
options = ConsumerSpendingGroups.Groups;
|
|
26986
|
+
nassSvc = inject(NassService);
|
|
26987
|
+
canAdd = input(true, ...(ngDevMode ? [{ debugName: "canAdd" }] : []));
|
|
26988
|
+
// Map Component
|
|
26989
|
+
map = input(...(ngDevMode ? [undefined, { debugName: "map" }] : []));
|
|
26990
|
+
// Currently selected NAICS codes
|
|
26991
|
+
current = model([], ...(ngDevMode ? [{ debugName: "current" }] : []));
|
|
26992
|
+
customizeDialog = viewChild('customizeDialog', ...(ngDevMode ? [{ debugName: "customizeDialog" }] : []));
|
|
26993
|
+
// Mapper group to hold NAICS layers
|
|
26994
|
+
mappers = new MapboxMapperGroup();
|
|
26995
|
+
constructor() {
|
|
26996
|
+
const _mapInit = effect(() => {
|
|
26997
|
+
const mapComp = this.map();
|
|
26998
|
+
if (mapComp) {
|
|
26999
|
+
mapComp.mapper().set('naicsmgr', this.mappers);
|
|
27000
|
+
}
|
|
27001
|
+
}, ...(ngDevMode ? [{ debugName: "_mapInit" }] : []));
|
|
27002
|
+
}
|
|
27003
|
+
isSelected(code) {
|
|
27004
|
+
return this.current().some((c) => c.ID === code.ID);
|
|
27005
|
+
}
|
|
27006
|
+
selectInfo(info) {
|
|
27007
|
+
const currentInfos = this.current();
|
|
27008
|
+
const index = currentInfos.findIndex((c) => c.ID === info.ID);
|
|
27009
|
+
if (index >= 0) {
|
|
27010
|
+
// Remove if already selected
|
|
27011
|
+
this.current.set(currentInfos.filter((c) => c.ID !== info.ID));
|
|
27012
|
+
}
|
|
27013
|
+
else {
|
|
27014
|
+
// Add if not selected - ensure no duplicates
|
|
27015
|
+
const newInfos = [...currentInfos, info];
|
|
27016
|
+
// Remove any potential duplicates by creating a Map
|
|
27017
|
+
const uniqueMap = new Map(newInfos.map((c) => [c.ID, c]));
|
|
27018
|
+
this.current.set(Array.from(uniqueMap.values()));
|
|
27019
|
+
}
|
|
27020
|
+
}
|
|
27021
|
+
removeInfo(info) {
|
|
27022
|
+
const currentInfos = this.current();
|
|
27023
|
+
this.current.set(currentInfos.filter((c) => c.ID !== info.ID));
|
|
27024
|
+
}
|
|
27025
|
+
toggleDialog() {
|
|
27026
|
+
const dialog = this.customizeDialog();
|
|
27027
|
+
if (!dialog) {
|
|
27028
|
+
return;
|
|
27029
|
+
}
|
|
27030
|
+
const dialogElement = dialog.nativeElement;
|
|
27031
|
+
if (dialogElement.open) {
|
|
27032
|
+
dialogElement.close();
|
|
27033
|
+
}
|
|
27034
|
+
else {
|
|
27035
|
+
dialogElement.show();
|
|
27036
|
+
}
|
|
27037
|
+
}
|
|
27038
|
+
fixTextSet(input) {
|
|
27039
|
+
const output = [];
|
|
27040
|
+
input.forEach((text) => {
|
|
27041
|
+
output.push({ key: text, value: this.fixText(text) });
|
|
27042
|
+
});
|
|
27043
|
+
return output;
|
|
27044
|
+
}
|
|
27045
|
+
fixText(text) {
|
|
27046
|
+
const parts = text
|
|
27047
|
+
.toLocaleLowerCase()
|
|
27048
|
+
.split('_')
|
|
27049
|
+
.map((part) => part.charAt(0).toUpperCase() + part.slice(1));
|
|
27050
|
+
return parts.join(' ');
|
|
27051
|
+
}
|
|
27052
|
+
reset() {
|
|
27053
|
+
}
|
|
27054
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: ConsumerSpendingSelectPanel, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
27055
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.15", type: ConsumerSpendingSelectPanel, isStandalone: true, selector: "mapag-consumer-spending-select-panel", inputs: { canAdd: { classPropertyName: "canAdd", publicName: "canAdd", isSignal: true, isRequired: false, transformFunction: null }, map: { classPropertyName: "map", publicName: "map", isSignal: true, isRequired: false, transformFunction: null }, current: { classPropertyName: "current", publicName: "current", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { current: "currentChange" }, viewQueries: [{ propertyName: "customizeDialog", first: true, predicate: ["customizeDialog"], descendants: true, isSignal: true }], ngImport: i0, template: `
|
|
27056
|
+
<mapag-details [open]="true" style="margin-top: 16px;">
|
|
27057
|
+
<span summary>Consumer Spending</span>
|
|
27058
|
+
|
|
27059
|
+
<!-- @for (info of current(); track info.ID) {
|
|
27060
|
+
<hub-nass-panel [map]="map()" [settings]="inf" (onRemove)="removeInfo(info)"></hub-nass-panel>
|
|
27061
|
+
} -->
|
|
27062
|
+
|
|
27063
|
+
@if (canAdd()) {
|
|
27064
|
+
<button class="mgr-btn" (click)="toggleDialog()" style="justify-self: center;">Add & Remove Layers</button>
|
|
27065
|
+
}
|
|
27066
|
+
</mapag-details>
|
|
27067
|
+
<dialog draggable mapagBringToFront onBody #customizeDialog>
|
|
27068
|
+
<h2>Consumer Spending Layers</h2>
|
|
27069
|
+
|
|
27070
|
+
<div class="dlg-body">
|
|
27071
|
+
<p>
|
|
27072
|
+
Select a consumer spending category from the list below to add it as a layer on the map. You can select multiple
|
|
27073
|
+
categories to compare them. Use the filters to narrow down the options. The data is sourced from the USDA Economic
|
|
27074
|
+
Research Service and represents average annual consumer spending in the United States for various food categories.
|
|
27075
|
+
</p>
|
|
27076
|
+
|
|
27077
|
+
<div class="zones results">
|
|
27078
|
+
@for (group of options; track group.ID) {
|
|
27079
|
+
<h3>{{group.Name}}</h3>
|
|
27080
|
+
@for (item of group.Children; track item.ID) {
|
|
27081
|
+
<label>
|
|
27082
|
+
<input type="checkbox" [checked]="isSelected(item)" (change)="selectInfo(item)" [ngClass]="'indent-' + (item.Level || 0)">
|
|
27083
|
+
{{item.Name}}
|
|
27084
|
+
</label>
|
|
27085
|
+
}
|
|
27086
|
+
}
|
|
27087
|
+
</div>
|
|
27088
|
+
|
|
27089
|
+
<h3>References</h3>
|
|
27090
|
+
<div style="display: flex; flex-direction: column;">
|
|
27091
|
+
<a href="https://doc.arcgis.com/en/esri-demographics/latest/esri-demographics/consumer-spending.htm" target="_blank">ESRi Consumer Spending Data</a>
|
|
27092
|
+
</div>
|
|
27093
|
+
</div>
|
|
27094
|
+
<div class="dlg-buttons">
|
|
27095
|
+
<button class="btn" (click)="reset()">Reset</button>
|
|
27096
|
+
<button class="btn" (click)="toggleDialog()">Close</button>
|
|
27097
|
+
</div>
|
|
27098
|
+
</dialog>
|
|
27099
|
+
`, isInline: true, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}.zones{font-size:.8em}.indent-1{margin-left:16px}.indent-2{margin-left:32px}.filters{display:flex;gap:8px;margin-bottom:8px;flex-wrap:wrap;flex-direction:row}.results{overflow-y:auto}.resultcont{display:flex;flex-direction:column;flex-grow:1}.search{display:flex;gap:4px;align-items:center;margin-bottom:8px;font-size:.8em}.search input[type=radio]{display:none}.search label{display:flex;align-items:center;gap:4px;padding:2px 4px;border:1px solid transparent;cursor:pointer}.search label:has(input[type=radio]:checked){border:1px solid #333;border-radius:4px;background-color:#f0f0f0}.filters select{padding:3px;border:1px solid grey;border-radius:4px}.filters label{font-size:.8em;font-weight:600}dialog h4{display:flex;justify-content:space-between;align-items:center;margin-bottom:4px;margin-top:4px}.ctrl-row{grid-template-columns:1fr;font-size:.8em}.zones{max-height:400px;height:400px;overflow-y:auto;margin-top:0}input[type=search]{width:100%;font-size:1em;padding:4px 8px;border-radius:4px;border:1px solid #ccc}label{display:flex;align-items:center;gap:4px}@media (max-width: 600px){.dlg-body{display:flex;flex-direction:column}.zones{max-height:unset;height:auto;flex-grow:1}}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: DraggableDialogDirective, selector: "dialog[draggable]" }, { kind: "directive", type: BringToFrontDirective, selector: "[mapagBringToFront]" }, { kind: "component", type: MapagDetails, selector: "mapag-details", inputs: ["open"] }, { kind: "directive", type: OnBodyDirective, selector: "dialog[onBody]" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
25655
27100
|
}
|
|
25656
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type:
|
|
27101
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: ConsumerSpendingSelectPanel, decorators: [{
|
|
25657
27102
|
type: Component,
|
|
25658
|
-
args: [{ selector: 'mapag-
|
|
25659
|
-
<
|
|
25660
|
-
<
|
|
25661
|
-
|
|
25662
|
-
|
|
25663
|
-
|
|
25664
|
-
|
|
27103
|
+
args: [{ selector: 'mapag-consumer-spending-select-panel', changeDetection: ChangeDetectionStrategy.OnPush, imports: [CommonModule, FormsModule, DraggableDialogDirective, BringToFrontDirective, MapagDetails, OnBodyDirective], template: `
|
|
27104
|
+
<mapag-details [open]="true" style="margin-top: 16px;">
|
|
27105
|
+
<span summary>Consumer Spending</span>
|
|
27106
|
+
|
|
27107
|
+
<!-- @for (info of current(); track info.ID) {
|
|
27108
|
+
<hub-nass-panel [map]="map()" [settings]="inf" (onRemove)="removeInfo(info)"></hub-nass-panel>
|
|
27109
|
+
} -->
|
|
27110
|
+
|
|
27111
|
+
@if (canAdd()) {
|
|
27112
|
+
<button class="mgr-btn" (click)="toggleDialog()" style="justify-self: center;">Add & Remove Layers</button>
|
|
27113
|
+
}
|
|
27114
|
+
</mapag-details>
|
|
27115
|
+
<dialog draggable mapagBringToFront onBody #customizeDialog>
|
|
27116
|
+
<h2>Consumer Spending Layers</h2>
|
|
27117
|
+
|
|
27118
|
+
<div class="dlg-body">
|
|
27119
|
+
<p>
|
|
27120
|
+
Select a consumer spending category from the list below to add it as a layer on the map. You can select multiple
|
|
27121
|
+
categories to compare them. Use the filters to narrow down the options. The data is sourced from the USDA Economic
|
|
27122
|
+
Research Service and represents average annual consumer spending in the United States for various food categories.
|
|
27123
|
+
</p>
|
|
27124
|
+
|
|
27125
|
+
<div class="zones results">
|
|
27126
|
+
@for (group of options; track group.ID) {
|
|
27127
|
+
<h3>{{group.Name}}</h3>
|
|
27128
|
+
@for (item of group.Children; track item.ID) {
|
|
27129
|
+
<label>
|
|
27130
|
+
<input type="checkbox" [checked]="isSelected(item)" (change)="selectInfo(item)" [ngClass]="'indent-' + (item.Level || 0)">
|
|
27131
|
+
{{item.Name}}
|
|
27132
|
+
</label>
|
|
27133
|
+
}
|
|
27134
|
+
}
|
|
27135
|
+
</div>
|
|
27136
|
+
|
|
27137
|
+
<h3>References</h3>
|
|
27138
|
+
<div style="display: flex; flex-direction: column;">
|
|
27139
|
+
<a href="https://doc.arcgis.com/en/esri-demographics/latest/esri-demographics/consumer-spending.htm" target="_blank">ESRi Consumer Spending Data</a>
|
|
27140
|
+
</div>
|
|
27141
|
+
</div>
|
|
27142
|
+
<div class="dlg-buttons">
|
|
27143
|
+
<button class="btn" (click)="reset()">Reset</button>
|
|
27144
|
+
<button class="btn" (click)="toggleDialog()">Close</button>
|
|
27145
|
+
</div>
|
|
27146
|
+
</dialog>
|
|
27147
|
+
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}.zones{font-size:.8em}.indent-1{margin-left:16px}.indent-2{margin-left:32px}.filters{display:flex;gap:8px;margin-bottom:8px;flex-wrap:wrap;flex-direction:row}.results{overflow-y:auto}.resultcont{display:flex;flex-direction:column;flex-grow:1}.search{display:flex;gap:4px;align-items:center;margin-bottom:8px;font-size:.8em}.search input[type=radio]{display:none}.search label{display:flex;align-items:center;gap:4px;padding:2px 4px;border:1px solid transparent;cursor:pointer}.search label:has(input[type=radio]:checked){border:1px solid #333;border-radius:4px;background-color:#f0f0f0}.filters select{padding:3px;border:1px solid grey;border-radius:4px}.filters label{font-size:.8em;font-weight:600}dialog h4{display:flex;justify-content:space-between;align-items:center;margin-bottom:4px;margin-top:4px}.ctrl-row{grid-template-columns:1fr;font-size:.8em}.zones{max-height:400px;height:400px;overflow-y:auto;margin-top:0}input[type=search]{width:100%;font-size:1em;padding:4px 8px;border-radius:4px;border:1px solid #ccc}label{display:flex;align-items:center;gap:4px}@media (max-width: 600px){.dlg-body{display:flex;flex-direction:column}.zones{max-height:unset;height:auto;flex-grow:1}}\n"] }]
|
|
27148
|
+
}], ctorParameters: () => [], propDecorators: { canAdd: [{ type: i0.Input, args: [{ isSignal: true, alias: "canAdd", required: false }] }], map: [{ type: i0.Input, args: [{ isSignal: true, alias: "map", required: false }] }], current: [{ type: i0.Input, args: [{ isSignal: true, alias: "current", required: false }] }, { type: i0.Output, args: ["currentChange"] }], customizeDialog: [{ type: i0.ViewChild, args: ['customizeDialog', { isSignal: true }] }] } });
|
|
25665
27149
|
|
|
25666
27150
|
class HubCropSequencePanel {
|
|
25667
27151
|
DefaultName = 'cropsequence';
|
|
@@ -25846,59 +27330,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImpo
|
|
|
25846
27330
|
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}dialog{max-width:700px}.zones{display:grid;grid-template-columns:1fr 1fr;column-gap:16px;row-gap:8px;overflow-y:auto;max-height:420px}@media (max-width: 600px){.zones{grid-template-columns:1fr}}\n"] }]
|
|
25847
27331
|
}], ctorParameters: () => [], propDecorators: { map: [{ type: i0.Input, args: [{ isSignal: true, alias: "map", required: false }] }], customizeDialog: [{ type: i0.ViewChild, args: ['customizeDialog', { isSignal: true }] }] } });
|
|
25848
27332
|
|
|
25849
|
-
class DialogHeader {
|
|
25850
|
-
faTimes = faTimes;
|
|
25851
|
-
dialog = input(...(ngDevMode ? [undefined, { debugName: "dialog" }] : []));
|
|
25852
|
-
close() {
|
|
25853
|
-
// Close the dialog by finding the closest dialog element and calling its close method
|
|
25854
|
-
const d = this.dialog();
|
|
25855
|
-
if (d) {
|
|
25856
|
-
d.close();
|
|
25857
|
-
}
|
|
25858
|
-
}
|
|
25859
|
-
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: DialogHeader, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
25860
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "20.3.15", type: DialogHeader, isStandalone: true, selector: "mapag-dialog-header", inputs: { dialog: { classPropertyName: "dialog", publicName: "dialog", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
25861
|
-
<h2><ng-content></ng-content></h2>
|
|
25862
|
-
<button class="btn-icon" (click)="close()"><fa-icon [icon]="faTimes" size="lg"></fa-icon></button>
|
|
25863
|
-
`, isInline: true, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}:host{display:flex;align-items:center}:host:first-child{flex-grow:1}:host h2{margin:0;flex-grow:1}.btn-icon{padding:2px;border:none;background:transparent;cursor:pointer;border-radius:4px;color:gray}.btn-icon:hover{color:#000;background-color:transparent}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "component", type: FaIconComponent, selector: "fa-icon", inputs: ["icon", "title", "animation", "mask", "flip", "size", "pull", "border", "inverse", "symbol", "rotate", "fixedWidth", "transform", "a11yRole"], outputs: ["iconChange", "titleChange", "animationChange", "maskChange", "flipChange", "sizeChange", "pullChange", "borderChange", "inverseChange", "symbolChange", "rotateChange", "fixedWidthChange", "transformChange", "a11yRoleChange"] }] });
|
|
25864
|
-
}
|
|
25865
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: DialogHeader, decorators: [{
|
|
25866
|
-
type: Component,
|
|
25867
|
-
args: [{ selector: 'mapag-dialog-header', imports: [CommonModule, FaIconComponent], template: `
|
|
25868
|
-
<h2><ng-content></ng-content></h2>
|
|
25869
|
-
<button class="btn-icon" (click)="close()"><fa-icon [icon]="faTimes" size="lg"></fa-icon></button>
|
|
25870
|
-
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}:host{display:flex;align-items:center}:host:first-child{flex-grow:1}:host h2{margin:0;flex-grow:1}.btn-icon{padding:2px;border:none;background:transparent;cursor:pointer;border-radius:4px;color:gray}.btn-icon:hover{color:#000;background-color:transparent}\n"] }]
|
|
25871
|
-
}], propDecorators: { dialog: [{ type: i0.Input, args: [{ isSignal: true, alias: "dialog", required: false }] }] } });
|
|
25872
|
-
|
|
25873
|
-
class StdLegend {
|
|
25874
|
-
items = input([], ...(ngDevMode ? [{ debugName: "items" }] : []));
|
|
25875
|
-
columns = input(1, ...(ngDevMode ? [{ debugName: "columns" }] : []));
|
|
25876
|
-
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: StdLegend, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
25877
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.15", type: StdLegend, isStandalone: true, selector: "mapag-std-legend", inputs: { items: { classPropertyName: "items", publicName: "items", isSignal: true, isRequired: false, transformFunction: null }, columns: { classPropertyName: "columns", publicName: "columns", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
25878
|
-
<div class="legend" [style.grid-template-columns]="'repeat(' + columns() + ',1fr)'">
|
|
25879
|
-
@for (item of items(); track item) {
|
|
25880
|
-
<div class="legend-row">
|
|
25881
|
-
<div class="legend-item" [style.background-color]="item.value" [ngStyle]="item.style"></div>
|
|
25882
|
-
<div>{{ item.label }}</div>
|
|
25883
|
-
</div>
|
|
25884
|
-
}
|
|
25885
|
-
</div>
|
|
25886
|
-
`, isInline: true, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}.legend{display:grid;column-gap:8px;font-size:.8em}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }] });
|
|
25887
|
-
}
|
|
25888
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: StdLegend, decorators: [{
|
|
25889
|
-
type: Component,
|
|
25890
|
-
args: [{ selector: 'mapag-std-legend', imports: [CommonModule], template: `
|
|
25891
|
-
<div class="legend" [style.grid-template-columns]="'repeat(' + columns() + ',1fr)'">
|
|
25892
|
-
@for (item of items(); track item) {
|
|
25893
|
-
<div class="legend-row">
|
|
25894
|
-
<div class="legend-item" [style.background-color]="item.value" [ngStyle]="item.style"></div>
|
|
25895
|
-
<div>{{ item.label }}</div>
|
|
25896
|
-
</div>
|
|
25897
|
-
}
|
|
25898
|
-
</div>
|
|
25899
|
-
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}.legend{display:grid;column-gap:8px;font-size:.8em}\n"] }]
|
|
25900
|
-
}], propDecorators: { items: [{ type: i0.Input, args: [{ isSignal: true, alias: "items", required: false }] }], columns: [{ type: i0.Input, args: [{ isSignal: true, alias: "columns", required: false }] }] } });
|
|
25901
|
-
|
|
25902
27333
|
class HubCroplandPanel {
|
|
25903
27334
|
DefaultName = 'cropland';
|
|
25904
27335
|
faImage = faImage;
|
|
@@ -27341,91 +28772,21 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImpo
|
|
|
27341
28772
|
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}dialog{max-width:700px}.zone{display:flex;align-items:center;gap:8px;margin:0;padding:0;font-size:11pt}.zones{display:grid;grid-template-columns:1fr 1fr;column-gap:16px;row-gap:8px}@media (max-width: 600px){.zones{grid-template-columns:1fr}}\n"] }]
|
|
27342
28773
|
}], ctorParameters: () => [], propDecorators: { map: [{ type: i0.Input, args: [{ isSignal: true, alias: "map", required: false }] }], customizeDialog: [{ type: i0.ViewChild, args: ['customizeDialog', { isSignal: true }] }], legendDialog: [{ type: i0.ViewChild, args: ['legendDialog', { isSignal: true }] }] } });
|
|
27343
28774
|
|
|
27344
|
-
class
|
|
27345
|
-
|
|
27346
|
-
|
|
27347
|
-
|
|
27348
|
-
|
|
27349
|
-
onSelect = output();
|
|
27350
|
-
dataDialog = viewChild('dataDialog', ...(ngDevMode ? [{ debugName: "dataDialog" }] : []));
|
|
27351
|
-
defaultTemplate = viewChild('defaultTemplate', ...(ngDevMode ? [{ debugName: "defaultTemplate" }] : []));
|
|
27352
|
-
toggle() {
|
|
27353
|
-
const dialog = this.dataDialog();
|
|
27354
|
-
if (!dialog) {
|
|
27355
|
-
return;
|
|
27356
|
-
}
|
|
27357
|
-
const dialogElement = dialog.nativeElement;
|
|
27358
|
-
if (dialogElement.open) {
|
|
27359
|
-
dialogElement.close();
|
|
27360
|
-
}
|
|
27361
|
-
else {
|
|
27362
|
-
dialogElement.show();
|
|
28775
|
+
class SafeHtmlPipe {
|
|
28776
|
+
sanitizer = inject(DomSanitizer);
|
|
28777
|
+
transform(url) {
|
|
28778
|
+
if (!url) {
|
|
28779
|
+
return undefined;
|
|
27363
28780
|
}
|
|
28781
|
+
return this.sanitizer.bypassSecurityTrustHtml(url);
|
|
27364
28782
|
}
|
|
27365
|
-
|
|
27366
|
-
|
|
27367
|
-
this.onSelect.emit(feature);
|
|
27368
|
-
}
|
|
27369
|
-
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: TileDialog, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
27370
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.15", type: TileDialog, isStandalone: true, selector: "mapag-tile-dialog", inputs: { data: { classPropertyName: "data", publicName: "data", isSignal: true, isRequired: false, transformFunction: null }, name: { classPropertyName: "name", publicName: "name", isSignal: true, isRequired: false, transformFunction: null }, contentTemplate: { classPropertyName: "contentTemplate", publicName: "contentTemplate", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { onSelect: "onSelect" }, viewQueries: [{ propertyName: "dataDialog", first: true, predicate: ["dataDialog"], descendants: true, isSignal: true }, { propertyName: "defaultTemplate", first: true, predicate: ["defaultTemplate"], descendants: true, isSignal: true }], ngImport: i0, template: `
|
|
27371
|
-
<ng-template #defaultTemplate let-feature>
|
|
27372
|
-
<div>{{ feature }}</div>
|
|
27373
|
-
</ng-template>
|
|
27374
|
-
<dialog draggable mapagBringToFront onBody #dataDialog class="data-dialog">
|
|
27375
|
-
<h2>{{ name() }}</h2>
|
|
27376
|
-
<div class="dlg-body dlg-body-list ">
|
|
27377
|
-
{{ data()?.length }} records matching current filters.
|
|
27378
|
-
@if (data()?.length === 0) {
|
|
27379
|
-
<p>No data to display.</p>
|
|
27380
|
-
} @else {
|
|
27381
|
-
<cdk-virtual-scroll-viewport [itemSize]="10">
|
|
27382
|
-
<div *cdkVirtualFor="let feature of data()" (click)="onClick(feature)">
|
|
27383
|
-
<ng-container *ngTemplateOutlet="contentTemplate() || defaultTemplate; context: { $implicit: feature }"></ng-container>
|
|
27384
|
-
</div>
|
|
27385
|
-
</cdk-virtual-scroll-viewport>
|
|
27386
|
-
}
|
|
27387
|
-
</div>
|
|
27388
|
-
<div class="dlg-buttons">
|
|
27389
|
-
<button class="btn" (click)="toggle()">Close</button>
|
|
27390
|
-
</div>
|
|
27391
|
-
</dialog>
|
|
27392
|
-
`, isInline: true, styles: [""], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgTemplateOutlet, selector: "[ngTemplateOutlet]", inputs: ["ngTemplateOutletContext", "ngTemplateOutlet", "ngTemplateOutletInjector"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: DraggableDialogDirective, selector: "dialog[draggable]" }, { kind: "directive", type: BringToFrontDirective, selector: "[mapagBringToFront]" }, { kind: "directive", type: OnBodyDirective, selector: "dialog[onBody]" }, { kind: "component", type: CdkVirtualScrollViewport, selector: "cdk-virtual-scroll-viewport", inputs: ["orientation", "appendOnly"], outputs: ["scrolledIndexChange"] }, { kind: "directive", type: CdkVirtualForOf, selector: "[cdkVirtualFor][cdkVirtualForOf]", inputs: ["cdkVirtualForOf", "cdkVirtualForTrackBy", "cdkVirtualForTemplate", "cdkVirtualForTemplateCacheSize"] }, { kind: "directive", type: CdkFixedSizeVirtualScroll, selector: "cdk-virtual-scroll-viewport[itemSize]", inputs: ["itemSize", "minBufferPx", "maxBufferPx"] }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
28783
|
+
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: SafeHtmlPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
|
|
28784
|
+
static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "20.3.15", ngImport: i0, type: SafeHtmlPipe, isStandalone: true, name: "safeHtml" });
|
|
27393
28785
|
}
|
|
27394
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type:
|
|
27395
|
-
type:
|
|
27396
|
-
args: [{
|
|
27397
|
-
|
|
27398
|
-
FormsModule,
|
|
27399
|
-
DraggableDialogDirective,
|
|
27400
|
-
BringToFrontDirective,
|
|
27401
|
-
OnBodyDirective,
|
|
27402
|
-
CdkVirtualScrollViewport,
|
|
27403
|
-
CdkVirtualForOf,
|
|
27404
|
-
CdkFixedSizeVirtualScroll,
|
|
27405
|
-
], template: `
|
|
27406
|
-
<ng-template #defaultTemplate let-feature>
|
|
27407
|
-
<div>{{ feature }}</div>
|
|
27408
|
-
</ng-template>
|
|
27409
|
-
<dialog draggable mapagBringToFront onBody #dataDialog class="data-dialog">
|
|
27410
|
-
<h2>{{ name() }}</h2>
|
|
27411
|
-
<div class="dlg-body dlg-body-list ">
|
|
27412
|
-
{{ data()?.length }} records matching current filters.
|
|
27413
|
-
@if (data()?.length === 0) {
|
|
27414
|
-
<p>No data to display.</p>
|
|
27415
|
-
} @else {
|
|
27416
|
-
<cdk-virtual-scroll-viewport [itemSize]="10">
|
|
27417
|
-
<div *cdkVirtualFor="let feature of data()" (click)="onClick(feature)">
|
|
27418
|
-
<ng-container *ngTemplateOutlet="contentTemplate() || defaultTemplate; context: { $implicit: feature }"></ng-container>
|
|
27419
|
-
</div>
|
|
27420
|
-
</cdk-virtual-scroll-viewport>
|
|
27421
|
-
}
|
|
27422
|
-
</div>
|
|
27423
|
-
<div class="dlg-buttons">
|
|
27424
|
-
<button class="btn" (click)="toggle()">Close</button>
|
|
27425
|
-
</div>
|
|
27426
|
-
</dialog>
|
|
27427
|
-
` }]
|
|
27428
|
-
}], propDecorators: { data: [{ type: i0.Input, args: [{ isSignal: true, alias: "data", required: false }] }], name: [{ type: i0.Input, args: [{ isSignal: true, alias: "name", required: false }] }], contentTemplate: [{ type: i0.Input, args: [{ isSignal: true, alias: "contentTemplate", required: false }] }], onSelect: [{ type: i0.Output, args: ["onSelect"] }], dataDialog: [{ type: i0.ViewChild, args: ['dataDialog', { isSignal: true }] }], defaultTemplate: [{ type: i0.ViewChild, args: ['defaultTemplate', { isSignal: true }] }] } });
|
|
28786
|
+
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: SafeHtmlPipe, decorators: [{
|
|
28787
|
+
type: Pipe,
|
|
28788
|
+
args: [{ name: 'safeHtml' }]
|
|
28789
|
+
}] });
|
|
27429
28790
|
|
|
27430
28791
|
class MMPanel {
|
|
27431
28792
|
// Icons and static data
|
|
@@ -27439,8 +28800,10 @@ class MMPanel {
|
|
|
27439
28800
|
USStates = states;
|
|
27440
28801
|
map = input(...(ngDevMode ? [undefined, { debugName: "map" }] : []));
|
|
27441
28802
|
settings = input(new PointDataMapperSettings(), ...(ngDevMode ? [{ debugName: "settings" }] : []));
|
|
27442
|
-
|
|
28803
|
+
popupRenderer = new MarketMakerPopupRenderer();
|
|
28804
|
+
mapper = new PointDataMapper(this.popupRenderer);
|
|
27443
28805
|
customizeDialog = viewChild('customizeDialog', ...(ngDevMode ? [{ debugName: "customizeDialog" }] : []));
|
|
28806
|
+
dataDialog = viewChild('dataDialog', ...(ngDevMode ? [{ debugName: "dataDialog" }] : []));
|
|
27444
28807
|
onRemove = output();
|
|
27445
28808
|
style = computed(() => {
|
|
27446
28809
|
const sel = this.mapper.settings().type;
|
|
@@ -27556,10 +28919,17 @@ class MMPanel {
|
|
|
27556
28919
|
this.mapper.clear();
|
|
27557
28920
|
}
|
|
27558
28921
|
toggleData() {
|
|
27559
|
-
|
|
28922
|
+
ToggleDialog(this.dataDialog);
|
|
28923
|
+
}
|
|
28924
|
+
onTileClick(feature) {
|
|
28925
|
+
const comp = this.map();
|
|
28926
|
+
if (!comp) {
|
|
28927
|
+
return;
|
|
28928
|
+
}
|
|
28929
|
+
flyToFeature(comp.map, feature);
|
|
27560
28930
|
}
|
|
27561
28931
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: MMPanel, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
27562
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.15", type: MMPanel, isStandalone: true, selector: "mapag-mm-panel", inputs: { map: { classPropertyName: "map", publicName: "map", isSignal: true, isRequired: false, transformFunction: null }, settings: { classPropertyName: "settings", publicName: "settings", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { onRemove: "onRemove" }, viewQueries: [{ propertyName: "customizeDialog", first: true, predicate: ["customizeDialog"], descendants: true, isSignal: true }], ngImport: i0, template: `
|
|
28932
|
+
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.0.0", version: "20.3.15", type: MMPanel, isStandalone: true, selector: "mapag-mm-panel", inputs: { map: { classPropertyName: "map", publicName: "map", isSignal: true, isRequired: false, transformFunction: null }, settings: { classPropertyName: "settings", publicName: "settings", isSignal: true, isRequired: false, transformFunction: null } }, outputs: { onRemove: "onRemove" }, viewQueries: [{ propertyName: "customizeDialog", first: true, predicate: ["customizeDialog"], descendants: true, isSignal: true }, { propertyName: "dataDialog", first: true, predicate: ["dataDialog"], descendants: true, isSignal: true }], ngImport: i0, template: `
|
|
27563
28933
|
<hub-data-layer [visible]="mapper.settings().visible" [name]="mapper.settings().name"
|
|
27564
28934
|
[desc]="mapper.settings().description || 'MarketMaker Business'" shape="point" (onCheck)="setVisible($event)" (onCustomize)="toggleDialog()">
|
|
27565
28935
|
|
|
@@ -27700,7 +29070,7 @@ class MMPanel {
|
|
|
27700
29070
|
</div>
|
|
27701
29071
|
<div class="dlg-buttons">
|
|
27702
29072
|
<button class="btn" (click)="toggleLegend()">Legend</button>
|
|
27703
|
-
|
|
29073
|
+
<button class="btn" (click)="toggleData()">Data</button>
|
|
27704
29074
|
<button class="btn" (click)="remove()">Remove</button>
|
|
27705
29075
|
<button class="btn" (click)="reset()">Reset</button>
|
|
27706
29076
|
<button class="btn" (click)="toggleShowHide()">
|
|
@@ -27711,6 +29081,21 @@ class MMPanel {
|
|
|
27711
29081
|
</div>
|
|
27712
29082
|
</dialog>
|
|
27713
29083
|
|
|
29084
|
+
<dialog draggable mapagBringToFront onBody #dataDialog class="data-dialog">
|
|
29085
|
+
<h2>{{mapper.settings().name}}</h2>
|
|
29086
|
+
<div class="dlg-body dlg-body-list ">
|
|
29087
|
+
{{ mapper.data().length }} records matching current filters.
|
|
29088
|
+
|
|
29089
|
+
<cdk-virtual-scroll-viewport [itemSize]="40">
|
|
29090
|
+
<div *cdkVirtualFor="let feature of mapper.data()" (click)="onTileClick(feature)"
|
|
29091
|
+
class="data-tile" [innerHTML]="popupRenderer.RenderPopupSync(feature) | safeHtml"></div>
|
|
29092
|
+
</cdk-virtual-scroll-viewport>
|
|
29093
|
+
</div>
|
|
29094
|
+
<div class="dlg-buttons">
|
|
29095
|
+
<button class="btn" (click)="toggleData()">Close</button>
|
|
29096
|
+
</div>
|
|
29097
|
+
</dialog>
|
|
29098
|
+
|
|
27714
29099
|
<!-- <ng-template #dataTemplate let-feature>
|
|
27715
29100
|
<div [innerHTML]="mapper.popupRenderer?.RenderPopup(feature) | async"></div>
|
|
27716
29101
|
</ng-template>
|
|
@@ -27721,11 +29106,12 @@ class MMPanel {
|
|
|
27721
29106
|
[contentTemplate]="dataTemplate"
|
|
27722
29107
|
(onSelect)="onSelect($event)">
|
|
27723
29108
|
</mapag-tile-dialog> -->
|
|
27724
|
-
`, isInline: true, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}::deep .ng-select-container,::deep .ng-select{font-size:.8em}.filter-row{display:flex;flex-direction:column;margin-bottom:8px;font-size:.8em}.filter-row-cols{display:block;column-count:2}.zone{display:flex;align-items:center;gap:8px;margin:0;padding:0}.zones{display:grid;grid-template-columns:1fr 1fr;column-gap:24px;row-gap:8px;overflow-y:auto;max-height:420px;font-size:.8em}.svgicon{height:30px;width:30px;-webkit-mask-size:contain;mask-size:contain}h4,label{display:flex;align-items:center;gap:4px}@media (max-width: 600px){.zones{grid-template-columns:1fr}}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$1.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$1.RangeValueAccessor, selector: "input[type=range][formControlName],input[type=range][formControl],input[type=range][ngModel]" }, { kind: "directive", type: i1$1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "component", type: HubDataLayer, selector: "hub-data-layer", inputs: ["visible", "name", "desc", "icon", "shape"], outputs: ["onCustomize", "onCheck"] }, { kind: "directive", type: DraggableDialogDirective, selector: "dialog[draggable]" }, { kind: "component", type: FaIconComponent, selector: "fa-icon", inputs: ["icon", "title", "animation", "mask", "flip", "size", "pull", "border", "inverse", "symbol", "rotate", "fixedWidth", "transform", "a11yRole"], outputs: ["iconChange", "titleChange", "animationChange", "maskChange", "flipChange", "sizeChange", "pullChange", "borderChange", "inverseChange", "symbolChange", "rotateChange", "fixedWidthChange", "transformChange", "a11yRoleChange"] }, { kind: "directive", type: BringToFrontDirective, selector: "[mapagBringToFront]" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
29109
|
+
`, isInline: true, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}::deep .ng-select-container,::deep .ng-select{font-size:.8em}.filter-row{display:flex;flex-direction:column;margin-bottom:8px;font-size:.8em}.filter-row-cols{display:block;column-count:2}.zone{display:flex;align-items:center;gap:8px;margin:0;padding:0}.zones{display:grid;grid-template-columns:1fr 1fr;column-gap:24px;row-gap:8px;overflow-y:auto;max-height:420px;font-size:.8em}.svgicon{height:30px;width:30px;-webkit-mask-size:contain;mask-size:contain}h4,label{display:flex;align-items:center;gap:4px}.dlg-body-list{display:grid;grid-template-rows:auto 1fr;row-gap:12px}.data-dialog{width:auto;max-width:min(450px,100vw);height:90dvh}.data-tile{padding:6px;border:1px solid #ccc;margin:4px;font-size:10pt;box-shadow:0 2px 4px #0000001a;cursor:pointer}.data-tile:hover{background-color:#f0f0f0}.data-tile:last-child{border-bottom:none}.tile-title{font-weight:600;color:#222}.tile-sub{color:#555;font-size:.85em}@media (max-width: 600px){.zones{grid-template-columns:1fr}}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "ngmodule", type: FormsModule }, { kind: "directive", type: i1$1.DefaultValueAccessor, selector: "input:not([type=checkbox])[formControlName],textarea[formControlName],input:not([type=checkbox])[formControl],textarea[formControl],input:not([type=checkbox])[ngModel],textarea[ngModel],[ngDefaultControl]" }, { kind: "directive", type: i1$1.RangeValueAccessor, selector: "input[type=range][formControlName],input[type=range][formControl],input[type=range][ngModel]" }, { kind: "directive", type: i1$1.NgControlStatus, selector: "[formControlName],[ngModel],[formControl]" }, { kind: "directive", type: i1$1.NgModel, selector: "[ngModel]:not([formControlName]):not([formControl])", inputs: ["name", "disabled", "ngModel", "ngModelOptions"], outputs: ["ngModelChange"], exportAs: ["ngModel"] }, { kind: "component", type: HubDataLayer, selector: "hub-data-layer", inputs: ["visible", "name", "desc", "icon", "shape"], outputs: ["onCustomize", "onCheck"] }, { kind: "directive", type: DraggableDialogDirective, selector: "dialog[draggable]" }, { kind: "component", type: FaIconComponent, selector: "fa-icon", inputs: ["icon", "title", "animation", "mask", "flip", "size", "pull", "border", "inverse", "symbol", "rotate", "fixedWidth", "transform", "a11yRole"], outputs: ["iconChange", "titleChange", "animationChange", "maskChange", "flipChange", "sizeChange", "pullChange", "borderChange", "inverseChange", "symbolChange", "rotateChange", "fixedWidthChange", "transformChange", "a11yRoleChange"] }, { kind: "directive", type: BringToFrontDirective, selector: "[mapagBringToFront]" }, { kind: "component", type: CdkVirtualScrollViewport, selector: "cdk-virtual-scroll-viewport", inputs: ["orientation", "appendOnly"], outputs: ["scrolledIndexChange"] }, { kind: "directive", type: CdkVirtualForOf, selector: "[cdkVirtualFor][cdkVirtualForOf]", inputs: ["cdkVirtualForOf", "cdkVirtualForTrackBy", "cdkVirtualForTemplate", "cdkVirtualForTemplateCacheSize"] }, { kind: "directive", type: CdkFixedSizeVirtualScroll, selector: "cdk-virtual-scroll-viewport[itemSize]", inputs: ["itemSize", "minBufferPx", "maxBufferPx"] }, { kind: "pipe", type: SafeHtmlPipe, name: "safeHtml" }], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
27725
29110
|
}
|
|
27726
29111
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: MMPanel, decorators: [{
|
|
27727
29112
|
type: Component,
|
|
27728
|
-
args: [{ selector: 'mapag-mm-panel', changeDetection: ChangeDetectionStrategy.OnPush, imports: [CommonModule, FormsModule, HubDataLayer, DraggableDialogDirective, FaIconComponent,
|
|
29113
|
+
args: [{ selector: 'mapag-mm-panel', changeDetection: ChangeDetectionStrategy.OnPush, imports: [CommonModule, FormsModule, HubDataLayer, DraggableDialogDirective, FaIconComponent,
|
|
29114
|
+
BringToFrontDirective, CdkVirtualScrollViewport, CdkVirtualForOf, CdkFixedSizeVirtualScroll, SafeHtmlPipe], template: `
|
|
27729
29115
|
<hub-data-layer [visible]="mapper.settings().visible" [name]="mapper.settings().name"
|
|
27730
29116
|
[desc]="mapper.settings().description || 'MarketMaker Business'" shape="point" (onCheck)="setVisible($event)" (onCustomize)="toggleDialog()">
|
|
27731
29117
|
|
|
@@ -27866,7 +29252,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImpo
|
|
|
27866
29252
|
</div>
|
|
27867
29253
|
<div class="dlg-buttons">
|
|
27868
29254
|
<button class="btn" (click)="toggleLegend()">Legend</button>
|
|
27869
|
-
|
|
29255
|
+
<button class="btn" (click)="toggleData()">Data</button>
|
|
27870
29256
|
<button class="btn" (click)="remove()">Remove</button>
|
|
27871
29257
|
<button class="btn" (click)="reset()">Reset</button>
|
|
27872
29258
|
<button class="btn" (click)="toggleShowHide()">
|
|
@@ -27877,6 +29263,21 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImpo
|
|
|
27877
29263
|
</div>
|
|
27878
29264
|
</dialog>
|
|
27879
29265
|
|
|
29266
|
+
<dialog draggable mapagBringToFront onBody #dataDialog class="data-dialog">
|
|
29267
|
+
<h2>{{mapper.settings().name}}</h2>
|
|
29268
|
+
<div class="dlg-body dlg-body-list ">
|
|
29269
|
+
{{ mapper.data().length }} records matching current filters.
|
|
29270
|
+
|
|
29271
|
+
<cdk-virtual-scroll-viewport [itemSize]="40">
|
|
29272
|
+
<div *cdkVirtualFor="let feature of mapper.data()" (click)="onTileClick(feature)"
|
|
29273
|
+
class="data-tile" [innerHTML]="popupRenderer.RenderPopupSync(feature) | safeHtml"></div>
|
|
29274
|
+
</cdk-virtual-scroll-viewport>
|
|
29275
|
+
</div>
|
|
29276
|
+
<div class="dlg-buttons">
|
|
29277
|
+
<button class="btn" (click)="toggleData()">Close</button>
|
|
29278
|
+
</div>
|
|
29279
|
+
</dialog>
|
|
29280
|
+
|
|
27880
29281
|
<!-- <ng-template #dataTemplate let-feature>
|
|
27881
29282
|
<div [innerHTML]="mapper.popupRenderer?.RenderPopup(feature) | async"></div>
|
|
27882
29283
|
</ng-template>
|
|
@@ -27887,13 +29288,13 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImpo
|
|
|
27887
29288
|
[contentTemplate]="dataTemplate"
|
|
27888
29289
|
(onSelect)="onSelect($event)">
|
|
27889
29290
|
</mapag-tile-dialog> -->
|
|
27890
|
-
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}::deep .ng-select-container,::deep .ng-select{font-size:.8em}.filter-row{display:flex;flex-direction:column;margin-bottom:8px;font-size:.8em}.filter-row-cols{display:block;column-count:2}.zone{display:flex;align-items:center;gap:8px;margin:0;padding:0}.zones{display:grid;grid-template-columns:1fr 1fr;column-gap:24px;row-gap:8px;overflow-y:auto;max-height:420px;font-size:.8em}.svgicon{height:30px;width:30px;-webkit-mask-size:contain;mask-size:contain}h4,label{display:flex;align-items:center;gap:4px}@media (max-width: 600px){.zones{grid-template-columns:1fr}}\n"] }]
|
|
27891
|
-
}], ctorParameters: () => [], propDecorators: { map: [{ type: i0.Input, args: [{ isSignal: true, alias: "map", required: false }] }], settings: [{ type: i0.Input, args: [{ isSignal: true, alias: "settings", required: false }] }], customizeDialog: [{ type: i0.ViewChild, args: ['customizeDialog', { isSignal: true }] }], onRemove: [{ type: i0.Output, args: ["onRemove"] }] } });
|
|
29291
|
+
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}::deep .ng-select-container,::deep .ng-select{font-size:.8em}.filter-row{display:flex;flex-direction:column;margin-bottom:8px;font-size:.8em}.filter-row-cols{display:block;column-count:2}.zone{display:flex;align-items:center;gap:8px;margin:0;padding:0}.zones{display:grid;grid-template-columns:1fr 1fr;column-gap:24px;row-gap:8px;overflow-y:auto;max-height:420px;font-size:.8em}.svgicon{height:30px;width:30px;-webkit-mask-size:contain;mask-size:contain}h4,label{display:flex;align-items:center;gap:4px}.dlg-body-list{display:grid;grid-template-rows:auto 1fr;row-gap:12px}.data-dialog{width:auto;max-width:min(450px,100vw);height:90dvh}.data-tile{padding:6px;border:1px solid #ccc;margin:4px;font-size:10pt;box-shadow:0 2px 4px #0000001a;cursor:pointer}.data-tile:hover{background-color:#f0f0f0}.data-tile:last-child{border-bottom:none}.tile-title{font-weight:600;color:#222}.tile-sub{color:#555;font-size:.85em}@media (max-width: 600px){.zones{grid-template-columns:1fr}}\n"] }]
|
|
29292
|
+
}], ctorParameters: () => [], propDecorators: { map: [{ type: i0.Input, args: [{ isSignal: true, alias: "map", required: false }] }], settings: [{ type: i0.Input, args: [{ isSignal: true, alias: "settings", required: false }] }], customizeDialog: [{ type: i0.ViewChild, args: ['customizeDialog', { isSignal: true }] }], dataDialog: [{ type: i0.ViewChild, args: ['dataDialog', { isSignal: true }] }], onRemove: [{ type: i0.Output, args: ["onRemove"] }] } });
|
|
27892
29293
|
class MarketMakerPopupRenderer {
|
|
27893
|
-
|
|
29294
|
+
RenderPopupSync(feature) {
|
|
27894
29295
|
const props = feature.properties;
|
|
27895
29296
|
if (!props) {
|
|
27896
|
-
return
|
|
29297
|
+
return undefined;
|
|
27897
29298
|
}
|
|
27898
29299
|
let html = `<div>`;
|
|
27899
29300
|
html += `<h3>${props.Name || 'MarketMaker Business'}</h3>`;
|
|
@@ -27925,7 +29326,10 @@ class MarketMakerPopupRenderer {
|
|
|
27925
29326
|
onclick="window.open('https://foodmarketmaker.com/business/${props.ID}', '_blank')">Learn More...</button>
|
|
27926
29327
|
`;
|
|
27927
29328
|
html += `</div>`;
|
|
27928
|
-
return
|
|
29329
|
+
return html;
|
|
29330
|
+
}
|
|
29331
|
+
RenderPopup(feature) {
|
|
29332
|
+
return this.RenderPopupSync(feature);
|
|
27929
29333
|
}
|
|
27930
29334
|
getArrayProperty(value) {
|
|
27931
29335
|
const arr = this.parseArrayProperty(value) || [];
|
|
@@ -28304,7 +29708,7 @@ class HubNaicsPanel {
|
|
|
28304
29708
|
{{ mapper.data().length }} records matching current filters.
|
|
28305
29709
|
<cdk-virtual-scroll-viewport [itemSize]="10">
|
|
28306
29710
|
<div *cdkVirtualFor="let feature of mapper.data()" (click)="mapper.flyToFeature(feature)"
|
|
28307
|
-
class="data-tile" [innerHTML]="mapper.
|
|
29711
|
+
class="data-tile" [innerHTML]="mapper.renderInfo(feature)">
|
|
28308
29712
|
</div>
|
|
28309
29713
|
|
|
28310
29714
|
</cdk-virtual-scroll-viewport>
|
|
@@ -28504,7 +29908,7 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImpo
|
|
|
28504
29908
|
{{ mapper.data().length }} records matching current filters.
|
|
28505
29909
|
<cdk-virtual-scroll-viewport [itemSize]="10">
|
|
28506
29910
|
<div *cdkVirtualFor="let feature of mapper.data()" (click)="mapper.flyToFeature(feature)"
|
|
28507
|
-
class="data-tile" [innerHTML]="mapper.
|
|
29911
|
+
class="data-tile" [innerHTML]="mapper.renderInfo(feature)">
|
|
28508
29912
|
</div>
|
|
28509
29913
|
|
|
28510
29914
|
</cdk-virtual-scroll-viewport>
|
|
@@ -28808,85 +30212,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImpo
|
|
|
28808
30212
|
`, styles: ["dialog{font-size:14pt;width:100%;max-width:700px;border:none;border-radius:8px;box-shadow:0 2px 10px #0003;padding:16px;position:fixed;top:50%;left:50%;transform:translate(-50%,-50%);margin:0;flex-direction:column}dialog:open{display:flex}dialog .dlg-body{flex-grow:1;overflow-y:auto}dialog.legend{width:fit-content}dialog.legend h2{font-size:smaller}dialog select{max-width:90vw}dialog h2{color:#000}dialog h2:before{content:\"\\22ee\\22ee \";padding-right:4px}dialog h3{color:#000;border-bottom:2px solid gray;font-weight:500;font-size:.9em;margin-top:16px;margin-bottom:8px}dialog h4{color:#000;font-weight:500;margin-bottom:8px;margin-top:12px;font-size:.85em;border:none}dialog p{font-size:.8em}dialog a{text-decoration:none;color:#0a3773;font-weight:500;font-size:.8em;padding-left:4px}dialog a:hover{text-decoration:underline;cursor:pointer}dialog a:before{content:\"\\1f517\";padding-right:2px}.ctrl-group{display:flex;flex-direction:column}.ctrl-row{display:grid;grid-template-columns:auto 1fr auto 1fr;align-items:center;gap:4px;justify-items:start;padding-left:20px}.ctrl-first{grid-column:1}.ctrl-row label{font-size:.8em;margin:0;padding:0;font-weight:400}.ctrl.wide{grid-column:span 3}input[type=range]{grid-column:span 3;justify-self:stretch}input[type=color]{width:40px;height:24px;border-radius:4px;cursor:pointer}input[type=number]{width:6ch;font-size:.8em}.dlg-buttons{display:flex;justify-content:flex-end;gap:8px;margin-top:16px}button{background-color:#0a3773;color:#fff;border:none;border-radius:4px;padding:8px 16px;cursor:pointer;font-size:.8em}button:hover{background-color:#083a5c}summary{font-size:1em;font-weight:600;color:#000;cursor:pointer;padding:8px 0;border-bottom:2px solid gray;list-style:none;-webkit-user-select:none;user-select:none;margin-bottom:8px}summary::-webkit-details-marker{display:none}summary:before{content:\"\\304f\";display:inline-block;margin-right:8px;transform:rotate(180deg);transition:transform .2s}details[open] summary:before{transform:rotate(270deg)}.radio-tabs{margin-bottom:12px;font-size:.8em;display:flex;flex-direction:row}.radio-tabs label{display:grid;grid-template-columns:auto 1fr;gap:4px;grid-template-rows:30px;align-items:center}.radio-tabs input[type=radio]{display:none}.radio-tabs label{padding:8px 12px;border:2px solid transparent;border-radius:6px;cursor:pointer;transition:all .2s ease}.radio-tabs label:has(input[type=radio]:checked){background-color:#fff;border-color:#333}.mgr-btn{justify-self:center;background-color:transparent;color:#4c4c4c;text-align:center;width:100%;font-weight:600;cursor:pointer;display:flex;align-items:center;justify-content:center;margin:4px 0;padding:6px;gap:4px;border:1px solid rgb(218,218,218)}.mgr-btn:hover{background-color:transparent;border-color:#4c4c4c}.legend-row{display:grid;grid-template-columns:auto 1fr;gap:8px;padding:4px 0;align-items:center}.legend-title{font-weight:700;text-align:center;margin-bottom:8px}.legend-item{height:15px;width:15px;border:1px solid #ccc}.maplibregl-popup-close-button{top:13px;right:15px}@media screen and (max-width: 600px){dialog{width:100vw;max-width:100vw;height:100dvh;max-height:100dvh;border-radius:0;border:none;box-shadow:none;overflow:hidden}.dlg-buttons{flex-direction:row;flex-wrap:wrap;align-items:center;justify-content:center}dialog h2:before{content:\"\";padding-right:0}}.search{display:flex;gap:4px;align-items:center;margin-bottom:8px;font-size:.8em}.search input[type=radio]{display:none}.search label{display:flex;align-items:center;gap:4px;padding:2px 4px;border:1px solid transparent;cursor:pointer}.search label:has(input[type=radio]:checked){border:1px solid #333;border-radius:4px;background-color:#f0f0f0}dialog h4{display:flex;justify-content:space-between;align-items:center;margin-bottom:4px;margin-top:4px}.ctrl-row{grid-template-columns:1fr;font-size:.8em}.zones{max-height:400px;height:400px;overflow-y:auto;margin-top:0}input[type=search]{width:100%;font-size:1em;padding:4px 8px;border-radius:4px;border:1px solid #ccc}label{display:flex;align-items:center;gap:4px}.svgicon{height:20px;width:20px;-webkit-mask-size:contain;mask-size:contain}.tiles{display:grid;grid-template-columns:repeat(auto-fit,115px);gap:8px;margin-top:8px;text-align:center;align-items:start}.tiles label{display:grid;grid-template-columns:1fr;grid-template-rows:auto 1fr;align-items:start;justify-items:center;height:100%;padding:2px;border:1px solid transparent;cursor:pointer}.tiles label:hover{background-color:#f0f0f0;border:1px solid #999;border-radius:4px}.tiles label:has(input[type=checkbox]:checked){border:1px solid #333;border-radius:4px}.tiles .svgicon{height:50px;width:50px;margin-bottom:4px}.tiles input[type=checkbox]{display:none}@media (max-width: 600px){.dlg-body{display:flex;flex-direction:column}.zones{max-height:unset;flex-grow:1}}\n"] }]
|
|
28809
30213
|
}], ctorParameters: () => [], propDecorators: { canAdd: [{ type: i0.Input, args: [{ isSignal: true, alias: "canAdd", required: false }] }], map: [{ type: i0.Input, args: [{ isSignal: true, alias: "map", required: false }] }], codes: [{ type: i0.Input, args: [{ isSignal: true, alias: "codes", required: false }] }], current: [{ type: i0.Input, args: [{ isSignal: true, alias: "current", required: false }] }], currentChange: [{ type: i0.Output, args: ["currentChange"] }], customizeDialog: [{ type: i0.ViewChild, args: ['customizeDialog', { isSignal: true }] }], legendDialog: [{ type: i0.ViewChild, args: ['legendDialog', { isSignal: true }] }] } });
|
|
28810
30214
|
|
|
28811
|
-
class GradientLegend {
|
|
28812
|
-
topStyle = signal({}, ...(ngDevMode ? [{ debugName: "topStyle" }] : []));
|
|
28813
|
-
bottomStyle = signal({}, ...(ngDevMode ? [{ debugName: "bottomStyle" }] : []));
|
|
28814
|
-
gradientStyle = signal({}, ...(ngDevMode ? [{ debugName: "gradientStyle" }] : []));
|
|
28815
|
-
settings = input(new GradientSettings(), ...(ngDevMode ? [{ debugName: "settings" }] : []));
|
|
28816
|
-
renderer = inject(Renderer2);
|
|
28817
|
-
host = inject((ElementRef));
|
|
28818
|
-
constructor() {
|
|
28819
|
-
const onUpdateSettings = effect(() => {
|
|
28820
|
-
const settings = this.settings();
|
|
28821
|
-
this.topStyle.set({
|
|
28822
|
-
background: settings.minTop ? settings.minColor : settings.maxColor,
|
|
28823
|
-
value: settings.minValue
|
|
28824
|
-
});
|
|
28825
|
-
this.bottomStyle.set({
|
|
28826
|
-
background: settings.minTop ? settings.maxColor : settings.minColor,
|
|
28827
|
-
value: settings.maxValue
|
|
28828
|
-
});
|
|
28829
|
-
this.gradientStyle.set({
|
|
28830
|
-
background: `linear-gradient(${settings.dir === 'horizontal' ? 'to right' : 'to top'}, ${settings.minColor}, ${settings.maxColor})`,
|
|
28831
|
-
height: settings.dir === 'horizontal' ? '30px' : '100%',
|
|
28832
|
-
width: settings.dir === 'horizontal' ? '100%' : '30px'
|
|
28833
|
-
});
|
|
28834
|
-
}, ...(ngDevMode ? [{ debugName: "onUpdateSettings" }] : []));
|
|
28835
|
-
}
|
|
28836
|
-
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: GradientLegend, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
28837
|
-
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "17.1.0", version: "20.3.15", type: GradientLegend, isStandalone: true, selector: "mapag-gradient-legend", inputs: { settings: { classPropertyName: "settings", publicName: "settings", isSignal: true, isRequired: false, transformFunction: null } }, ngImport: i0, template: `
|
|
28838
|
-
<div class="top" [ngStyle]="topStyle()"></div>
|
|
28839
|
-
<div>{{settings().unitPrefix}}{{ settings().maxValue | number:"1.0-2" }}{{settings().unitSuffix}}</div>
|
|
28840
|
-
<div class="gradient" [ngStyle]="gradientStyle()"></div>
|
|
28841
|
-
<div></div>
|
|
28842
|
-
<div class="bottom" [ngStyle]="bottomStyle()"></div>
|
|
28843
|
-
<div>{{settings().unitPrefix}}{{ settings().minValue | number:"1.0-2" }}{{settings().unitSuffix}}</div>
|
|
28844
|
-
`, isInline: true, styles: [":host{display:grid;grid-template-rows:auto 1fr auto;grid-template-columns:auto max-content;align-items:center;font-size:.8em;height:var(--legend-height, 150px);column-gap:4px}.h2{margin-bottom:8px}.top,.bottom{height:50%}.top{background:var(--top-color, green);align-self:end}.bottom{background:var(--bottom-color, black);align-self:start}.gradient{width:20px;flex-grow:1;height:100%;align-self:center;justify-self:center}\n"], dependencies: [{ kind: "ngmodule", type: CommonModule }, { kind: "directive", type: i1.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }, { kind: "ngmodule", type: FormsModule }, { kind: "pipe", type: i1.DecimalPipe, name: "number" }] });
|
|
28845
|
-
}
|
|
28846
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: GradientLegend, decorators: [{
|
|
28847
|
-
type: Component,
|
|
28848
|
-
args: [{ selector: 'mapag-gradient-legend', imports: [CommonModule, FormsModule], template: `
|
|
28849
|
-
<div class="top" [ngStyle]="topStyle()"></div>
|
|
28850
|
-
<div>{{settings().unitPrefix}}{{ settings().maxValue | number:"1.0-2" }}{{settings().unitSuffix}}</div>
|
|
28851
|
-
<div class="gradient" [ngStyle]="gradientStyle()"></div>
|
|
28852
|
-
<div></div>
|
|
28853
|
-
<div class="bottom" [ngStyle]="bottomStyle()"></div>
|
|
28854
|
-
<div>{{settings().unitPrefix}}{{ settings().minValue | number:"1.0-2" }}{{settings().unitSuffix}}</div>
|
|
28855
|
-
`, styles: [":host{display:grid;grid-template-rows:auto 1fr auto;grid-template-columns:auto max-content;align-items:center;font-size:.8em;height:var(--legend-height, 150px);column-gap:4px}.h2{margin-bottom:8px}.top,.bottom{height:50%}.top{background:var(--top-color, green);align-self:end}.bottom{background:var(--bottom-color, black);align-self:start}.gradient{width:20px;flex-grow:1;height:100%;align-self:center;justify-self:center}\n"] }]
|
|
28856
|
-
}], ctorParameters: () => [], propDecorators: { settings: [{ type: i0.Input, args: [{ isSignal: true, alias: "settings", required: false }] }] } });
|
|
28857
|
-
class GradientSettings {
|
|
28858
|
-
minColor = "#000000";
|
|
28859
|
-
maxColor = "#FFFFFF";
|
|
28860
|
-
minValue = 0.0;
|
|
28861
|
-
maxValue = 1.0;
|
|
28862
|
-
height = "100px";
|
|
28863
|
-
width = "30px";
|
|
28864
|
-
minTop = false;
|
|
28865
|
-
dir = 'vertical';
|
|
28866
|
-
unitPrefix = '';
|
|
28867
|
-
unitSuffix = '';
|
|
28868
|
-
}
|
|
28869
|
-
|
|
28870
|
-
class TextPipe {
|
|
28871
|
-
transform(value, ...args) {
|
|
28872
|
-
if (value === null || value === undefined) {
|
|
28873
|
-
return '';
|
|
28874
|
-
}
|
|
28875
|
-
if (typeof value === 'string') {
|
|
28876
|
-
return fixText(value);
|
|
28877
|
-
}
|
|
28878
|
-
return value;
|
|
28879
|
-
}
|
|
28880
|
-
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: TextPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
|
|
28881
|
-
static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "20.3.15", ngImport: i0, type: TextPipe, isStandalone: true, name: "text" });
|
|
28882
|
-
}
|
|
28883
|
-
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: TextPipe, decorators: [{
|
|
28884
|
-
type: Pipe,
|
|
28885
|
-
args: [{
|
|
28886
|
-
name: 'text'
|
|
28887
|
-
}]
|
|
28888
|
-
}] });
|
|
28889
|
-
|
|
28890
30215
|
class NassPanel {
|
|
28891
30216
|
map = input(...(ngDevMode ? [undefined, { debugName: "map" }] : []));
|
|
28892
30217
|
mapper = new NAASMapper();
|
|
@@ -30935,13 +32260,13 @@ class SettingsPanel {
|
|
|
30935
32260
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: SettingsPanel, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
30936
32261
|
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "20.3.15", type: SettingsPanel, isStandalone: true, selector: "app-settings-panel", ngImport: i0, template: `
|
|
30937
32262
|
<ng-content></ng-content>
|
|
30938
|
-
`, isInline: true, styles: [":host{position:fixed;padding:16px;border:1px solid #ccc;border-radius:8px;background-color:#efe9e1;right:16px;top:16px;bottom:16px;width:
|
|
32263
|
+
`, isInline: true, styles: [":host{position:fixed;padding:16px;border:1px solid #ccc;border-radius:8px;background-color:#efe9e1;right:16px;top:16px;bottom:16px;width:320px;box-shadow:0 2px 8px #0000001a;overflow-y:auto}\n"], changeDetection: i0.ChangeDetectionStrategy.OnPush });
|
|
30939
32264
|
}
|
|
30940
32265
|
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImport: i0, type: SettingsPanel, decorators: [{
|
|
30941
32266
|
type: Component,
|
|
30942
32267
|
args: [{ selector: 'app-settings-panel', changeDetection: ChangeDetectionStrategy.OnPush, imports: [], template: `
|
|
30943
32268
|
<ng-content></ng-content>
|
|
30944
|
-
`, styles: [":host{position:fixed;padding:16px;border:1px solid #ccc;border-radius:8px;background-color:#efe9e1;right:16px;top:16px;bottom:16px;width:
|
|
32269
|
+
`, styles: [":host{position:fixed;padding:16px;border:1px solid #ccc;border-radius:8px;background-color:#efe9e1;right:16px;top:16px;bottom:16px;width:320px;box-shadow:0 2px 8px #0000001a;overflow-y:auto}\n"] }]
|
|
30945
32270
|
}] });
|
|
30946
32271
|
|
|
30947
32272
|
/*
|
|
@@ -30953,5 +32278,5 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "20.3.15", ngImpo
|
|
|
30953
32278
|
* Generated bundle index. Do not edit.
|
|
30954
32279
|
*/
|
|
30955
32280
|
|
|
30956
|
-
export { AddLayer, AddSource, AreaIcon, AreaMapperMapper, BackgroundMaskMapper, BackgroundMaskSettings, BaseMapLight, BasemapSelect, BasemapSelectMenu, BringToFrontDirective, BringToFrontService, CensusTractMapper, Codes, CropSequenceMapper, CropSequenceSettings, CroplandDataLayerMapper, CroplandDataLayerSettings, CroplandLegend, DEFAULT_GLYPHS, DEFAULT_GLYPHS2, DEFAULT_PIN_URL, DataSetFieldValue, DirectoryIndexPToTable, DirectoryIndexToTable, DraggableDialogDirective, DrawPolygon, DrawSquare, DrawingMapper, EsriMapper, EsriSettings, ExpandArrows, FilterPanel, FipsFromDataSet, FoodHubPanel, FoodhubMapper, FoodhubMapperSettings, HardinessMapper, HardinessSettings, HttpBoundaryLoader, HubCropSequencePanel, HubCroplandPanel, HubDataLayer, HubHardinessPanel, HubNaicsPanel, HubRailroadPanel, HubWatershedPanel, Icons, LineIcon, MMPanel, MapAreaSelectComponent, MapComponent, MapSelectionService, MapService, MapStyles, MapagDetails, MapboxMapperGroup, MarketMakerPopupRenderer, NAASMapper, NAASSettings, NASSInfo, NaicsEmployeesOptions, NaicsMapper, NaicsMapperSettings, NaicsMgrPanel, NaicsSalesOptions, NassIndex, NassInfoFromIndex, NassInfoFromIndexP, NassInfoFromPath, NassMgrPanel, NassPanel, NassService, NoOpMapper, PaletteDisplay, PaletteSelect, PointDataMapper, PointDataMapperSettings, PrintPanel, RailroadSettings, RailroadUsageSettings, RailroadsMapper, RasterIcon, ReferenceDataService, RemoveLayer, RemoveSource, SaveMap, SelectMode, SettingsPanel, SimpleMapper, SourceLoadWatcher, StandardLayersMapper, StateCountySelectComponent, Styles, TableBuilder, TableRow, VectorTileServerMapper, WatershedMapper, WatershedSettings, WelcomePanel, discoverLayers, fixText, isGeoloader, isMultiPolygon, isNumber2DArray, isNumber3DArray, isPolygon, mapboxImageName, mapboxLoadImages, mapboxloadImage, normalize, normalizeArray, pmtilesPixelInfo, prefixMatch, propertiesToTableHtml, randomColor, sampleTilesForLayers, simpleClone, toMultiPolygon, trySync };
|
|
32281
|
+
export { AddLayer, AddSource, AreaIcon, AreaMapperMapper, BackgroundMaskMapper, BackgroundMaskSettings, BaseMapLight, BasemapSelect, BasemapSelectMenu, BringToFrontDirective, BringToFrontService, CensusTractMapper, Codes, ConsumerSpendingPanel, ConsumerSpendingSelectPanel, CropSequenceMapper, CropSequenceSettings, CroplandDataLayerMapper, CroplandDataLayerSettings, CroplandLegend, DEFAULT_GLYPHS, DEFAULT_GLYPHS2, DEFAULT_PIN_URL, DataSetFieldValue$1 as DataSetFieldValue, DirectoryIndexPToTable, DirectoryIndexToTable, DraggableDialogDirective, DrawPolygon, DrawSquare, DrawingMapper, EsriMapper, EsriSettings, ExpandArrows, FilterPanel, FipsFromDataSet$1 as FipsFromDataSet, FoodHubPanel, FoodhubMapper, FoodhubMapperSettings, HardinessMapper, HardinessSettings, HttpBoundaryLoader, HubCropSequencePanel, HubCroplandPanel, HubDataLayer, HubHardinessPanel, HubNaicsPanel, HubRailroadPanel, HubWatershedPanel, Icons, LineIcon, MMPanel, MapAreaSelectComponent, MapComponent, MapSelectionService, MapService, MapStyles, MapagDetails, MapboxMapperGroup, MarketMakerPopupRenderer, NAASMapper, NAASSettings, NASSInfo, NaicsEmployeesOptions, NaicsMapper, NaicsMapperSettings, NaicsMgrPanel, NaicsSalesOptions, NassIndex, NassInfoFromIndex, NassInfoFromIndexP, NassInfoFromPath, NassMgrPanel, NassPanel, NassService, NoOpMapper, PaletteDisplay, PaletteSelect, PointDataMapper, PointDataMapperSettings, PrintPanel, RailroadSettings, RailroadUsageSettings, RailroadsMapper, RasterIcon, ReferenceDataService, RemoveLayer, RemoveSource, SaveMap, SelectMode, SettingsPanel, SimpleMapper, SourceLoadWatcher, StandardLayersMapper, StateCountySelectComponent, Styles, TableBuilder, TableRow, ToggleDialog, VectorTileServerMapper, WatershedMapper, WatershedSettings, WelcomePanel, discoverLayers, fixText, flyToFeature, isGeoloader, isMultiPolygon, isNumber2DArray, isNumber3DArray, isPolygon, mapboxImageName, mapboxLoadImages, mapboxloadImage, normalize, normalizeArray, pmtilesPixelInfo, prefixMatch, propertiesToTableHtml, randomColor, sampleTilesForLayers, simpleClone, toMultiPolygon, trySync };
|
|
30957
32282
|
//# sourceMappingURL=foodmarketmaker-mapag.mjs.map
|