my-openlayer 2.5.4 → 3.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/CHANGELOG.md +68 -0
- package/MyOl.d.ts +3 -22
- package/MyOl.js +52 -112
- package/README.md +116 -29
- package/core/line/Line.d.ts +24 -5
- package/core/line/Line.js +38 -10
- package/core/map/ConfigManager.d.ts +169 -89
- package/core/map/ConfigManager.js +157 -175
- package/core/map/MapBaseLayers.d.ts +6 -0
- package/core/map/MapBaseLayers.js +9 -0
- package/core/map/MapTools.d.ts +17 -1
- package/core/map/MapTools.js +39 -5
- package/core/point/Point.d.ts +54 -14
- package/core/point/Point.js +132 -76
- package/core/point/PointOverlay.d.ts +2 -4
- package/core/point/PointOverlay.js +2 -1
- package/core/point/PointPulseLayer.js +6 -4
- package/core/polygon/Polygon.d.ts +32 -17
- package/core/polygon/Polygon.js +87 -64
- package/core/polygon/PolygonHeatmapLayer.js +15 -2
- package/core/polygon/PolygonMaskLayer.d.ts +2 -2
- package/core/polygon/PolygonMaskLayer.js +3 -1
- package/core/polygon/PolygonStyleFactory.d.ts +4 -3
- package/core/projection/ProjectionManager.d.ts +66 -0
- package/core/projection/ProjectionManager.js +144 -0
- package/core/projection/index.d.ts +2 -0
- package/core/projection/index.js +1 -0
- package/core/select/SelectHandler.d.ts +1 -1
- package/core/vue-template-point/VueTemplatePoint.d.ts +2 -4
- package/core/vue-template-point/VueTemplatePoint.js +16 -2
- package/docs/.vitepress/config.mts +1 -0
- package/docs/Line.md +4 -4
- package/docs/MIGRATION-3.0.md +221 -0
- package/docs/Point.md +24 -6
- package/docs/Polygon.md +14 -5
- package/index.d.ts +6 -3
- package/index.js +4 -1
- package/package.json +6 -3
- package/types/base.d.ts +4 -4
- package/types/common.d.ts +8 -6
- package/types/handle.d.ts +34 -0
- package/types/handle.js +1 -0
- package/types/index.d.ts +1 -0
- package/types/line.d.ts +3 -2
- package/types/map.d.ts +1 -1
- package/types/point.d.ts +11 -3
- package/utils/ErrorHandler.d.ts +12 -0
- package/utils/ErrorHandler.js +21 -0
|
@@ -0,0 +1,221 @@
|
|
|
1
|
+
# my-openlayer 3.0 迁移指南
|
|
2
|
+
|
|
3
|
+
3.0 完成了一次系统性的 API 改造。图层类 `add*` 返回值会从原始 OpenLayers layer 改成统一 Handle;迁移后可以用同一套 `remove()` / `setVisible()` 管理生命周期。本指南分三段:
|
|
4
|
+
|
|
5
|
+
1. **必须改的**(编译错误)
|
|
6
|
+
2. **推荐改的**(用新 API 写新代码)
|
|
7
|
+
3. **保留旧 API 的期限**
|
|
8
|
+
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
## 1. 必须改的(编译错误)
|
|
12
|
+
|
|
13
|
+
### 1.1 `layerName` 在公开 `add*` 签名上变成必填
|
|
14
|
+
|
|
15
|
+
所有 `Point.addPoint / addClusterPoint / addPulsePointLayer`、`Line.addLine / addLineByUrl / addFlowLine / addFlowLineByUrl`、`Polygon.addPolygon / addPolygonByUrl` 现在要求 `options.layerName` 是 `string`(不再可选)。
|
|
16
|
+
|
|
17
|
+
```ts
|
|
18
|
+
// ❌ 2.x:layerName 可选,遗忘时取 ConfigManager 默认值 'lineLayer'
|
|
19
|
+
line.addLine(data)
|
|
20
|
+
line.addLine(data, { strokeColor: 'red' })
|
|
21
|
+
|
|
22
|
+
// ✅ 3.0:必须传 layerName
|
|
23
|
+
line.addLine(data, { layerName: 'my-line' })
|
|
24
|
+
line.addLine(data, { layerName: 'my-line', strokeColor: 'red' })
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
> **为什么**:依赖默认 `layerName` 的两次调用会互相覆盖,是 2.x 最常见的"图层莫名消失"陷阱。
|
|
28
|
+
|
|
29
|
+
`PointOptions / LineOptions / PolygonOptions` interface **本身**没改(`layerName?: string` 仍然可选),所以已有的工厂函数、配置对象不受影响 —— 只是公开方法签名收紧了。
|
|
30
|
+
|
|
31
|
+
### 1.2 `add*` 返回值改为 Handle
|
|
32
|
+
|
|
33
|
+
真实图层类 `add*` 不再直接返回 OpenLayers layer,而是返回统一 `LayerHandle`。
|
|
34
|
+
|
|
35
|
+
```ts
|
|
36
|
+
// ❌ 2.x
|
|
37
|
+
const layer = line.addLine(data, { layerName: 'l1' })
|
|
38
|
+
layer.getSource()
|
|
39
|
+
layer.setVisible(false)
|
|
40
|
+
|
|
41
|
+
// ✅ 3.0
|
|
42
|
+
const handle = line.addLine(data, { layerName: 'l1' })
|
|
43
|
+
handle.layer.getSource()
|
|
44
|
+
handle.setVisible(false)
|
|
45
|
+
handle.remove()
|
|
46
|
+
```
|
|
47
|
+
|
|
48
|
+
`addDomPoint` / `addVueTemplatePoint` 不是 OL 图层,3.0 返回 `ControlHandle`:
|
|
49
|
+
|
|
50
|
+
```ts
|
|
51
|
+
const domHandle = point.addDomPoint(points)
|
|
52
|
+
domHandle.target // Overlay[]
|
|
53
|
+
domHandle.anchors // 兼容原字段
|
|
54
|
+
|
|
55
|
+
const vueHandle = point.addVueTemplatePoint(points, Component)
|
|
56
|
+
vueHandle.target // VueTemplatePointInstance[]
|
|
57
|
+
vueHandle.getPoints() // 兼容原方法
|
|
58
|
+
```
|
|
59
|
+
|
|
60
|
+
---
|
|
61
|
+
|
|
62
|
+
## 2. 推荐改的(用新 API 写新代码)
|
|
63
|
+
|
|
64
|
+
### 2.1 用 `add*` 拿统一句柄
|
|
65
|
+
|
|
66
|
+
新代码统一用 `add*` 系列:
|
|
67
|
+
|
|
68
|
+
```ts
|
|
69
|
+
import type { LayerHandle } from 'my-openlayer'
|
|
70
|
+
|
|
71
|
+
// 跨 Point / Line / Polygon 一致的形态
|
|
72
|
+
const pointHandle: LayerHandle | null = myOl.getPoint().addPoint(data, { layerName: 'p1' })
|
|
73
|
+
const lineHandle: LayerHandle = myOl.getLine().addLine(data, { layerName: 'l1' })
|
|
74
|
+
const polyHandle: LayerHandle = myOl.getPolygon().addPolygon(data, { layerName: 'r1' })
|
|
75
|
+
|
|
76
|
+
// 统一生命周期
|
|
77
|
+
pointHandle?.setVisible(false)
|
|
78
|
+
pointHandle?.remove()
|
|
79
|
+
```
|
|
80
|
+
|
|
81
|
+
动画句柄(`PulsePointLayerHandle` / `FlowLineLayerHandle`)现在显式继承 `AnimatedLayerHandle`:
|
|
82
|
+
|
|
83
|
+
```ts
|
|
84
|
+
import type { AnimatedLayerHandle } from 'my-openlayer'
|
|
85
|
+
|
|
86
|
+
const flowHandle: AnimatedLayerHandle | null = myOl.getLine().addFlowLine(data, { layerName: 'flow' })
|
|
87
|
+
flowHandle?.start()
|
|
88
|
+
flowHandle?.pause?.()
|
|
89
|
+
flowHandle?.remove()
|
|
90
|
+
```
|
|
91
|
+
|
|
92
|
+
### 2.2 `*ByUrl` 统一异步返回 Handle
|
|
93
|
+
|
|
94
|
+
旧的 `Line.addLineByUrl` / `Polygon.addPolygonByUrl` 同步返回 layer,但 features 仍在异步加载,导致 `fitView` 经常失败、`getFeatures().length === 0`。3.0 改为先 `fetch` JSON,再调用对应 add 方法:
|
|
95
|
+
|
|
96
|
+
```ts
|
|
97
|
+
// ❌ 2.x:返回 layer 时 features 还在路上
|
|
98
|
+
const layer = polygon.addPolygonByUrl('/boundary.geojson', { layerName: 'b' })
|
|
99
|
+
// layer.getSource().getFeatures().length === 0 ← 经常踩坑
|
|
100
|
+
|
|
101
|
+
// ✅ 3.0:await 后拿到完整 LayerHandle
|
|
102
|
+
const handle = await polygon.addPolygonByUrl('/boundary.geojson', { layerName: 'b' })
|
|
103
|
+
console.log(handle.layer.getSource()?.getFeatures().length) // 准确
|
|
104
|
+
```
|
|
105
|
+
|
|
106
|
+
### 2.3 Point 新增 `*ByUrl` Promise API
|
|
107
|
+
|
|
108
|
+
之前 `Point` 没有任何 `*ByUrl` 方法,必须自己 `fetch + addPoint`。3.0 补齐:
|
|
109
|
+
|
|
110
|
+
```ts
|
|
111
|
+
// 从 URL 加载点位(自动识别 PointData[] 数组或 GeoJSON FeatureCollection)
|
|
112
|
+
const handle = await myOl.getPoint().addPointByUrl('/points.json', { layerName: 'p1' })
|
|
113
|
+
|
|
114
|
+
const handle = await myOl.getPoint().addPulsePointLayerByUrl('/villages.json', {
|
|
115
|
+
layerName: 'villages',
|
|
116
|
+
pulse: { enabled: true, frameCount: 24 }
|
|
117
|
+
})
|
|
118
|
+
```
|
|
119
|
+
|
|
120
|
+
### 2.4 投影注册抽到 `ProjectionManager`
|
|
121
|
+
|
|
122
|
+
2.x 用 `options.projection` 注册自定义投影。3.0 仍然支持,**外加**一个独立入口:
|
|
123
|
+
|
|
124
|
+
```ts
|
|
125
|
+
import { ProjectionManager } from 'my-openlayer'
|
|
126
|
+
|
|
127
|
+
// 应用启动时一次性注册自定义 EPSG
|
|
128
|
+
ProjectionManager.register({
|
|
129
|
+
code: 'EPSG:2380',
|
|
130
|
+
def: '+proj=tmerc +lat_0=0 +lon_0=117 +k=1 +x_0=500000 +y_0=0 +ellps=WGS84 +units=m +no_defs'
|
|
131
|
+
// units 省略时由 proj4 自动推导
|
|
132
|
+
})
|
|
133
|
+
|
|
134
|
+
// 之后任何 new MyOl({ projection: { code: 'EPSG:2380' } }) 都能直接用
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
### 2.5 `ConfigManager.setDefaults` 全局覆盖默认值
|
|
138
|
+
|
|
139
|
+
```ts
|
|
140
|
+
import { ConfigManager } from 'my-openlayer'
|
|
141
|
+
|
|
142
|
+
// 应用启动时把所有线的默认宽度改成 3px
|
|
143
|
+
ConfigManager.setDefaults('LINE_OPTIONS', { strokeWidth: 3 })
|
|
144
|
+
|
|
145
|
+
// 嵌套对象深合并
|
|
146
|
+
ConfigManager.setDefaults('FLOW_LINE_OPTIONS', {
|
|
147
|
+
flowSymbol: { scale: 1.2 } // 其它 flowSymbol 字段保持原默认
|
|
148
|
+
})
|
|
149
|
+
|
|
150
|
+
// 测试结束后重置
|
|
151
|
+
ConfigManager.resetDefaults() // 全部
|
|
152
|
+
ConfigManager.resetDefaults('LINE_OPTIONS') // 单组
|
|
153
|
+
```
|
|
154
|
+
|
|
155
|
+
所有现有 `add*` 方法都通过 `ConfigManager.DEFAULT_X` getter 读默认值,因此 `setDefaults` **立即对所有后续调用生效**,不需要改任何业务代码。
|
|
156
|
+
|
|
157
|
+
### 2.6 `PulsePointIconOptions.src` → `img`
|
|
158
|
+
|
|
159
|
+
为了和 `PointOptions.img` 命名统一:
|
|
160
|
+
|
|
161
|
+
```ts
|
|
162
|
+
// ❌ 2.x(仍可用,但 @deprecated)
|
|
163
|
+
point.addPulsePointLayer(data, {
|
|
164
|
+
layerName: 'p',
|
|
165
|
+
icon: { src: '/icon.svg', scale: 0.8 }
|
|
166
|
+
})
|
|
167
|
+
|
|
168
|
+
// ✅ 3.0
|
|
169
|
+
point.addPulsePointLayer(data, {
|
|
170
|
+
layerName: 'p',
|
|
171
|
+
icon: { img: '/icon.svg', scale: 0.8 }
|
|
172
|
+
})
|
|
173
|
+
```
|
|
174
|
+
|
|
175
|
+
PointPulseLayer 同时识别 `img` 和 `src`,平滑过渡。
|
|
176
|
+
|
|
177
|
+
### 2.7 用具体错误类型做精细化处理
|
|
178
|
+
|
|
179
|
+
```ts
|
|
180
|
+
import { LayerNotFoundError, InvalidGeoJSONError, ProjectionError } from 'my-openlayer'
|
|
181
|
+
|
|
182
|
+
try {
|
|
183
|
+
polygon.updateFeatureColor('nonexistent', { /* ... */ })
|
|
184
|
+
} catch (e) {
|
|
185
|
+
if (e instanceof LayerNotFoundError) {
|
|
186
|
+
// 友好提示
|
|
187
|
+
showToast(`图层 "${e.context.layerName}" 不存在,请先调用 addPolygon`)
|
|
188
|
+
} else if (e instanceof InvalidGeoJSONError) {
|
|
189
|
+
showToast('GeoJSON 数据格式有误')
|
|
190
|
+
} else {
|
|
191
|
+
throw e
|
|
192
|
+
}
|
|
193
|
+
}
|
|
194
|
+
```
|
|
195
|
+
|
|
196
|
+
---
|
|
197
|
+
|
|
198
|
+
## 3. 保留旧 API 的期限
|
|
199
|
+
|
|
200
|
+
下列旧 API 在 3.0 标了 `@deprecated`,**3.x 整个生命周期都仍然可用**,但 3.x 末尾(4.0)会移除。建议趁早迁移:
|
|
201
|
+
|
|
202
|
+
| 旧 API | 替代品 |
|
|
203
|
+
|---|---|
|
|
204
|
+
| `add*` 不传 `layerName`(仅使用 `ConfigManager.DEFAULT_*.layerName`) | `add*` 显式传 `layerName` |
|
|
205
|
+
| `addPolygonByUrl`(同步返回 layer) | `await addPolygonByUrl`(Promise<LayerHandle>) |
|
|
206
|
+
| `addLineByUrl`(同步返回 layer) | `await addLineByUrl`(Promise<LayerHandle>) |
|
|
207
|
+
| `MyOl.getView` | `MyOl.createView` |
|
|
208
|
+
| `PulsePointIconOptions.src` | `PulsePointIconOptions.img` |
|
|
209
|
+
| `(MyOl as any).initializeProjections` | `ProjectionManager.initialize` |
|
|
210
|
+
|
|
211
|
+
---
|
|
212
|
+
|
|
213
|
+
## 4. 升级前后检查清单
|
|
214
|
+
|
|
215
|
+
- [ ] 所有 `add*` 调用都显式传 `layerName`(TS 编译会提示)
|
|
216
|
+
- [ ] `addPolygonByUrl` / `addLineByUrl` 调用处加 `await`,并通过 `handle.layer` 访问底层图层
|
|
217
|
+
- [ ] `MyOl.destroy()` 调用后是否真的需要重建地图(destroy 已强化级联清理,老代码可能不再需要手动 stop 各 handle)
|
|
218
|
+
- [ ] 自定义投影注册:尝试迁移到 `ProjectionManager.register` 集中管理
|
|
219
|
+
- [ ] 全局样式默认值:用 `ConfigManager.setDefaults` 替代多处复制 options
|
|
220
|
+
|
|
221
|
+
升级过程中遇到任何"老代码 TS 编译过不去"的情况,请优先翻看本指南第 1 节。
|
package/docs/Point.md
CHANGED
|
@@ -94,24 +94,32 @@ constructor(map: Map)
|
|
|
94
94
|
添加普通点图层。
|
|
95
95
|
|
|
96
96
|
```typescript
|
|
97
|
-
addPoint(pointData: PointData[], options: PointOptions): VectorLayer<VectorSource
|
|
97
|
+
addPoint(pointData: PointData[], options: PointOptions & { layerName: string }): LayerHandle<VectorLayer<VectorSource>> | null
|
|
98
98
|
```
|
|
99
99
|
|
|
100
100
|
- **pointData**: 点位数据数组。
|
|
101
101
|
- **options**: 配置选项。
|
|
102
|
-
- **返回值**:
|
|
102
|
+
- **返回值**: `{ layer, remove(), setVisible() }` 形态的统一句柄;如果数据无效返回 `null`。
|
|
103
103
|
|
|
104
104
|
### addClusterPoint
|
|
105
105
|
|
|
106
106
|
添加聚合点图层。
|
|
107
107
|
|
|
108
108
|
```typescript
|
|
109
|
-
addClusterPoint(pointData: PointData[], options: ClusterOptions): VectorLayer<VectorSource
|
|
109
|
+
addClusterPoint(pointData: PointData[], options: ClusterOptions & { layerName: string }): LayerHandle<VectorLayer<VectorSource>> | null
|
|
110
110
|
```
|
|
111
111
|
|
|
112
112
|
- **pointData**: 点位数据数组。
|
|
113
113
|
- **options**: 聚合配置选项。
|
|
114
|
-
- **返回值**:
|
|
114
|
+
- **返回值**: `{ layer, remove(), setVisible() }` 形态的统一句柄。
|
|
115
|
+
|
|
116
|
+
### addPointByUrl
|
|
117
|
+
|
|
118
|
+
从 URL 加载点位数据,支持 `PointData[]` 数组或 GeoJSON FeatureCollection。
|
|
119
|
+
|
|
120
|
+
```typescript
|
|
121
|
+
addPointByUrl(url: string, options: PointOptions & { layerName: string }): Promise<LayerHandle<VectorLayer<VectorSource>> | null>
|
|
122
|
+
```
|
|
115
123
|
|
|
116
124
|
### addDomPoint
|
|
117
125
|
|
|
@@ -119,6 +127,7 @@ addClusterPoint(pointData: PointData[], options: ClusterOptions): VectorLayer<Ve
|
|
|
119
127
|
|
|
120
128
|
```typescript
|
|
121
129
|
addDomPoint(twinkleList: TwinkleItem[], callback?: Function): {
|
|
130
|
+
target: Overlay[],
|
|
122
131
|
anchors: Overlay[],
|
|
123
132
|
remove: () => void,
|
|
124
133
|
setVisible: (visible: boolean) => void
|
|
@@ -127,7 +136,7 @@ addDomPoint(twinkleList: TwinkleItem[], callback?: Function): {
|
|
|
127
136
|
|
|
128
137
|
- **twinkleList**: 包含经纬度和类名的数据列表。
|
|
129
138
|
- **callback**: 点击回调函数。
|
|
130
|
-
- **返回值**: 控制对象,包含 `remove` 和 `setVisible
|
|
139
|
+
- **返回值**: 控制对象,包含 `target`、`anchors`、`remove` 和 `setVisible`。
|
|
131
140
|
|
|
132
141
|
### addPulsePointLayer
|
|
133
142
|
|
|
@@ -141,12 +150,21 @@ addPulsePointLayer(pointData: PointData[], options: PulsePointOptions): PulsePoi
|
|
|
141
150
|
- **options**: 闪烁点配置选项,复用 `addPoint` 的图标、文本和图层参数习惯。
|
|
142
151
|
- **返回值**: 控制对象,包含动画启停、显隐、数据更新和移除方法;如果数据无效返回 `null`。
|
|
143
152
|
|
|
153
|
+
### addPulsePointLayerByUrl
|
|
154
|
+
|
|
155
|
+
从 URL 加载点位数据并添加高性能闪烁点图层。
|
|
156
|
+
|
|
157
|
+
```typescript
|
|
158
|
+
addPulsePointLayerByUrl(url: string, options: PulsePointOptions & { layerName: string }): Promise<PulsePointLayerHandle | null>
|
|
159
|
+
```
|
|
160
|
+
|
|
144
161
|
### addVueTemplatePoint
|
|
145
162
|
|
|
146
163
|
添加 Vue 组件作为点位。
|
|
147
164
|
|
|
148
165
|
```typescript
|
|
149
166
|
addVueTemplatePoint(pointDataList: PointData[], template: any, options?: VueTemplatePointOptions): {
|
|
167
|
+
target: VueTemplatePointInstance[],
|
|
150
168
|
setVisible: (visible: boolean) => void,
|
|
151
169
|
setOneVisibleByProp: (propName: string, propValue: any, visible: boolean) => void,
|
|
152
170
|
remove: () => void,
|
|
@@ -157,7 +175,7 @@ addVueTemplatePoint(pointDataList: PointData[], template: any, options?: VueTemp
|
|
|
157
175
|
- **pointDataList**: 点位数据列表。
|
|
158
176
|
- **template**: Vue 组件。
|
|
159
177
|
- **options**: 配置选项。
|
|
160
|
-
- **返回值**:
|
|
178
|
+
- **返回值**: 控制对象,包含 `target`、显示/隐藏、按属性显示/隐藏和移除方法。
|
|
161
179
|
|
|
162
180
|
## 使用示例
|
|
163
181
|
|
package/docs/Polygon.md
CHANGED
|
@@ -69,7 +69,7 @@ const polygon = new Polygon(map: Map);
|
|
|
69
69
|
添加多边形图层。
|
|
70
70
|
|
|
71
71
|
```typescript
|
|
72
|
-
addPolygon(data: MapJSONData, options
|
|
72
|
+
addPolygon(data: MapJSONData, options: PolygonOptions & { layerName: string }): LayerHandle<VectorLayer<VectorSource>>
|
|
73
73
|
```
|
|
74
74
|
|
|
75
75
|
| 参数 | 类型 | 说明 |
|
|
@@ -82,7 +82,7 @@ addPolygon(data: MapJSONData, options?: PolygonOptions): VectorLayer<VectorSourc
|
|
|
82
82
|
从 URL 加载多边形图层。
|
|
83
83
|
|
|
84
84
|
```typescript
|
|
85
|
-
addPolygonByUrl(url: string, options
|
|
85
|
+
addPolygonByUrl(url: string, options: PolygonOptions & { layerName: string }): Promise<LayerHandle<VectorLayer<VectorSource>>>
|
|
86
86
|
```
|
|
87
87
|
|
|
88
88
|
### addBorderPolygon
|
|
@@ -90,7 +90,8 @@ addPolygonByUrl(url: string, options?: PolygonOptions): VectorLayer<VectorSource
|
|
|
90
90
|
添加边界图层(通常用于行政区划边界,支持镂空效果)。
|
|
91
91
|
|
|
92
92
|
```typescript
|
|
93
|
-
addBorderPolygon(data: MapJSONData, options?: PolygonOptions): VectorLayer<VectorSource
|
|
93
|
+
addBorderPolygon(data: MapJSONData, options?: PolygonOptions): LayerHandle<VectorLayer<VectorSource>>
|
|
94
|
+
addBorderPolygonByUrl(url: string, options?: PolygonOptions): Promise<LayerHandle<VectorLayer<VectorSource>>>
|
|
94
95
|
```
|
|
95
96
|
|
|
96
97
|
### updateFeatureColor
|
|
@@ -116,7 +117,7 @@ updateFeatureColor(
|
|
|
116
117
|
添加静态图片图层(如叠加平面图、卫星图)。
|
|
117
118
|
|
|
118
119
|
```typescript
|
|
119
|
-
addImageLayer(imageData: ImageLayerData, options?: PolygonOptions): ImageLayer<any
|
|
120
|
+
addImageLayer(imageData: ImageLayerData, options?: PolygonOptions): LayerHandle<ImageLayer<any>>
|
|
120
121
|
```
|
|
121
122
|
|
|
122
123
|
### addHeatmap
|
|
@@ -124,7 +125,15 @@ addImageLayer(imageData: ImageLayerData, options?: PolygonOptions): ImageLayer<a
|
|
|
124
125
|
添加热力图。
|
|
125
126
|
|
|
126
127
|
```typescript
|
|
127
|
-
addHeatmap(pointData: PointData[], options?: HeatMapOptions):
|
|
128
|
+
addHeatmap(pointData: PointData[], options?: HeatMapOptions): LayerHandle<BaseLayer>
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
### addMaskLayer
|
|
132
|
+
|
|
133
|
+
添加遮罩图层。
|
|
134
|
+
|
|
135
|
+
```typescript
|
|
136
|
+
addMaskLayer(data: MapJSONData, options?: MaskLayerOptions): LayerHandle<VectorLayer<VectorSource>>
|
|
128
137
|
```
|
|
129
138
|
|
|
130
139
|
### setOutLayer
|
package/index.d.ts
CHANGED
|
@@ -7,10 +7,13 @@ export { Polygon } from './core/polygon';
|
|
|
7
7
|
export { MapBaseLayers, MapTools, MeasureHandler, ConfigManager, EventManager } from './core/map';
|
|
8
8
|
export { VueTemplatePoint } from './core/vue-template-point';
|
|
9
9
|
export { SelectHandler } from './core/select';
|
|
10
|
+
export { ProjectionManager, PROJECTIONS } from './core/projection';
|
|
11
|
+
export type { CustomProjectionRegistration } from './core/projection';
|
|
10
12
|
export type { MapEventType, EventCallback, MapEventData } from './core/map/EventManager';
|
|
11
|
-
export { ErrorHandler, MyOpenLayersError, ErrorType } from './utils/ErrorHandler';
|
|
13
|
+
export { ErrorHandler, MyOpenLayersError, ErrorType, LayerNotFoundError, InvalidGeoJSONError, ProjectionError } from './utils/ErrorHandler';
|
|
12
14
|
export { default as ValidationUtils } from './utils/ValidationUtils';
|
|
13
|
-
export type { BaseOptions, StyleOptions, TextOptions } from './types';
|
|
15
|
+
export type { BaseOptions, StyleOptions, TextOptions, LayerHandle, AnimatedLayerHandle } from './types';
|
|
14
16
|
export type { PointOptions, LineOptions, FlowLineOptions, FlowLineLayerHandle, PolygonOptions, PulsePointOptions, PulsePointLayerHandle } from './types';
|
|
15
17
|
export type { OptionsType } from './types';
|
|
16
|
-
export type { MapInitType, MapLayersOptions, HeatMapOptions, ImageLayerData, MaskLayerOptions, FeatureColorUpdateOptions, PointData, PulsePointIconOptions, LineData, ClusterOptions, MeasureHandlerType, VueTemplatePointOptions, MapJSONData, FeatureData, AnnotationType, TiandituType, MapLayers, AnnotationLayerOptions, SelectOptions, SelectMode, SelectCallbackEvent, ProgrammaticSelectOptions } from './types';
|
|
18
|
+
export type { MapInitType, MapLayersOptions, HeatMapOptions, ImageLayerData, MaskLayerOptions, FeatureColorUpdateOptions, PointData, PulsePointIconOptions, LineData, ClusterOptions, MeasureHandlerType, VueTemplatePointOptions, VueTemplatePointInstance, TwinkleItem, MapJSONData, FeatureData, AnnotationType, TiandituType, MapLayers, AnnotationLayerOptions, SelectOptions, SelectMode, SelectCallbackEvent, ProgrammaticSelectOptions } from './types';
|
|
19
|
+
export { VueTemplatePointState } from './types';
|
package/index.js
CHANGED
|
@@ -7,7 +7,10 @@ export { Polygon } from './core/polygon';
|
|
|
7
7
|
export { MapBaseLayers, MapTools, MeasureHandler, ConfigManager, EventManager } from './core/map';
|
|
8
8
|
export { VueTemplatePoint } from './core/vue-template-point';
|
|
9
9
|
export { SelectHandler } from './core/select';
|
|
10
|
+
export { ProjectionManager, PROJECTIONS } from './core/projection';
|
|
10
11
|
// 错误处理
|
|
11
|
-
export { ErrorHandler, MyOpenLayersError, ErrorType } from './utils/ErrorHandler';
|
|
12
|
+
export { ErrorHandler, MyOpenLayersError, ErrorType, LayerNotFoundError, InvalidGeoJSONError, ProjectionError } from './utils/ErrorHandler';
|
|
12
13
|
// 验证工具
|
|
13
14
|
export { default as ValidationUtils } from './utils/ValidationUtils';
|
|
15
|
+
// Vue 模板点位状态枚举(运行时值,需要单独导出)
|
|
16
|
+
export { VueTemplatePointState } from './types';
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "my-openlayer",
|
|
3
3
|
"private": false,
|
|
4
|
-
"version": "
|
|
4
|
+
"version": "3.0.1",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
7
7
|
"main": "index.js",
|
|
@@ -47,7 +47,8 @@
|
|
|
47
47
|
"publish-flat-dry": "npm run build && npm run prepare-publish && cd temp-publish && npm publish --dry-run",
|
|
48
48
|
"docs:dev": "vitepress dev docs",
|
|
49
49
|
"docs:build": "vitepress build docs",
|
|
50
|
-
"docs:preview": "vitepress preview docs"
|
|
50
|
+
"docs:preview": "vitepress preview docs",
|
|
51
|
+
"demo:build": "vite build --base /my-openlayer/demo/ --outDir demo-dist"
|
|
51
52
|
},
|
|
52
53
|
"dependencies": {
|
|
53
54
|
"@turf/turf": "^7.2.0",
|
|
@@ -57,12 +58,14 @@
|
|
|
57
58
|
"devDependencies": {
|
|
58
59
|
"@types/proj4": "^2.5.2",
|
|
59
60
|
"@vitejs/plugin-vue": "^5.0.4",
|
|
61
|
+
"happy-dom": "^20.9.0",
|
|
60
62
|
"typescript": "~5.6.2",
|
|
61
63
|
"vite": "^5.4.10",
|
|
62
|
-
"vitest": "^2.1.9",
|
|
63
64
|
"vite-plugin-css-modules": "^0.0.1",
|
|
64
65
|
"vite-plugin-libcss": "^1.1.1",
|
|
65
66
|
"vitepress": "^1.6.4",
|
|
67
|
+
"vitest": "^2.1.9",
|
|
68
|
+
"vue-router": "^4.6.4",
|
|
66
69
|
"vue-tsc": "^2.0.6"
|
|
67
70
|
},
|
|
68
71
|
"peerDependencies": {
|
package/types/base.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import
|
|
1
|
+
import { FeatureLike } from "ol/Feature";
|
|
2
2
|
import { Style } from "ol/style";
|
|
3
3
|
import type { MapJSONData } from "./common";
|
|
4
4
|
/**
|
|
@@ -17,7 +17,7 @@ export interface BaseOptions {
|
|
|
17
17
|
/**
|
|
18
18
|
* @deprecated 新项目请使用 dataProjection / featureProjection。
|
|
19
19
|
*/
|
|
20
|
-
projectionOptOptions?:
|
|
20
|
+
projectionOptOptions?: Record<string, unknown>;
|
|
21
21
|
style?: Style | Style[] | ((feature: FeatureLike) => Style | Style[]);
|
|
22
22
|
}
|
|
23
23
|
/**
|
|
@@ -29,7 +29,7 @@ export interface StyleOptions {
|
|
|
29
29
|
lineDash?: number[];
|
|
30
30
|
lineDashOffset?: number;
|
|
31
31
|
fillColor?: string;
|
|
32
|
-
fillColorCallBack?: (feature:
|
|
32
|
+
fillColorCallBack?: (feature: FeatureLike) => string;
|
|
33
33
|
withDefaultStroke?: boolean;
|
|
34
34
|
withDefaultFill?: boolean;
|
|
35
35
|
}
|
|
@@ -38,7 +38,7 @@ export interface StyleOptions {
|
|
|
38
38
|
*/
|
|
39
39
|
export interface TextOptions {
|
|
40
40
|
textVisible?: boolean;
|
|
41
|
-
textCallBack?: (feature:
|
|
41
|
+
textCallBack?: (feature: FeatureLike) => string;
|
|
42
42
|
textFont?: string;
|
|
43
43
|
textFillColor?: string;
|
|
44
44
|
textStrokeColor?: string;
|
package/types/common.d.ts
CHANGED
|
@@ -3,10 +3,10 @@
|
|
|
3
3
|
*/
|
|
4
4
|
export interface FeatureData {
|
|
5
5
|
type: string;
|
|
6
|
-
properties:
|
|
6
|
+
properties: Record<string, unknown>;
|
|
7
7
|
geometry: {
|
|
8
8
|
type: "Polygon" | "MultiPolygon" | "Point" | "LineString" | "MultiLineString" | "MultiPoint" | "GeometryCollection";
|
|
9
|
-
coordinates:
|
|
9
|
+
coordinates: number[] | number[][] | number[][][] | number[][][][];
|
|
10
10
|
};
|
|
11
11
|
}
|
|
12
12
|
/**
|
|
@@ -33,18 +33,18 @@ export type OptionsType = {
|
|
|
33
33
|
mapClipData?: MapJSONData;
|
|
34
34
|
dataProjection?: string;
|
|
35
35
|
featureProjection?: string;
|
|
36
|
-
projectionOptOptions?:
|
|
37
|
-
style?:
|
|
36
|
+
projectionOptOptions?: Record<string, unknown>;
|
|
37
|
+
style?: Style | Style[] | ((feature: FeatureLike) => Style | Style[]);
|
|
38
38
|
strokeColor?: string | number[];
|
|
39
39
|
strokeWidth?: number;
|
|
40
40
|
lineDash?: number[];
|
|
41
41
|
lineDashOffset?: number;
|
|
42
42
|
fillColor?: string;
|
|
43
|
-
fillColorCallBack?: (feature:
|
|
43
|
+
fillColorCallBack?: (feature: FeatureLike) => string;
|
|
44
44
|
withDefaultStroke?: boolean;
|
|
45
45
|
withDefaultFill?: boolean;
|
|
46
46
|
textVisible?: boolean;
|
|
47
|
-
textCallBack?: (feature:
|
|
47
|
+
textCallBack?: (feature: FeatureLike) => string;
|
|
48
48
|
textFont?: string;
|
|
49
49
|
textFillColor?: string;
|
|
50
50
|
textStrokeColor?: string;
|
|
@@ -57,3 +57,5 @@ export type OptionsType = {
|
|
|
57
57
|
type?: string;
|
|
58
58
|
mask?: boolean;
|
|
59
59
|
};
|
|
60
|
+
import type { FeatureLike } from "ol/Feature";
|
|
61
|
+
import type { Style } from "ol/style";
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* P1-1:统一图层句柄接口。
|
|
3
|
+
*
|
|
4
|
+
* 真实图层类 add* 方法在 3.0 之后都返回符合 LayerHandle 的对象,
|
|
5
|
+
* 用户记一次 `{ layer, remove, setVisible }` 就能跨 Point / Line / Polygon 通用。
|
|
6
|
+
*
|
|
7
|
+
* 动画句柄(流动线、闪烁点)扩展为 AnimatedLayerHandle,额外暴露 start/stop。
|
|
8
|
+
* Overlay / Vue 组件点这类非图层控制对象使用 ControlHandle,通过 target 暴露控制目标。
|
|
9
|
+
*/
|
|
10
|
+
import type BaseLayer from "ol/layer/Base";
|
|
11
|
+
export interface LayerHandle<L extends BaseLayer = BaseLayer> {
|
|
12
|
+
/** 实际的 OL 图层实例。 */
|
|
13
|
+
readonly layer: L;
|
|
14
|
+
/** 从地图移除此图层,停止所有动画与监听。可安全多次调用。 */
|
|
15
|
+
remove(): void;
|
|
16
|
+
/** 切换图层可见性。 */
|
|
17
|
+
setVisible(visible: boolean): void;
|
|
18
|
+
}
|
|
19
|
+
export interface AnimatedLayerHandle<L extends BaseLayer = BaseLayer> extends LayerHandle<L> {
|
|
20
|
+
start(): void;
|
|
21
|
+
stop(): void;
|
|
22
|
+
pause?(): void;
|
|
23
|
+
resume?(): void;
|
|
24
|
+
/** 更新底层数据(数据形态因实现而异)。 */
|
|
25
|
+
updateData?(data: unknown): void;
|
|
26
|
+
}
|
|
27
|
+
export interface ControlHandle<T = unknown> {
|
|
28
|
+
/** 非 OL 图层控制目标,例如 Overlay[] 或 VueTemplatePointInstance[]。 */
|
|
29
|
+
readonly target: T;
|
|
30
|
+
/** 移除控制目标。可安全多次调用。 */
|
|
31
|
+
remove(): void;
|
|
32
|
+
/** 切换控制目标可见性。 */
|
|
33
|
+
setVisible(visible: boolean): void;
|
|
34
|
+
}
|
package/types/handle.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
package/types/index.d.ts
CHANGED
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
export type { BaseOptions, StyleOptions, TextOptions } from './base';
|
|
2
|
+
export type { LayerHandle, AnimatedLayerHandle, ControlHandle } from './handle';
|
|
2
3
|
export type { FeatureData, MapJSONData, OptionsType, MeasureHandlerType, EventType } from './common';
|
|
3
4
|
export type { MapInitType, MapLayersOptions, MapLayers, AnnotationType, TiandituType, AnnotationLayerOptions, HeatMapOptions, ImageLayerData, MaskLayerOptions } from './map';
|
|
4
5
|
export type { PointOptions, PointData, ClusterOptions, PulsePointIconOptions, PulsePointOptions, PulsePointLayerHandle, TwinkleItem } from './point';
|
package/types/line.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import VectorLayer from "ol/layer/Vector";
|
|
2
2
|
import VectorSource from "ol/source/Vector";
|
|
3
3
|
import type { BaseOptions, StyleOptions, TextOptions } from "./base";
|
|
4
|
+
import type { AnimatedLayerHandle } from "./handle";
|
|
4
5
|
import type { MapJSONData } from "./common";
|
|
5
6
|
export interface LineOptions extends BaseOptions, StyleOptions, TextOptions {
|
|
6
7
|
type?: string;
|
|
@@ -8,7 +9,7 @@ export interface LineOptions extends BaseOptions, StyleOptions, TextOptions {
|
|
|
8
9
|
export interface LineData {
|
|
9
10
|
type: string;
|
|
10
11
|
coordinates: number[][];
|
|
11
|
-
[key: string]:
|
|
12
|
+
[key: string]: unknown;
|
|
12
13
|
}
|
|
13
14
|
export interface FlowLineOptions extends LineOptions {
|
|
14
15
|
loop?: boolean;
|
|
@@ -28,7 +29,7 @@ export interface FlowLineOptions extends LineOptions {
|
|
|
28
29
|
trailEnabled?: boolean;
|
|
29
30
|
trailLength?: number;
|
|
30
31
|
}
|
|
31
|
-
export interface FlowLineLayerHandle {
|
|
32
|
+
export interface FlowLineLayerHandle extends AnimatedLayerHandle<VectorLayer<VectorSource>> {
|
|
32
33
|
layer: VectorLayer<VectorSource>;
|
|
33
34
|
animationLayer: VectorLayer<VectorSource>;
|
|
34
35
|
start: () => void;
|
package/types/map.d.ts
CHANGED
package/types/point.d.ts
CHANGED
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import VectorLayer from "ol/layer/Vector";
|
|
2
2
|
import VectorSource from "ol/source/Vector";
|
|
3
3
|
import type { BaseOptions, StyleOptions, TextOptions } from "./base";
|
|
4
|
+
import type { AnimatedLayerHandle } from "./handle";
|
|
4
5
|
export interface PointOptions extends BaseOptions, StyleOptions, TextOptions {
|
|
5
6
|
textKey?: string;
|
|
6
7
|
img?: string;
|
|
@@ -10,13 +11,20 @@ export interface PointOptions extends BaseOptions, StyleOptions, TextOptions {
|
|
|
10
11
|
export interface PointData {
|
|
11
12
|
lgtd: number;
|
|
12
13
|
lttd: number;
|
|
13
|
-
[key: string]:
|
|
14
|
+
[key: string]: unknown;
|
|
14
15
|
}
|
|
15
16
|
export interface ClusterOptions extends PointOptions {
|
|
16
17
|
distance?: number;
|
|
17
18
|
minDistance?: number;
|
|
18
19
|
}
|
|
19
20
|
export interface PulsePointIconOptions {
|
|
21
|
+
/**
|
|
22
|
+
* 图标资源 URL。
|
|
23
|
+
*/
|
|
24
|
+
img?: string;
|
|
25
|
+
/**
|
|
26
|
+
* @deprecated 请使用 `img` 字段,3.x 末尾会移除。
|
|
27
|
+
*/
|
|
20
28
|
src?: string;
|
|
21
29
|
scale?: number;
|
|
22
30
|
color?: string;
|
|
@@ -38,7 +46,7 @@ export interface PulsePointOptions extends PointOptions {
|
|
|
38
46
|
frameCount?: number;
|
|
39
47
|
};
|
|
40
48
|
}
|
|
41
|
-
export interface PulsePointLayerHandle {
|
|
49
|
+
export interface PulsePointLayerHandle extends AnimatedLayerHandle<VectorLayer<VectorSource>> {
|
|
42
50
|
layer: VectorLayer<VectorSource>;
|
|
43
51
|
source: VectorSource;
|
|
44
52
|
start: () => void;
|
|
@@ -50,5 +58,5 @@ export interface PulsePointLayerHandle {
|
|
|
50
58
|
export interface TwinkleItem extends PointData {
|
|
51
59
|
className?: string;
|
|
52
60
|
element?: HTMLElement | ((item: TwinkleItem) => HTMLElement);
|
|
53
|
-
[key: string]:
|
|
61
|
+
[key: string]: unknown;
|
|
54
62
|
}
|
package/utils/ErrorHandler.d.ts
CHANGED
|
@@ -18,6 +18,18 @@ export declare class MyOpenLayersError extends Error {
|
|
|
18
18
|
readonly context?: any;
|
|
19
19
|
constructor(message: string, type: ErrorType, context?: any);
|
|
20
20
|
}
|
|
21
|
+
/**
|
|
22
|
+
* P2-2:具体错误子类,方便调用方用 instanceof 判分支。
|
|
23
|
+
*/
|
|
24
|
+
export declare class LayerNotFoundError extends MyOpenLayersError {
|
|
25
|
+
constructor(layerName: string, context?: any);
|
|
26
|
+
}
|
|
27
|
+
export declare class InvalidGeoJSONError extends MyOpenLayersError {
|
|
28
|
+
constructor(reason: string, context?: any);
|
|
29
|
+
}
|
|
30
|
+
export declare class ProjectionError extends MyOpenLayersError {
|
|
31
|
+
constructor(reason: string, context?: any);
|
|
32
|
+
}
|
|
21
33
|
/**
|
|
22
34
|
* 错误处理工具类
|
|
23
35
|
*/
|
package/utils/ErrorHandler.js
CHANGED
|
@@ -30,6 +30,27 @@ export class MyOpenLayersError extends Error {
|
|
|
30
30
|
}
|
|
31
31
|
}
|
|
32
32
|
}
|
|
33
|
+
/**
|
|
34
|
+
* P2-2:具体错误子类,方便调用方用 instanceof 判分支。
|
|
35
|
+
*/
|
|
36
|
+
export class LayerNotFoundError extends MyOpenLayersError {
|
|
37
|
+
constructor(layerName, context) {
|
|
38
|
+
super(`Layer '${layerName}' not found. 请检查 layerName 拼写、图层是否已被 remove,或在 fitView / removeLayer 调用前先 await *ByUrl。`, ErrorType.LAYER_ERROR, { layerName, ...context });
|
|
39
|
+
this.name = 'LayerNotFoundError';
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
export class InvalidGeoJSONError extends MyOpenLayersError {
|
|
43
|
+
constructor(reason, context) {
|
|
44
|
+
super(`Invalid GeoJSON data: ${reason}. 请检查数据是否为标准 GeoJSON FeatureCollection / Feature / Geometry。`, ErrorType.DATA_ERROR, context);
|
|
45
|
+
this.name = 'InvalidGeoJSONError';
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
export class ProjectionError extends MyOpenLayersError {
|
|
49
|
+
constructor(reason, context) {
|
|
50
|
+
super(`Projection error: ${reason}. 请确认 EPSG code 已通过 ProjectionManager.register 或 options.projection 注册。`, ErrorType.MAP_ERROR, context);
|
|
51
|
+
this.name = 'ProjectionError';
|
|
52
|
+
}
|
|
53
|
+
}
|
|
33
54
|
/**
|
|
34
55
|
* 错误处理工具类
|
|
35
56
|
*/
|