@geoit/ui 0.1.0 → 0.1.1
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/ai/README.md +1 -1
- package/ai/catalog.json +18 -2
- package/ai/components/geo-map-shell.md +3 -0
- package/ai/mockup.html +2 -2
- package/esm2022/lib/figma/geo-map/chrome/geo-map-locate/geo-map-locate.component.mjs +14 -37
- package/esm2022/lib/figma/geo-map/chrome/geo-map-locate/geo-map-locate.util.mjs +38 -0
- package/esm2022/lib/figma/geo-map/chrome/geo-map-shell/geo-map-shell.component.mjs +25 -3
- package/esm2022/lib/figma/geo-map/geo-map.constants.mjs +13 -1
- package/fesm2022/geoit-ui.mjs +84 -38
- package/fesm2022/geoit-ui.mjs.map +1 -1
- package/lib/figma/geo-map/chrome/geo-map-locate/geo-map-locate.util.d.ts +16 -0
- package/lib/figma/geo-map/chrome/geo-map-shell/geo-map-shell.component.d.ts +11 -2
- package/lib/figma/geo-map/geo-map.constants.d.ts +6 -0
- package/package.json +1 -1
package/ai/README.md
CHANGED
|
@@ -76,6 +76,6 @@ Agent rules: [`AGENTS.md`](./AGENTS.md) · Recipes: [`recipes.md`](./recipes.md)
|
|
|
76
76
|
| `geo-typography` | display | Text with GEO type scale (h1–tiny) and semantic colors. | [geo-typography.md](./components/geo-typography.md) |
|
|
77
77
|
| `geo-upload` | forms | Drag-drop upload zone with progress list. | [geo-upload.md](./components/geo-upload.md) |
|
|
78
78
|
|
|
79
|
-
Generated: 2026-09-
|
|
79
|
+
Generated: 2026-09-11T02:34:24.165Z
|
|
80
80
|
|
|
81
81
|
Regenerate: `npm run ai:docs`
|
package/ai/catalog.json
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
{
|
|
2
2
|
"package": "@geoit/ui",
|
|
3
3
|
"import": "@geoit/ui",
|
|
4
|
-
"version": "0.1.
|
|
5
|
-
"generatedAt": "2026-09-
|
|
4
|
+
"version": "0.1.1",
|
|
5
|
+
"generatedAt": "2026-09-11T02:34:24.165Z",
|
|
6
6
|
"styles": [
|
|
7
7
|
"@geoit/ui/src/lib/styles/design-tokens.scss",
|
|
8
8
|
"@geoit/ui/src/lib/styles/theme.scss"
|
|
@@ -3558,6 +3558,12 @@
|
|
|
3558
3558
|
"default": "GEO_MAP_DEMO_LEGEND_ITEMS",
|
|
3559
3559
|
"note": ""
|
|
3560
3560
|
},
|
|
3561
|
+
{
|
|
3562
|
+
"name": "legendCatalogMissing",
|
|
3563
|
+
"type": "boolean",
|
|
3564
|
+
"default": "false",
|
|
3565
|
+
"note": "Host app sets true when the legend catalog (loại đất/ký hiệu/màu) failed to load."
|
|
3566
|
+
},
|
|
3561
3567
|
{
|
|
3562
3568
|
"name": "showNav",
|
|
3563
3569
|
"type": "boolean",
|
|
@@ -3708,11 +3714,21 @@
|
|
|
3708
3714
|
"type": "OutputEmitterRef<GeoMapClickEvent>",
|
|
3709
3715
|
"note": ""
|
|
3710
3716
|
},
|
|
3717
|
+
{
|
|
3718
|
+
"name": "located",
|
|
3719
|
+
"type": "OutputEmitterRef<void>",
|
|
3720
|
+
"note": ""
|
|
3721
|
+
},
|
|
3711
3722
|
{
|
|
3712
3723
|
"name": "locateDenied",
|
|
3713
3724
|
"type": "OutputEmitterRef<void>",
|
|
3714
3725
|
"note": ""
|
|
3715
3726
|
},
|
|
3727
|
+
{
|
|
3728
|
+
"name": "locateError",
|
|
3729
|
+
"type": "OutputEmitterRef<{ reason: GeoMapLocateErrorReason; message?: string; }>",
|
|
3730
|
+
"note": ""
|
|
3731
|
+
},
|
|
3716
3732
|
{
|
|
3717
3733
|
"name": "actionClick",
|
|
3718
3734
|
"type": "OutputEmitterRef<GeoMapToolbarAction>",
|
|
@@ -53,6 +53,7 @@ Every supported Input (do not invent others):
|
|
|
53
53
|
| `toolbarActions` | `GeoMapToolbarAction[]` | `GEO_MAP_DEFAULT_TOOLBAR_ACTIONS` | — |
|
|
54
54
|
| `layers` | `GeoMapLayerConfig[]` | `[]` | Extra overlays merged after demo thematic + traffic. |
|
|
55
55
|
| `legendItems` | `GeoMapLegendItem[]` | `GEO_MAP_DEMO_LEGEND_ITEMS` | — |
|
|
56
|
+
| `legendCatalogMissing` | `boolean` | `false` | Host app sets true when the legend catalog (loại đất/ký hiệu/màu) failed to load. |
|
|
56
57
|
| `showNav` | `boolean` | `true` | — |
|
|
57
58
|
| `includeDemoLayers` | `boolean` | `true` | — |
|
|
58
59
|
| `adminNodes` | `GeoTreeNode[]` | `GEO_MAP_DEMO_ADMIN_NODES` | — |
|
|
@@ -83,7 +84,9 @@ Every supported Input (do not invent others):
|
|
|
83
84
|
|--------|---------|-------------|
|
|
84
85
|
| `mapReady` | `OutputEmitterRef<GeoMapController>` | — |
|
|
85
86
|
| `mapClick` | `OutputEmitterRef<GeoMapClickEvent>` | — |
|
|
87
|
+
| `located` | `OutputEmitterRef<void>` | — |
|
|
86
88
|
| `locateDenied` | `OutputEmitterRef<void>` | — |
|
|
89
|
+
| `locateError` | `OutputEmitterRef<{ reason: GeoMapLocateErrorReason; message?: string; }>` | — |
|
|
87
90
|
| `actionClick` | `OutputEmitterRef<GeoMapToolbarAction>` | — |
|
|
88
91
|
| `search` | `OutputEmitterRef<GeoMapSearchQuery>` | — |
|
|
89
92
|
| `searchReset` | `OutputEmitterRef<void>` | — |
|
package/ai/mockup.html
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
<meta name="viewport" content="width=device-width, initial-scale=1" />
|
|
6
6
|
<title>@geoit/ui — Component mockup (design tokens)</title>
|
|
7
7
|
<!-- Generated by tools/generate-mockup.js — do not edit ai/mockup.html by hand -->
|
|
8
|
-
<!-- 2026-09-
|
|
8
|
+
<!-- 2026-09-11T02:34:24.225Z -->
|
|
9
9
|
<link rel="preconnect" href="https://fonts.googleapis.com" />
|
|
10
10
|
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
|
|
11
11
|
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&display=swap" rel="stylesheet" />
|
|
@@ -685,7 +685,7 @@
|
|
|
685
685
|
HTML tĩnh mô phỏng visual của các <code>geo-*</code> trong <code>ai/components</code>,
|
|
686
686
|
dùng đúng CSS variables từ <code>design-tokens.scss</code>.
|
|
687
687
|
Tokens được inject tự động khi <code>npm run ai:docs</code> / <code>npm run build</code>.
|
|
688
|
-
<br /><span class="typo-caption typo-secondary">Generated 2026-09-
|
|
688
|
+
<br /><span class="typo-caption typo-secondary">Generated 2026-09-11T02:34:24.225Z · source: projects/geo-ui/src/lib/styles/design-tokens.scss · 69 component docs in ai/components</span>
|
|
689
689
|
</p>
|
|
690
690
|
</header>
|
|
691
691
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { ChangeDetectionStrategy, Component, input, output, signal, ViewEncapsulation, } from '@angular/core';
|
|
2
2
|
import { NzToolTipModule } from 'ng-zorro-antd/tooltip';
|
|
3
|
-
import { fromLonLat } from 'ol/proj';
|
|
4
3
|
import { GeoIconComponent } from '../../../geo-icon/geo-icon.component';
|
|
4
|
+
import { runGeoMapLocate } from './geo-map-locate.util';
|
|
5
5
|
import * as i0 from "@angular/core";
|
|
6
6
|
import * as i1 from "ng-zorro-antd/tooltip";
|
|
7
7
|
/**
|
|
@@ -23,43 +23,20 @@ export class GeoMapLocateComponent {
|
|
|
23
23
|
if (!ctrl || this.busy()) {
|
|
24
24
|
return;
|
|
25
25
|
}
|
|
26
|
-
if (typeof navigator === 'undefined' || !navigator.geolocation) {
|
|
27
|
-
this.locateError.emit({
|
|
28
|
-
reason: 'unsupported',
|
|
29
|
-
message: 'Trình duyệt không hỗ trợ định vị.',
|
|
30
|
-
});
|
|
31
|
-
return;
|
|
32
|
-
}
|
|
33
26
|
this.busy.set(true);
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
ctrl.setCenter(mercator, Math.max(ctrl.getZoom() ?? 14, 14));
|
|
42
|
-
this.located.emit(lonLat);
|
|
43
|
-
}, (err) => {
|
|
44
|
-
this.busy.set(false);
|
|
45
|
-
if (err.code === err.PERMISSION_DENIED) {
|
|
27
|
+
runGeoMapLocate(ctrl, {
|
|
28
|
+
onLocated: (lonLat) => {
|
|
29
|
+
this.busy.set(false);
|
|
30
|
+
this.located.emit(lonLat);
|
|
31
|
+
},
|
|
32
|
+
onDenied: () => {
|
|
33
|
+
this.busy.set(false);
|
|
46
34
|
this.denied.emit();
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
}
|
|
53
|
-
const reason = err.code === err.POSITION_UNAVAILABLE
|
|
54
|
-
? 'unavailable'
|
|
55
|
-
: err.code === err.TIMEOUT
|
|
56
|
-
? 'timeout'
|
|
57
|
-
: 'unknown';
|
|
58
|
-
this.locateError.emit({ reason, message: err.message });
|
|
59
|
-
}, {
|
|
60
|
-
enableHighAccuracy: true,
|
|
61
|
-
timeout: 12000,
|
|
62
|
-
maximumAge: 0,
|
|
35
|
+
},
|
|
36
|
+
onError: (error) => {
|
|
37
|
+
this.busy.set(false);
|
|
38
|
+
this.locateError.emit(error);
|
|
39
|
+
},
|
|
63
40
|
});
|
|
64
41
|
}
|
|
65
42
|
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.14", ngImport: i0, type: GeoMapLocateComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
|
|
@@ -69,4 +46,4 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.14", ngImpo
|
|
|
69
46
|
type: Component,
|
|
70
47
|
args: [{ selector: 'geo-map-locate', standalone: true, imports: [GeoIconComponent, NzToolTipModule], changeDetection: ChangeDetectionStrategy.OnPush, encapsulation: ViewEncapsulation.None, host: { class: 'geo-map-locate-host' }, template: "<button\n type=\"button\"\n class=\"geo-map-locate__btn\"\n [nz-tooltip]=\"label()\"\n nzTooltipPlacement=\"left\"\n [attr.aria-label]=\"label()\"\n [disabled]=\"!controller() || busy()\"\n (click)=\"locate()\"\n>\n <geo-icon type=\"aim\" size=\"md\" />\n</button>\n", styles: ["@charset \"UTF-8\";.geo-map-locate-host{display:block}.geo-map-locate__btn{border:1px solid var(--geo-color-border-default);border-radius:var(--geo-radius-lg);background:var(--geo-color-surface-elevated);box-shadow:var(--geo-shadow-sm);display:inline-flex;align-items:center;justify-content:center;gap:6px;min-width:40px;min-height:40px;border:0;border-radius:var(--geo-radius);background:transparent;color:var(--geo-color-neutral-700);font:inherit;font-size:var(--geo-font-size-body-small);font-weight:var(--geo-font-weight-medium);line-height:1;cursor:pointer;transition:background-color .15s ease,color .15s ease,transform .1s ease;width:48px;min-height:48px;padding:0}.geo-map-locate__btn:hover:not(:disabled){background:var(--geo-color-primary-soft-hover);color:var(--geo-color-primary-default)}.geo-map-locate__btn:active:not(:disabled){transform:scale(.98)}.geo-map-locate__btn:disabled{opacity:.45;cursor:not-allowed}.geo-map-locate__btn--active,.geo-map-locate__btn--checked{background:var(--geo-color-primary-soft-active);color:var(--geo-color-primary-default)}.geo-map-locate__btn--icon-only{width:40px;padding:0}\n"] }]
|
|
71
48
|
}] });
|
|
72
|
-
//# sourceMappingURL=data:application/json;base64,
|
|
49
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZ2VvLW1hcC1sb2NhdGUuY29tcG9uZW50LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvZ2VvLXVpL3NyYy9saWIvZmlnbWEvZ2VvLW1hcC9jaHJvbWUvZ2VvLW1hcC1sb2NhdGUvZ2VvLW1hcC1sb2NhdGUuY29tcG9uZW50LnRzIiwiLi4vLi4vLi4vLi4vLi4vLi4vLi4vLi4vcHJvamVjdHMvZ2VvLXVpL3NyYy9saWIvZmlnbWEvZ2VvLW1hcC9jaHJvbWUvZ2VvLW1hcC1sb2NhdGUvZ2VvLW1hcC1sb2NhdGUuY29tcG9uZW50Lmh0bWwiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUNMLHVCQUF1QixFQUN2QixTQUFTLEVBQ1QsS0FBSyxFQUNMLE1BQU0sRUFDTixNQUFNLEVBQ04saUJBQWlCLEdBQ2xCLE1BQU0sZUFBZSxDQUFDO0FBQ3ZCLE9BQU8sRUFBRSxlQUFlLEVBQUUsTUFBTSx1QkFBdUIsQ0FBQztBQUN4RCxPQUFPLEVBQUUsZ0JBQWdCLEVBQUUsTUFBTSxzQ0FBc0MsQ0FBQztBQUd4RSxPQUFPLEVBQUUsZUFBZSxFQUFFLE1BQU0sdUJBQXVCLENBQUM7OztBQUV4RDs7Ozs7O0dBTUc7QUFXSCxNQUFNLE9BQU8scUJBQXFCO0lBQ3ZCLFVBQVUsR0FBRyxLQUFLLENBQTBCLElBQUksQ0FBQyxDQUFDO0lBQ2xELEtBQUssR0FBRyxLQUFLLENBQUMsZ0JBQWdCLENBQUMsQ0FBQztJQUVoQyxPQUFPLEdBQUcsTUFBTSxFQUFvQixDQUFDO0lBQ3JDLE1BQU0sR0FBRyxNQUFNLEVBQVEsQ0FBQztJQUN4QixXQUFXLEdBQUcsTUFBTSxFQUd6QixDQUFDO0lBRUksSUFBSSxHQUFHLE1BQU0sQ0FBQyxLQUFLLENBQUMsQ0FBQztJQUU5QixNQUFNO1FBQ0osTUFBTSxJQUFJLEdBQUcsSUFBSSxDQUFDLFVBQVUsRUFBRSxDQUFDO1FBQy9CLElBQUksQ0FBQyxJQUFJLElBQUksSUFBSSxDQUFDLElBQUksRUFBRSxFQUFFLENBQUM7WUFDekIsT0FBTztRQUNULENBQUM7UUFFRCxJQUFJLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxJQUFJLENBQUMsQ0FBQztRQUNwQixlQUFlLENBQUMsSUFBSSxFQUFFO1lBQ3BCLFNBQVMsRUFBRSxDQUFDLE1BQU0sRUFBRSxFQUFFO2dCQUNwQixJQUFJLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxLQUFLLENBQUMsQ0FBQztnQkFDckIsSUFBSSxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsTUFBTSxDQUFDLENBQUM7WUFDNUIsQ0FBQztZQUNELFFBQVEsRUFBRSxHQUFHLEVBQUU7Z0JBQ2IsSUFBSSxDQUFDLElBQUksQ0FBQyxHQUFHLENBQUMsS0FBSyxDQUFDLENBQUM7Z0JBQ3JCLElBQUksQ0FBQyxNQUFNLENBQUMsSUFBSSxFQUFFLENBQUM7WUFDckIsQ0FBQztZQUNELE9BQU8sRUFBRSxDQUFDLEtBQUssRUFBRSxFQUFFO2dCQUNqQixJQUFJLENBQUMsSUFBSSxDQUFDLEdBQUcsQ0FBQyxLQUFLLENBQUMsQ0FBQztnQkFDckIsSUFBSSxDQUFDLFdBQVcsQ0FBQyxJQUFJLENBQUMsS0FBSyxDQUFDLENBQUM7WUFDL0IsQ0FBQztTQUNGLENBQUMsQ0FBQztJQUNMLENBQUM7d0dBbENVLHFCQUFxQjs0RkFBckIscUJBQXFCLHFkQy9CbEMsb1JBV0EsZ3FDRGFZLGdCQUFnQix3R0FBRSxlQUFlOzs0RkFPaEMscUJBQXFCO2tCQVZqQyxTQUFTOytCQUNFLGdCQUFnQixjQUNkLElBQUksV0FDUCxDQUFDLGdCQUFnQixFQUFFLGVBQWUsQ0FBQyxtQkFHM0IsdUJBQXVCLENBQUMsTUFBTSxpQkFDaEMsaUJBQWlCLENBQUMsSUFBSSxRQUMvQixFQUFFLEtBQUssRUFBRSxxQkFBcUIsRUFBRSIsInNvdXJjZXNDb250ZW50IjpbImltcG9ydCB7XG4gIENoYW5nZURldGVjdGlvblN0cmF0ZWd5LFxuICBDb21wb25lbnQsXG4gIGlucHV0LFxuICBvdXRwdXQsXG4gIHNpZ25hbCxcbiAgVmlld0VuY2Fwc3VsYXRpb24sXG59IGZyb20gJ0Bhbmd1bGFyL2NvcmUnO1xuaW1wb3J0IHsgTnpUb29sVGlwTW9kdWxlIH0gZnJvbSAnbmctem9ycm8tYW50ZC90b29sdGlwJztcbmltcG9ydCB7IEdlb0ljb25Db21wb25lbnQgfSBmcm9tICcuLi8uLi8uLi9nZW8taWNvbi9nZW8taWNvbi5jb21wb25lbnQnO1xuaW1wb3J0IHsgR2VvTWFwQ29udHJvbGxlciB9IGZyb20gJy4uLy4uL2dlby1tYXAuY29udHJvbGxlcic7XG5pbXBvcnQgdHlwZSB7IEdlb01hcExvY2F0ZUVycm9yUmVhc29uIH0gZnJvbSAnLi4vLi4vZ2VvLW1hcC50eXBlcyc7XG5pbXBvcnQgeyBydW5HZW9NYXBMb2NhdGUgfSBmcm9tICcuL2dlby1tYXAtbG9jYXRlLnV0aWwnO1xuXG4vKipcbiAqIEdlb2xvY2F0aW9uIGJ1dHRvbjogY2VudGVyIG1hcCBvbiB1c2VyIGFmdGVyIHBlcm1pc3Npb24uXG4gKlxuICogQHN1bW1hcnkgR2VvbG9jYXRpb24gYnV0dG9uOiBjZW50ZXIgbWFwIG9uIHVzZXIgYWZ0ZXIgcGVybWlzc2lvbi5cbiAqIEB3aGVuVG9Vc2UgVuG7iyB0csOtIGPhu6dhIHTDtGkgdHLDqm4gYuG6o24gxJHhu5MuXG4gKiBAZG9Ob3RVc2VXaGVuIFNlcnZlci1zaWRlIHRyYWNraW5nLlxuICovXG5AQ29tcG9uZW50KHtcbiAgc2VsZWN0b3I6ICdnZW8tbWFwLWxvY2F0ZScsXG4gIHN0YW5kYWxvbmU6IHRydWUsXG4gIGltcG9ydHM6IFtHZW9JY29uQ29tcG9uZW50LCBOelRvb2xUaXBNb2R1bGVdLFxuICB0ZW1wbGF0ZVVybDogJy4vZ2VvLW1hcC1sb2NhdGUuY29tcG9uZW50Lmh0bWwnLFxuICBzdHlsZVVybDogJy4vZ2VvLW1hcC1sb2NhdGUuY29tcG9uZW50LnNjc3MnLFxuICBjaGFuZ2VEZXRlY3Rpb246IENoYW5nZURldGVjdGlvblN0cmF0ZWd5Lk9uUHVzaCxcbiAgZW5jYXBzdWxhdGlvbjogVmlld0VuY2Fwc3VsYXRpb24uTm9uZSxcbiAgaG9zdDogeyBjbGFzczogJ2dlby1tYXAtbG9jYXRlLWhvc3QnIH0sXG59KVxuZXhwb3J0IGNsYXNzIEdlb01hcExvY2F0ZUNvbXBvbmVudCB7XG4gIHJlYWRvbmx5IGNvbnRyb2xsZXIgPSBpbnB1dDxHZW9NYXBDb250cm9sbGVyIHwgbnVsbD4obnVsbCk7XG4gIHJlYWRvbmx5IGxhYmVsID0gaW5wdXQoJ1bhu4sgdHLDrSBj4bunYSB0w7RpJyk7XG5cbiAgcmVhZG9ubHkgbG9jYXRlZCA9IG91dHB1dDxbbnVtYmVyLCBudW1iZXJdPigpO1xuICByZWFkb25seSBkZW5pZWQgPSBvdXRwdXQ8dm9pZD4oKTtcbiAgcmVhZG9ubHkgbG9jYXRlRXJyb3IgPSBvdXRwdXQ8e1xuICAgIHJlYXNvbjogR2VvTWFwTG9jYXRlRXJyb3JSZWFzb247XG4gICAgbWVzc2FnZT86IHN0cmluZztcbiAgfT4oKTtcblxuICByZWFkb25seSBidXN5ID0gc2lnbmFsKGZhbHNlKTtcblxuICBsb2NhdGUoKTogdm9pZCB7XG4gICAgY29uc3QgY3RybCA9IHRoaXMuY29udHJvbGxlcigpO1xuICAgIGlmICghY3RybCB8fCB0aGlzLmJ1c3koKSkge1xuICAgICAgcmV0dXJuO1xuICAgIH1cblxuICAgIHRoaXMuYnVzeS5zZXQodHJ1ZSk7XG4gICAgcnVuR2VvTWFwTG9jYXRlKGN0cmwsIHtcbiAgICAgIG9uTG9jYXRlZDogKGxvbkxhdCkgPT4ge1xuICAgICAgICB0aGlzLmJ1c3kuc2V0KGZhbHNlKTtcbiAgICAgICAgdGhpcy5sb2NhdGVkLmVtaXQobG9uTGF0KTtcbiAgICAgIH0sXG4gICAgICBvbkRlbmllZDogKCkgPT4ge1xuICAgICAgICB0aGlzLmJ1c3kuc2V0KGZhbHNlKTtcbiAgICAgICAgdGhpcy5kZW5pZWQuZW1pdCgpO1xuICAgICAgfSxcbiAgICAgIG9uRXJyb3I6IChlcnJvcikgPT4ge1xuICAgICAgICB0aGlzLmJ1c3kuc2V0KGZhbHNlKTtcbiAgICAgICAgdGhpcy5sb2NhdGVFcnJvci5lbWl0KGVycm9yKTtcbiAgICAgIH0sXG4gICAgfSk7XG4gIH1cbn1cbiIsIjxidXR0b25cbiAgdHlwZT1cImJ1dHRvblwiXG4gIGNsYXNzPVwiZ2VvLW1hcC1sb2NhdGVfX2J0blwiXG4gIFtuei10b29sdGlwXT1cImxhYmVsKClcIlxuICBuelRvb2x0aXBQbGFjZW1lbnQ9XCJsZWZ0XCJcbiAgW2F0dHIuYXJpYS1sYWJlbF09XCJsYWJlbCgpXCJcbiAgW2Rpc2FibGVkXT1cIiFjb250cm9sbGVyKCkgfHwgYnVzeSgpXCJcbiAgKGNsaWNrKT1cImxvY2F0ZSgpXCJcbj5cbiAgPGdlby1pY29uIHR5cGU9XCJhaW1cIiBzaXplPVwibWRcIiAvPlxuPC9idXR0b24+XG4iXX0=
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import { fromLonLat } from 'ol/proj';
|
|
2
|
+
/**
|
|
3
|
+
* Shared browser-geolocation trigger — centers `ctrl` on the user and reports the outcome.
|
|
4
|
+
* Used by both `geo-map-locate` (standalone button) and `geo-map-shell`'s built-in locate
|
|
5
|
+
* toolbar action so the two never drift on error-reason mapping.
|
|
6
|
+
*/
|
|
7
|
+
export function runGeoMapLocate(ctrl, callbacks) {
|
|
8
|
+
if (typeof navigator === 'undefined' || !navigator.geolocation) {
|
|
9
|
+
callbacks.onError?.({
|
|
10
|
+
reason: 'unsupported',
|
|
11
|
+
message: 'Trình duyệt không hỗ trợ định vị.',
|
|
12
|
+
});
|
|
13
|
+
return;
|
|
14
|
+
}
|
|
15
|
+
navigator.geolocation.getCurrentPosition((pos) => {
|
|
16
|
+
const lonLat = [pos.coords.longitude, pos.coords.latitude];
|
|
17
|
+
const mercator = fromLonLat(lonLat);
|
|
18
|
+
ctrl.setCenter(mercator, Math.max(ctrl.getZoom() ?? 14, 14));
|
|
19
|
+
callbacks.onLocated?.(lonLat);
|
|
20
|
+
}, (err) => {
|
|
21
|
+
if (err.code === err.PERMISSION_DENIED) {
|
|
22
|
+
callbacks.onDenied?.();
|
|
23
|
+
callbacks.onError?.({ reason: 'denied', message: err.message });
|
|
24
|
+
return;
|
|
25
|
+
}
|
|
26
|
+
const reason = err.code === err.POSITION_UNAVAILABLE
|
|
27
|
+
? 'unavailable'
|
|
28
|
+
: err.code === err.TIMEOUT
|
|
29
|
+
? 'timeout'
|
|
30
|
+
: 'unknown';
|
|
31
|
+
callbacks.onError?.({ reason, message: err.message });
|
|
32
|
+
}, {
|
|
33
|
+
enableHighAccuracy: true,
|
|
34
|
+
timeout: 12000,
|
|
35
|
+
maximumAge: 0,
|
|
36
|
+
});
|
|
37
|
+
}
|
|
38
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZ2VvLW1hcC1sb2NhdGUudXRpbC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uLy4uLy4uLy4uLy4uL3Byb2plY3RzL2dlby11aS9zcmMvbGliL2ZpZ21hL2dlby1tYXAvY2hyb21lL2dlby1tYXAtbG9jYXRlL2dlby1tYXAtbG9jYXRlLnV0aWwudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFVBQVUsRUFBRSxNQUFNLFNBQVMsQ0FBQztBQVVyQzs7OztHQUlHO0FBQ0gsTUFBTSxVQUFVLGVBQWUsQ0FDN0IsSUFBc0IsRUFDdEIsU0FBZ0M7SUFFaEMsSUFBSSxPQUFPLFNBQVMsS0FBSyxXQUFXLElBQUksQ0FBQyxTQUFTLENBQUMsV0FBVyxFQUFFLENBQUM7UUFDL0QsU0FBUyxDQUFDLE9BQU8sRUFBRSxDQUFDO1lBQ2xCLE1BQU0sRUFBRSxhQUFhO1lBQ3JCLE9BQU8sRUFBRSxtQ0FBbUM7U0FDN0MsQ0FBQyxDQUFDO1FBQ0gsT0FBTztJQUNULENBQUM7SUFFRCxTQUFTLENBQUMsV0FBVyxDQUFDLGtCQUFrQixDQUN0QyxDQUFDLEdBQUcsRUFBRSxFQUFFO1FBQ04sTUFBTSxNQUFNLEdBQXFCLENBQUMsR0FBRyxDQUFDLE1BQU0sQ0FBQyxTQUFTLEVBQUUsR0FBRyxDQUFDLE1BQU0sQ0FBQyxRQUFRLENBQUMsQ0FBQztRQUM3RSxNQUFNLFFBQVEsR0FBRyxVQUFVLENBQUMsTUFBTSxDQUFDLENBQUM7UUFDcEMsSUFBSSxDQUFDLFNBQVMsQ0FBQyxRQUFRLEVBQUUsSUFBSSxDQUFDLEdBQUcsQ0FBQyxJQUFJLENBQUMsT0FBTyxFQUFFLElBQUksRUFBRSxFQUFFLEVBQUUsQ0FBQyxDQUFDLENBQUM7UUFDN0QsU0FBUyxDQUFDLFNBQVMsRUFBRSxDQUFDLE1BQU0sQ0FBQyxDQUFDO0lBQ2hDLENBQUMsRUFDRCxDQUFDLEdBQUcsRUFBRSxFQUFFO1FBQ04sSUFBSSxHQUFHLENBQUMsSUFBSSxLQUFLLEdBQUcsQ0FBQyxpQkFBaUIsRUFBRSxDQUFDO1lBQ3ZDLFNBQVMsQ0FBQyxRQUFRLEVBQUUsRUFBRSxDQUFDO1lBQ3ZCLFNBQVMsQ0FBQyxPQUFPLEVBQUUsQ0FBQyxFQUFFLE1BQU0sRUFBRSxRQUFRLEVBQUUsT0FBTyxFQUFFLEdBQUcsQ0FBQyxPQUFPLEVBQUUsQ0FBQyxDQUFDO1lBQ2hFLE9BQU87UUFDVCxDQUFDO1FBQ0QsTUFBTSxNQUFNLEdBQ1YsR0FBRyxDQUFDLElBQUksS0FBSyxHQUFHLENBQUMsb0JBQW9CO1lBQ25DLENBQUMsQ0FBQyxhQUFhO1lBQ2YsQ0FBQyxDQUFDLEdBQUcsQ0FBQyxJQUFJLEtBQUssR0FBRyxDQUFDLE9BQU87Z0JBQ3hCLENBQUMsQ0FBQyxTQUFTO2dCQUNYLENBQUMsQ0FBQyxTQUFTLENBQUM7UUFDbEIsU0FBUyxDQUFDLE9BQU8sRUFBRSxDQUFDLEVBQUUsTUFBTSxFQUFFLE9BQU8sRUFBRSxHQUFHLENBQUMsT0FBTyxFQUFFLENBQUMsQ0FBQztJQUN4RCxDQUFDLEVBQ0Q7UUFDRSxrQkFBa0IsRUFBRSxJQUFJO1FBQ3hCLE9BQU8sRUFBRSxLQUFLO1FBQ2QsVUFBVSxFQUFFLENBQUM7S0FDZCxDQUNGLENBQUM7QUFDSixDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgZnJvbUxvbkxhdCB9IGZyb20gJ29sL3Byb2onO1xuaW1wb3J0IHsgR2VvTWFwQ29udHJvbGxlciB9IGZyb20gJy4uLy4uL2dlby1tYXAuY29udHJvbGxlcic7XG5pbXBvcnQgdHlwZSB7IEdlb01hcExvY2F0ZUVycm9yUmVhc29uIH0gZnJvbSAnLi4vLi4vZ2VvLW1hcC50eXBlcyc7XG5cbmV4cG9ydCBpbnRlcmZhY2UgR2VvTWFwTG9jYXRlQ2FsbGJhY2tzIHtcbiAgb25Mb2NhdGVkPzogKGxvbkxhdDogW251bWJlciwgbnVtYmVyXSkgPT4gdm9pZDtcbiAgb25EZW5pZWQ/OiAoKSA9PiB2b2lkO1xuICBvbkVycm9yPzogKGVycm9yOiB7IHJlYXNvbjogR2VvTWFwTG9jYXRlRXJyb3JSZWFzb247IG1lc3NhZ2U/OiBzdHJpbmcgfSkgPT4gdm9pZDtcbn1cblxuLyoqXG4gKiBTaGFyZWQgYnJvd3Nlci1nZW9sb2NhdGlvbiB0cmlnZ2VyIOKAlCBjZW50ZXJzIGBjdHJsYCBvbiB0aGUgdXNlciBhbmQgcmVwb3J0cyB0aGUgb3V0Y29tZS5cbiAqIFVzZWQgYnkgYm90aCBgZ2VvLW1hcC1sb2NhdGVgIChzdGFuZGFsb25lIGJ1dHRvbikgYW5kIGBnZW8tbWFwLXNoZWxsYCdzIGJ1aWx0LWluIGxvY2F0ZVxuICogdG9vbGJhciBhY3Rpb24gc28gdGhlIHR3byBuZXZlciBkcmlmdCBvbiBlcnJvci1yZWFzb24gbWFwcGluZy5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHJ1bkdlb01hcExvY2F0ZShcbiAgY3RybDogR2VvTWFwQ29udHJvbGxlcixcbiAgY2FsbGJhY2tzOiBHZW9NYXBMb2NhdGVDYWxsYmFja3MsXG4pOiB2b2lkIHtcbiAgaWYgKHR5cGVvZiBuYXZpZ2F0b3IgPT09ICd1bmRlZmluZWQnIHx8ICFuYXZpZ2F0b3IuZ2VvbG9jYXRpb24pIHtcbiAgICBjYWxsYmFja3Mub25FcnJvcj8uKHtcbiAgICAgIHJlYXNvbjogJ3Vuc3VwcG9ydGVkJyxcbiAgICAgIG1lc3NhZ2U6ICdUcsOsbmggZHV54buHdCBraMO0bmcgaOG7lyB0cuG7oyDEkeG7i25oIHbhu4suJyxcbiAgICB9KTtcbiAgICByZXR1cm47XG4gIH1cblxuICBuYXZpZ2F0b3IuZ2VvbG9jYXRpb24uZ2V0Q3VycmVudFBvc2l0aW9uKFxuICAgIChwb3MpID0+IHtcbiAgICAgIGNvbnN0IGxvbkxhdDogW251bWJlciwgbnVtYmVyXSA9IFtwb3MuY29vcmRzLmxvbmdpdHVkZSwgcG9zLmNvb3Jkcy5sYXRpdHVkZV07XG4gICAgICBjb25zdCBtZXJjYXRvciA9IGZyb21Mb25MYXQobG9uTGF0KTtcbiAgICAgIGN0cmwuc2V0Q2VudGVyKG1lcmNhdG9yLCBNYXRoLm1heChjdHJsLmdldFpvb20oKSA/PyAxNCwgMTQpKTtcbiAgICAgIGNhbGxiYWNrcy5vbkxvY2F0ZWQ/Lihsb25MYXQpO1xuICAgIH0sXG4gICAgKGVycikgPT4ge1xuICAgICAgaWYgKGVyci5jb2RlID09PSBlcnIuUEVSTUlTU0lPTl9ERU5JRUQpIHtcbiAgICAgICAgY2FsbGJhY2tzLm9uRGVuaWVkPy4oKTtcbiAgICAgICAgY2FsbGJhY2tzLm9uRXJyb3I/Lih7IHJlYXNvbjogJ2RlbmllZCcsIG1lc3NhZ2U6IGVyci5tZXNzYWdlIH0pO1xuICAgICAgICByZXR1cm47XG4gICAgICB9XG4gICAgICBjb25zdCByZWFzb246IEdlb01hcExvY2F0ZUVycm9yUmVhc29uID1cbiAgICAgICAgZXJyLmNvZGUgPT09IGVyci5QT1NJVElPTl9VTkFWQUlMQUJMRVxuICAgICAgICAgID8gJ3VuYXZhaWxhYmxlJ1xuICAgICAgICAgIDogZXJyLmNvZGUgPT09IGVyci5USU1FT1VUXG4gICAgICAgICAgICA/ICd0aW1lb3V0J1xuICAgICAgICAgICAgOiAndW5rbm93bic7XG4gICAgICBjYWxsYmFja3Mub25FcnJvcj8uKHsgcmVhc29uLCBtZXNzYWdlOiBlcnIubWVzc2FnZSB9KTtcbiAgICB9LFxuICAgIHtcbiAgICAgIGVuYWJsZUhpZ2hBY2N1cmFjeTogdHJ1ZSxcbiAgICAgIHRpbWVvdXQ6IDEyMDAwLFxuICAgICAgbWF4aW11bUFnZTogMCxcbiAgICB9LFxuICApO1xufVxuIl19
|