@versatiles/svelte 1.1.2 → 2.0.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/dist/components/BasicMap/BasicMap.svelte +4 -4
- package/dist/components/BasicMap/BasicMap.svelte.d.ts +2 -2
- package/dist/components/MapEditor/MapEditor.svelte +16 -3
- package/dist/components/MapEditor/components/Editor.svelte +56 -40
- package/dist/components/MapEditor/components/Editor.svelte.d.ts +1 -1
- package/dist/components/MapEditor/components/EditorFill.svelte +42 -12
- package/dist/components/MapEditor/components/EditorStroke.svelte +43 -13
- package/dist/components/MapEditor/components/EditorSymbol.svelte +105 -34
- package/dist/components/MapEditor/components/InputRow.svelte +34 -0
- package/dist/components/MapEditor/components/InputRow.svelte.d.ts +9 -0
- package/dist/components/MapEditor/components/Sidebar.svelte +119 -109
- package/dist/components/MapEditor/components/SidebarPanel.svelte +101 -0
- package/dist/components/MapEditor/components/SidebarPanel.svelte.d.ts +10 -0
- package/dist/components/MapEditor/components/SymbolSelector.svelte +7 -15
- package/dist/components/MapEditor/lib/element/abstract.d.ts +4 -4
- package/dist/components/MapEditor/lib/element/abstract.js +2 -2
- package/dist/components/MapEditor/lib/element/line.d.ts +3 -4
- package/dist/components/MapEditor/lib/element/line.js +0 -1
- package/dist/components/MapEditor/lib/element/marker.d.ts +4 -4
- package/dist/components/MapEditor/lib/element/polygon.d.ts +3 -3
- package/dist/components/MapEditor/lib/geometry_manager.d.ts +20 -10
- package/dist/components/MapEditor/lib/geometry_manager.js +42 -52
- package/dist/components/MapEditor/lib/map_layer/abstract.d.ts +2 -2
- package/dist/components/MapEditor/lib/map_layer/fill.d.ts +4 -3
- package/dist/components/MapEditor/lib/map_layer/fill.js +9 -17
- package/dist/components/MapEditor/lib/map_layer/line.d.ts +4 -3
- package/dist/components/MapEditor/lib/map_layer/line.js +15 -26
- package/dist/components/MapEditor/lib/map_layer/symbol.d.ts +5 -4
- package/dist/components/MapEditor/lib/map_layer/symbol.js +28 -46
- package/dist/components/MapEditor/lib/state/constants.d.ts +4 -0
- package/dist/components/MapEditor/lib/state/constants.js +22 -0
- package/dist/components/MapEditor/lib/state/manager.d.ts +17 -0
- package/dist/components/MapEditor/lib/state/manager.js +87 -0
- package/dist/components/MapEditor/lib/state/reader.d.ts +21 -14
- package/dist/components/MapEditor/lib/state/reader.js +259 -142
- package/dist/components/MapEditor/lib/state/types.d.ts +27 -12
- package/dist/components/MapEditor/lib/state/writer.d.ts +18 -14
- package/dist/components/MapEditor/lib/state/writer.js +182 -169
- package/dist/components/MapEditor/lib/utils.d.ts +2 -5
- package/dist/components/MapEditor/lib/utils.js +0 -19
- package/package.json +19 -19
@@ -1,9 +1,13 @@
|
|
1
1
|
<script lang="ts">
|
2
2
|
import Editor from './Editor.svelte';
|
3
3
|
import type { GeometryManager } from '../lib/geometry_manager.js';
|
4
|
+
import SidebarPanel from './SidebarPanel.svelte';
|
4
5
|
|
5
6
|
const { geometryManager, width }: { geometryManager: GeometryManager; width: number } = $props();
|
6
7
|
|
8
|
+
let history = geometryManager.state;
|
9
|
+
let undoEnabled = $state(geometryManager.state.undoEnabled);
|
10
|
+
let redoEnabled = $state(geometryManager.state.redoEnabled);
|
7
11
|
let activeElement = geometryManager.selectedElement;
|
8
12
|
|
9
13
|
function importGeoJSON() {
|
@@ -18,6 +22,7 @@
|
|
18
22
|
if (!evt.target) return alert('Failed to read file.');
|
19
23
|
const json = JSON.parse(evt.target.result as string);
|
20
24
|
geometryManager.addGeoJSON(json);
|
25
|
+
geometryManager.state.log();
|
21
26
|
} catch (error) {
|
22
27
|
console.error(error);
|
23
28
|
return alert('Failed to import GeoJSON. Please check the file format.');
|
@@ -41,137 +46,142 @@
|
|
41
46
|
a.click();
|
42
47
|
URL.revokeObjectURL(url);
|
43
48
|
}
|
49
|
+
|
50
|
+
function getLink() {
|
51
|
+
const url = new URL(window.location.href);
|
52
|
+
url.hash = geometryManager.state.getHash();
|
53
|
+
return url.href;
|
54
|
+
}
|
55
|
+
|
56
|
+
function copyLink() {
|
57
|
+
navigator.clipboard.writeText(getLink()).then(
|
58
|
+
() => alert('Link copied to clipboard!'),
|
59
|
+
() => alert('Failed to copy link. Please try again.')
|
60
|
+
);
|
61
|
+
}
|
62
|
+
|
63
|
+
function copyEmbedCode() {
|
64
|
+
const html = `<iframe style="width:100%; height:60vh" src="${getLink()}"></iframe>`;
|
65
|
+
navigator.clipboard.writeText(html).then(
|
66
|
+
() => alert('Embed code copied to clipboard!'),
|
67
|
+
() => alert('Failed to copy embed code. Please try again.')
|
68
|
+
);
|
69
|
+
}
|
44
70
|
</script>
|
45
71
|
|
46
|
-
<div class="sidebar" style="
|
47
|
-
<div style="
|
48
|
-
<div class="
|
49
|
-
|
50
|
-
<
|
51
|
-
<input type="button" value="Export" onclick={exportGeoJSON} />
|
72
|
+
<div class="sidebar" style="width: {width}px;">
|
73
|
+
<div style="margin-bottom: 36px;">
|
74
|
+
<div class="flex flex-two">
|
75
|
+
<button onclick={() => history.undo()} disabled={!$undoEnabled}>Undo</button>
|
76
|
+
<button onclick={() => history.redo()} disabled={!$redoEnabled}>Redo</button>
|
52
77
|
</div>
|
53
|
-
<
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
<
|
67
|
-
|
68
|
-
|
69
|
-
onclick={() => activeElement.set(geometryManager.addNewPolygon())}
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
78
|
+
<SidebarPanel title="Share map" open={false}>
|
79
|
+
<div class="flex flex-one">
|
80
|
+
<button value="Link" onclick={copyLink}>Link</button>
|
81
|
+
<button onclick={copyEmbedCode}>Embed Code</button>
|
82
|
+
</div>
|
83
|
+
</SidebarPanel>
|
84
|
+
<SidebarPanel title="Import/Export" open={false}>
|
85
|
+
<div class="flex flex-one">
|
86
|
+
<button onclick={importGeoJSON}>Import GeoJSON</button>
|
87
|
+
<button onclick={exportGeoJSON}>Export GeoJSON</button>
|
88
|
+
</div>
|
89
|
+
</SidebarPanel>
|
90
|
+
<SidebarPanel title="Add new">
|
91
|
+
<div class="flex flex-two">
|
92
|
+
<button onclick={() => activeElement.set(geometryManager.addNewMarker())}>Marker</button>
|
93
|
+
<button onclick={() => activeElement.set(geometryManager.addNewLine())}>Line</button>
|
94
|
+
<button onclick={() => activeElement.set(geometryManager.addNewPolygon())}>Polygon</button>
|
95
|
+
<button disabled>Circle</button>
|
96
|
+
</div>
|
97
|
+
</SidebarPanel>
|
98
|
+
<Editor element={$activeElement} />
|
99
|
+
<SidebarPanel title="Actions" disabled={!$activeElement}>
|
100
|
+
<div class="flex flex-two">
|
101
|
+
<button
|
102
|
+
onclick={() => {
|
103
|
+
$activeElement!.delete();
|
104
|
+
geometryManager.state.log();
|
105
|
+
}}>Delete</button
|
106
|
+
>
|
107
|
+
</div>
|
108
|
+
</SidebarPanel>
|
109
|
+
<SidebarPanel title="Help" open={false}>
|
110
|
+
Submit bugs and feature requests as
|
111
|
+
<a
|
112
|
+
id="github_link"
|
113
|
+
href="https://github.com/versatiles-org/node-versatiles-svelte/issues"
|
114
|
+
target="_blank"
|
115
|
+
aria-label="Repository on GitHub">GitHub issues</a
|
116
|
+
>
|
117
|
+
</SidebarPanel>
|
83
118
|
</div>
|
84
119
|
</div>
|
85
120
|
|
86
121
|
<style>
|
87
122
|
.sidebar {
|
88
|
-
|
123
|
+
--color-btn: #336680;
|
124
|
+
--color-bg: #ffffff;
|
125
|
+
--color-text: #000000;
|
126
|
+
--gap: 10px;
|
127
|
+
|
128
|
+
background-color: rgb(from var(--color-bg) r g b/ 0.7);
|
129
|
+
backdrop-filter: blur(10px);
|
130
|
+
box-sizing: border-box;
|
131
|
+
color: var(--color-text);
|
132
|
+
font-size: 0.8em;
|
89
133
|
height: 100%;
|
134
|
+
overflow-y: scroll;
|
135
|
+
padding: var(--gap);
|
90
136
|
position: absolute;
|
91
|
-
top: 0;
|
92
137
|
right: 0;
|
93
|
-
|
94
|
-
|
95
|
-
box-sizing: border-box;
|
96
|
-
padding: 0.5em var(--gap) 0;
|
97
|
-
border-left: 0.5px solid rgba(0, 0, 0, 0.5);
|
98
|
-
|
99
|
-
hr {
|
100
|
-
border: none;
|
101
|
-
border-top: 0.5px solid rgba(0, 0, 0, 1);
|
102
|
-
margin: var(--gap) 0 var(--gap);
|
103
|
-
}
|
104
|
-
|
105
|
-
:global(h2) {
|
106
|
-
font-size: 0.9em;
|
107
|
-
font-weight: normal;
|
108
|
-
opacity: 0.5;
|
109
|
-
padding-top: var(--gap);
|
110
|
-
border-top: 0.5px solid rgba(0, 0, 0, 1);
|
111
|
-
margin: var(--gap) 0 var(--gap);
|
112
|
-
text-align: center;
|
113
|
-
}
|
138
|
+
top: 0;
|
139
|
+
width: 200px;
|
114
140
|
|
115
|
-
|
116
|
-
|
141
|
+
.flex {
|
142
|
+
--gap: 5px;
|
143
|
+
align-items: center;
|
117
144
|
display: flex;
|
145
|
+
flex-wrap: wrap;
|
146
|
+
gap: var(--gap);
|
118
147
|
justify-content: space-between;
|
119
|
-
column-gap: var(--gap);
|
120
|
-
:global(input) {
|
121
|
-
flex-grow: 0;
|
122
|
-
}
|
123
|
-
}
|
124
|
-
|
125
|
-
:global(.row-input) {
|
126
148
|
margin: var(--gap) 0 var(--gap);
|
127
|
-
|
128
|
-
justify-content: space-between;
|
129
|
-
align-items: center;
|
130
|
-
& > :global(label) {
|
131
|
-
flex-grow: 0;
|
132
|
-
}
|
133
|
-
& > :global(button),
|
134
|
-
& > :global(input),
|
135
|
-
& > :global(select) {
|
136
|
-
width: 60%;
|
137
|
-
flex-grow: 0;
|
138
|
-
}
|
139
|
-
& > :global(input[type='checkbox']) {
|
140
|
-
width: auto;
|
141
|
-
}
|
149
|
+
width: 100%;
|
142
150
|
}
|
143
|
-
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
font-size: 0.8em;
|
151
|
+
.flex-two button {
|
152
|
+
flex-grow: 1;
|
153
|
+
flex-basis: 0;
|
154
|
+
width: 40%;
|
148
155
|
}
|
149
156
|
|
150
|
-
|
151
|
-
:global(input),
|
152
|
-
:global(select) {
|
157
|
+
.flex-one button {
|
153
158
|
width: 100%;
|
154
|
-
box-sizing: border-box;
|
155
|
-
margin: 0;
|
156
|
-
}
|
157
|
-
|
158
|
-
:global(p) {
|
159
|
-
font-size: 0.8em;
|
160
|
-
opacity: 0.5;
|
161
|
-
margin: 0.5em 0 1em;
|
162
159
|
}
|
163
160
|
|
164
|
-
|
165
|
-
|
166
|
-
|
167
|
-
|
168
|
-
|
169
|
-
|
170
|
-
|
171
|
-
|
172
|
-
|
173
|
-
|
161
|
+
button {
|
162
|
+
background-color: var(--color-btn);
|
163
|
+
border: 2px solid var(--color-btn);
|
164
|
+
border-radius: 0.2em;
|
165
|
+
color: var(--color-bg);
|
166
|
+
cursor: pointer;
|
167
|
+
font-weight: 600;
|
168
|
+
padding: 0.4em 1em;
|
169
|
+
transition:
|
170
|
+
background-color 0.1s ease-in-out,
|
171
|
+
color 0.1s ease-in-out;
|
172
|
+
|
173
|
+
&:not([disabled]):hover {
|
174
|
+
background-color: var(--color-bg);
|
175
|
+
color: var(--color-btn);
|
176
|
+
}
|
177
|
+
&:disabled {
|
178
|
+
cursor: not-allowed;
|
179
|
+
opacity: 0.5;
|
174
180
|
}
|
175
181
|
}
|
176
182
|
}
|
183
|
+
|
184
|
+
a {
|
185
|
+
color: var(--fg-color);
|
186
|
+
}
|
177
187
|
</style>
|
@@ -0,0 +1,101 @@
|
|
1
|
+
<script lang="ts">
|
2
|
+
import type { Snippet } from 'svelte';
|
3
|
+
|
4
|
+
let {
|
5
|
+
children,
|
6
|
+
disabled = false,
|
7
|
+
open = true,
|
8
|
+
title
|
9
|
+
}: { children: Snippet; disabled?: boolean; open?: boolean; title: string } = $props();
|
10
|
+
</script>
|
11
|
+
|
12
|
+
<div class={{ panel: true, open, disabled }}>
|
13
|
+
<button class="header" onclick={() => (open = !open)}>
|
14
|
+
<span class="title">{title}</span>
|
15
|
+
<div class="chevron">
|
16
|
+
<svg viewBox="0 0 7 12">
|
17
|
+
<path d="M1,0L7,6L1,12L0,11,L5,6L0,1z" />
|
18
|
+
</svg>
|
19
|
+
</div>
|
20
|
+
</button>
|
21
|
+
<div class="content">
|
22
|
+
{@render children()}
|
23
|
+
</div>
|
24
|
+
</div>
|
25
|
+
|
26
|
+
<style>
|
27
|
+
.panel {
|
28
|
+
margin: 1em 0;
|
29
|
+
|
30
|
+
.header {
|
31
|
+
background: none;
|
32
|
+
border: none;
|
33
|
+
color: var(--color-text);
|
34
|
+
cursor: pointer;
|
35
|
+
font-weight: 600;
|
36
|
+
margin: 0;
|
37
|
+
padding: 0;
|
38
|
+
position: relative;
|
39
|
+
text-align: left;
|
40
|
+
width: 100%;
|
41
|
+
|
42
|
+
.title {
|
43
|
+
opacity: 0.8;
|
44
|
+
text-transform: uppercase;
|
45
|
+
}
|
46
|
+
|
47
|
+
.chevron {
|
48
|
+
box-sizing: border-box;
|
49
|
+
display: block;
|
50
|
+
height: 1em;
|
51
|
+
opacity: 0.7;
|
52
|
+
padding: 0;
|
53
|
+
position: absolute;
|
54
|
+
right: 0.4em;
|
55
|
+
top: 0;
|
56
|
+
width: 1em;
|
57
|
+
|
58
|
+
svg {
|
59
|
+
fill: var(--color-fg);
|
60
|
+
height: 100%;
|
61
|
+
rotate: 0deg;
|
62
|
+
transform-origin: 40% 50%;
|
63
|
+
transition: rotate 0.1s linear;
|
64
|
+
width: 100%;
|
65
|
+
}
|
66
|
+
}
|
67
|
+
}
|
68
|
+
|
69
|
+
.content {
|
70
|
+
box-sizing: border-box;
|
71
|
+
height: 0;
|
72
|
+
margin: var(--gap) 0;
|
73
|
+
overflow: hidden;
|
74
|
+
padding: 0;
|
75
|
+
}
|
76
|
+
}
|
77
|
+
|
78
|
+
.open {
|
79
|
+
margin-bottom: 2em;
|
80
|
+
|
81
|
+
.header {
|
82
|
+
.chevron {
|
83
|
+
svg {
|
84
|
+
rotate: 90deg;
|
85
|
+
}
|
86
|
+
}
|
87
|
+
}
|
88
|
+
|
89
|
+
.content {
|
90
|
+
height: auto;
|
91
|
+
}
|
92
|
+
}
|
93
|
+
|
94
|
+
.disabled {
|
95
|
+
opacity: 0.3;
|
96
|
+
|
97
|
+
.content {
|
98
|
+
display: none;
|
99
|
+
}
|
100
|
+
}
|
101
|
+
</style>
|
@@ -0,0 +1,10 @@
|
|
1
|
+
import type { Snippet } from 'svelte';
|
2
|
+
type $$ComponentProps = {
|
3
|
+
children: Snippet;
|
4
|
+
disabled?: boolean;
|
5
|
+
open?: boolean;
|
6
|
+
title: string;
|
7
|
+
};
|
8
|
+
declare const SidebarPanel: import("svelte").Component<$$ComponentProps, {}, "">;
|
9
|
+
type SidebarPanel = ReturnType<typeof SidebarPanel>;
|
10
|
+
export default SidebarPanel;
|
@@ -7,17 +7,17 @@
|
|
7
7
|
symbolLibrary
|
8
8
|
}: { symbolIndex: number; symbolLibrary: SymbolLibrary } = $props();
|
9
9
|
|
10
|
-
let open = $state(false);
|
11
|
-
|
12
10
|
const drawIconHalo: Action<HTMLCanvasElement, number> = (canvas, index) =>
|
13
11
|
symbolLibrary.drawSymbol(canvas, index, true);
|
14
12
|
|
15
13
|
const drawIcon: Action<HTMLCanvasElement, number> = (canvas, index) =>
|
16
14
|
symbolLibrary.drawSymbol(canvas, index);
|
15
|
+
|
16
|
+
let dialog: HTMLDialogElement | null = null;
|
17
17
|
</script>
|
18
18
|
|
19
19
|
<button
|
20
|
-
onclick={() => (
|
20
|
+
onclick={() => dialog?.showModal()}
|
21
21
|
style="text-align: left; white-space: nowrap; overflow: hidden; padding: 1px"
|
22
22
|
>
|
23
23
|
{#key symbolIndex}
|
@@ -35,28 +35,20 @@
|
|
35
35
|
{/if}
|
36
36
|
</button>
|
37
37
|
|
38
|
-
<
|
39
|
-
<button class="close" onclick={() => (
|
38
|
+
<dialog class="modal" bind:this={dialog}>
|
39
|
+
<button class="close" onclick={() => dialog?.close()}>✕</button>
|
40
40
|
<div class="inner">
|
41
41
|
{#each symbolLibrary.asList() as symbol (symbol.index)}
|
42
|
-
<button
|
43
|
-
class="icon"
|
44
|
-
onclick={() => {
|
45
|
-
symbolIndex = symbol.index;
|
46
|
-
open = false;
|
47
|
-
}}
|
42
|
+
<button class="icon" onclick={() => (symbolIndex = symbol.index)}
|
48
43
|
><canvas width="64" height="64" use:drawIconHalo={symbol.index}></canvas><br
|
49
44
|
/>{symbol.name}</button
|
50
45
|
>
|
51
46
|
{/each}
|
52
47
|
</div>
|
53
|
-
</
|
48
|
+
</dialog>
|
54
49
|
|
55
50
|
<style>
|
56
51
|
.modal {
|
57
|
-
position: fixed;
|
58
|
-
top: max(calc(50vh - 250px), 0px);
|
59
|
-
left: max(calc(50vw - 250px), 0px);
|
60
52
|
width: min(500px, 100vw);
|
61
53
|
height: min(500px, 100vh);
|
62
54
|
background-color: rgba(255, 255, 255, 0.5);
|
@@ -1,21 +1,21 @@
|
|
1
1
|
import type { ElementPoint, SelectionNode, SelectionNodeUpdater } from './types.js';
|
2
2
|
import type { GeometryManager } from '../geometry_manager.js';
|
3
|
-
import type {
|
3
|
+
import type { StateElement } from '../state/types.js';
|
4
4
|
export declare abstract class AbstractElement {
|
5
5
|
protected readonly canvas: HTMLElement;
|
6
|
-
protected readonly manager: GeometryManager;
|
7
6
|
protected readonly map: maplibregl.Map;
|
8
7
|
protected readonly source: maplibregl.GeoJSONSource;
|
9
8
|
protected readonly slug: string;
|
10
9
|
protected isSelected: boolean;
|
10
|
+
readonly manager: GeometryManager;
|
11
11
|
readonly sourceId: string;
|
12
12
|
constructor(manager: GeometryManager);
|
13
13
|
select(value: boolean): void;
|
14
14
|
protected randomPositions(length: number): ElementPoint[];
|
15
15
|
delete(): void;
|
16
16
|
abstract destroy(): void;
|
17
|
-
abstract getFeature(includeProperties
|
17
|
+
abstract getFeature(includeProperties?: boolean): GeoJSON.Feature;
|
18
18
|
abstract getSelectionNodes(): SelectionNode[];
|
19
19
|
abstract getSelectionNodeUpdater(properties?: Record<string, unknown>): SelectionNodeUpdater | undefined;
|
20
|
-
abstract getState():
|
20
|
+
abstract getState(): StateElement;
|
21
21
|
}
|
@@ -1,10 +1,10 @@
|
|
1
1
|
export class AbstractElement {
|
2
2
|
canvas;
|
3
|
-
manager;
|
4
3
|
map;
|
5
4
|
source;
|
6
5
|
slug = '_' + Math.random().toString(36).slice(2);
|
7
6
|
isSelected = false;
|
7
|
+
manager;
|
8
8
|
sourceId = 'source' + this.slug;
|
9
9
|
constructor(manager) {
|
10
10
|
this.manager = manager;
|
@@ -33,7 +33,7 @@ export class AbstractElement {
|
|
33
33
|
return points;
|
34
34
|
}
|
35
35
|
delete() {
|
36
|
+
this.manager.removeElement(this);
|
36
37
|
this.destroy();
|
37
|
-
this.manager.deleteElement(this);
|
38
38
|
}
|
39
39
|
}
|
@@ -2,15 +2,14 @@ import type { GeometryManager } from '../geometry_manager.js';
|
|
2
2
|
import type { ElementPath } from './types.js';
|
3
3
|
import { MapLayerLine } from '../map_layer/line.js';
|
4
4
|
import { AbstractPathElement } from './abstract_path.js';
|
5
|
-
import type {
|
5
|
+
import type { StateElementLine } from '../state/types.js';
|
6
6
|
export declare class LineElement extends AbstractPathElement {
|
7
7
|
readonly layer: MapLayerLine;
|
8
|
-
readonly path: ElementPath;
|
9
8
|
constructor(manager: GeometryManager, line?: ElementPath);
|
10
9
|
select(value: boolean): void;
|
11
10
|
getFeature(includeProperties?: boolean): GeoJSON.Feature<GeoJSON.LineString>;
|
12
11
|
destroy(): void;
|
13
|
-
getState():
|
14
|
-
static fromState(manager: GeometryManager, state:
|
12
|
+
getState(): StateElementLine;
|
13
|
+
static fromState(manager: GeometryManager, state: StateElementLine): LineElement;
|
15
14
|
static fromGeoJSON(manager: GeometryManager, feature: GeoJSON.Feature<GeoJSON.LineString>): LineElement;
|
16
15
|
}
|
@@ -2,7 +2,6 @@ import { MapLayerLine } from '../map_layer/line.js';
|
|
2
2
|
import { AbstractPathElement } from './abstract_path.js';
|
3
3
|
export class LineElement extends AbstractPathElement {
|
4
4
|
layer;
|
5
|
-
path;
|
6
5
|
constructor(manager, line) {
|
7
6
|
super(manager, true);
|
8
7
|
this.path = line ?? this.randomPositions(2);
|
@@ -2,17 +2,17 @@ import { AbstractElement } from './abstract.js';
|
|
2
2
|
import type { GeometryManager } from '../geometry_manager.js';
|
3
3
|
import type { ElementPoint, SelectionNode, SelectionNodeUpdater } from './types.js';
|
4
4
|
import { MapLayerSymbol } from '../map_layer/symbol.js';
|
5
|
-
import type {
|
5
|
+
import type { StateElementMarker } from '../state/types.js';
|
6
6
|
export declare class MarkerElement extends AbstractElement {
|
7
7
|
readonly layer: MapLayerSymbol;
|
8
|
-
|
8
|
+
point: ElementPoint;
|
9
9
|
constructor(manager: GeometryManager, point?: ElementPoint);
|
10
10
|
select(value: boolean): void;
|
11
11
|
getFeature(includeProperties?: boolean): GeoJSON.Feature<GeoJSON.Point>;
|
12
12
|
getSelectionNodes(): SelectionNode[];
|
13
13
|
getSelectionNodeUpdater(): SelectionNodeUpdater | undefined;
|
14
14
|
destroy(): void;
|
15
|
-
getState():
|
16
|
-
static fromState(manager: GeometryManager, state:
|
15
|
+
getState(): StateElementMarker;
|
16
|
+
static fromState(manager: GeometryManager, state: StateElementMarker): MarkerElement;
|
17
17
|
static fromGeoJSON(manager: GeometryManager, feature: GeoJSON.Feature<GeoJSON.Point>): MarkerElement;
|
18
18
|
}
|
@@ -3,7 +3,7 @@ import type { ElementPath } from './types.js';
|
|
3
3
|
import { MapLayerFill } from '../map_layer/fill.js';
|
4
4
|
import { MapLayerLine } from '../map_layer/line.js';
|
5
5
|
import { AbstractPathElement } from './abstract_path.js';
|
6
|
-
import type {
|
6
|
+
import type { StateElementPolygon } from '../state/types.js';
|
7
7
|
export declare class PolygonElement extends AbstractPathElement {
|
8
8
|
readonly fillLayer: MapLayerFill;
|
9
9
|
readonly strokeLayer: MapLayerLine;
|
@@ -11,7 +11,7 @@ export declare class PolygonElement extends AbstractPathElement {
|
|
11
11
|
select(value: boolean): void;
|
12
12
|
getFeature(includeProperties?: boolean): GeoJSON.Feature<GeoJSON.Polygon>;
|
13
13
|
destroy(): void;
|
14
|
-
getState():
|
15
|
-
static fromState(manager: GeometryManager, state:
|
14
|
+
getState(): StateElementPolygon;
|
15
|
+
static fromState(manager: GeometryManager, state: StateElementPolygon): PolygonElement;
|
16
16
|
static fromGeoJSON(manager: GeometryManager, feature: GeoJSON.Feature<GeoJSON.Polygon>): PolygonElement;
|
17
17
|
}
|
@@ -1,8 +1,18 @@
|
|
1
1
|
import { type Writable } from 'svelte/store';
|
2
2
|
import type { AbstractElement } from './element/abstract.js';
|
3
|
+
import { MarkerElement } from './element/marker.js';
|
4
|
+
import { LineElement } from './element/line.js';
|
5
|
+
import { PolygonElement } from './element/polygon.js';
|
3
6
|
import { Cursor } from './cursor.js';
|
4
|
-
import type { StateObject } from './state/types.js';
|
5
7
|
import { SymbolLibrary } from './symbols.js';
|
8
|
+
import { StateManager } from './state/manager.js';
|
9
|
+
import type { StateRoot } from './state/types.js';
|
10
|
+
export type ExtendedGeoJSON = GeoJSON.FeatureCollection & {
|
11
|
+
map?: {
|
12
|
+
center: [number, number];
|
13
|
+
zoom: number;
|
14
|
+
};
|
15
|
+
};
|
6
16
|
export declare class GeometryManager {
|
7
17
|
readonly elements: Writable<AbstractElement[]>;
|
8
18
|
readonly map: maplibregl.Map;
|
@@ -10,19 +20,19 @@ export declare class GeometryManager {
|
|
10
20
|
readonly canvas: HTMLElement;
|
11
21
|
readonly cursor: Cursor;
|
12
22
|
readonly symbolLibrary: SymbolLibrary;
|
23
|
+
readonly state: StateManager;
|
13
24
|
private readonly selectionNodes;
|
14
25
|
constructor(map: maplibregl.Map);
|
15
26
|
selectElement(element: AbstractElement | undefined): void;
|
16
27
|
drawSelectionNodes(): void;
|
17
|
-
getState():
|
18
|
-
|
19
|
-
loadState(hash: string): Promise<void>;
|
28
|
+
getState(): StateRoot;
|
29
|
+
setState(state: StateRoot): void;
|
20
30
|
getElement(index: number): AbstractElement;
|
21
|
-
addNewMarker():
|
22
|
-
addNewLine():
|
23
|
-
addNewPolygon():
|
24
|
-
private
|
25
|
-
|
31
|
+
addNewMarker(): MarkerElement;
|
32
|
+
addNewLine(): LineElement;
|
33
|
+
addNewPolygon(): PolygonElement;
|
34
|
+
private appendElement;
|
35
|
+
removeElement(element: AbstractElement): void;
|
26
36
|
getGeoJSON(): GeoJSON.FeatureCollection;
|
27
|
-
addGeoJSON(geojson:
|
37
|
+
addGeoJSON(geojson: ExtendedGeoJSON): void;
|
28
38
|
}
|