@sakuzu/maplibre-gl-draw 1.0.0
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 +43 -0
- package/LICENSE +661 -0
- package/README.ja.md +248 -0
- package/README.md +255 -0
- package/THIRD_PARTY_NOTICES.md +275 -0
- package/dist/api/api.d.ts +1259 -0
- package/dist/api/api.js +86 -0
- package/dist/api/context.d.ts +173 -0
- package/dist/api/context.js +193 -0
- package/dist/api/display-api.d.ts +1 -0
- package/dist/api/display-api.js +23 -0
- package/dist/api/event-api.d.ts +13 -0
- package/dist/api/event-api.js +17 -0
- package/dist/api/extension-api.d.ts +46 -0
- package/dist/api/extension-api.js +85 -0
- package/dist/api/feature-api.d.ts +11 -0
- package/dist/api/feature-api.js +101 -0
- package/dist/api/geometry/apply.d.ts +51 -0
- package/dist/api/geometry/apply.js +114 -0
- package/dist/api/geometry/boolean.d.ts +28 -0
- package/dist/api/geometry/boolean.js +65 -0
- package/dist/api/geometry/buffer.d.ts +11 -0
- package/dist/api/geometry/buffer.js +105 -0
- package/dist/api/geometry/split.d.ts +16 -0
- package/dist/api/geometry/split.js +75 -0
- package/dist/api/geometry/targets.d.ts +76 -0
- package/dist/api/geometry/targets.js +158 -0
- package/dist/api/geometry/types.d.ts +31 -0
- package/dist/api/geometry/types.js +3 -0
- package/dist/api/geometry-operations.d.ts +162 -0
- package/dist/api/geometry-operations.js +94 -0
- package/dist/api/group-api.d.ts +10 -0
- package/dist/api/group-api.js +78 -0
- package/dist/api/import-export/constants.d.ts +29 -0
- package/dist/api/import-export/constants.js +40 -0
- package/dist/api/import-export/embedded-file.d.ts +13 -0
- package/dist/api/import-export/embedded-file.js +31 -0
- package/dist/api/import-export/file-name.d.ts +10 -0
- package/dist/api/import-export/file-name.js +20 -0
- package/dist/api/import-export/format-detection.d.ts +12 -0
- package/dist/api/import-export/format-detection.js +29 -0
- package/dist/api/import-export/geojson-export.d.ts +19 -0
- package/dist/api/import-export/geojson-export.js +262 -0
- package/dist/api/import-export/geojson-import.d.ts +34 -0
- package/dist/api/import-export/geojson-import.js +538 -0
- package/dist/api/import-export/geometry-validation.d.ts +20 -0
- package/dist/api/import-export/geometry-validation.js +107 -0
- package/dist/api/import-export/image-import.d.ts +12 -0
- package/dist/api/import-export/image-import.js +53 -0
- package/dist/api/import-export/index.d.ts +9 -0
- package/dist/api/import-export/index.js +107 -0
- package/dist/api/import-export/native-format.d.ts +15 -0
- package/dist/api/import-export/native-format.js +126 -0
- package/dist/api/import-export/native-validation.d.ts +28 -0
- package/dist/api/import-export/native-validation.js +212 -0
- package/dist/api/import-export/own-property.d.ts +10 -0
- package/dist/api/import-export/own-property.js +19 -0
- package/dist/api/import-export/style-validation.d.ts +27 -0
- package/dist/api/import-export/style-validation.js +49 -0
- package/dist/api/import-export/types.d.ts +26 -0
- package/dist/api/import-export/types.js +3 -0
- package/dist/api/index.d.ts +15 -0
- package/dist/api/index.js +3 -0
- package/dist/api/input-api.d.ts +158 -0
- package/dist/api/input-api.js +144 -0
- package/dist/api/instance-api.d.ts +38 -0
- package/dist/api/instance-api.js +136 -0
- package/dist/api/layer-api.d.ts +12 -0
- package/dist/api/layer-api.js +62 -0
- package/dist/api/selection-api.d.ts +7 -0
- package/dist/api/selection-api.js +78 -0
- package/dist/api/snapping-api.d.ts +125 -0
- package/dist/api/snapping-api.js +50 -0
- package/dist/api/topology-api.d.ts +30 -0
- package/dist/api/topology-api.js +16 -0
- package/dist/api/tracing-api.d.ts +31 -0
- package/dist/api/tracing-api.js +16 -0
- package/dist/dispatcher/hit-test/box-strategies.d.ts +19 -0
- package/dist/dispatcher/hit-test/box-strategies.js +275 -0
- package/dist/dispatcher/hit-test/box-strategy.d.ts +59 -0
- package/dist/dispatcher/hit-test/box-strategy.js +37 -0
- package/dist/dispatcher/hit-test/globe-shape.d.ts +46 -0
- package/dist/dispatcher/hit-test/globe-shape.js +70 -0
- package/dist/dispatcher/hit-test/index.d.ts +14 -0
- package/dist/dispatcher/hit-test/index.js +9 -0
- package/dist/dispatcher/hit-test/local-frame.d.ts +77 -0
- package/dist/dispatcher/hit-test/local-frame.js +112 -0
- package/dist/dispatcher/hit-test/segment-grid.d.ts +32 -0
- package/dist/dispatcher/hit-test/segment-grid.js +79 -0
- package/dist/dispatcher/hit-test/service.d.ts +120 -0
- package/dist/dispatcher/hit-test/service.js +333 -0
- package/dist/dispatcher/hit-test/strategies/base.d.ts +136 -0
- package/dist/dispatcher/hit-test/strategies/base.js +66 -0
- package/dist/dispatcher/hit-test/strategies/circle.d.ts +10 -0
- package/dist/dispatcher/hit-test/strategies/circle.js +56 -0
- package/dist/dispatcher/hit-test/strategies/image.d.ts +22 -0
- package/dist/dispatcher/hit-test/strategies/image.js +115 -0
- package/dist/dispatcher/hit-test/strategies/index.d.ts +11 -0
- package/dist/dispatcher/hit-test/strategies/index.js +10 -0
- package/dist/dispatcher/hit-test/strategies/line.d.ts +17 -0
- package/dist/dispatcher/hit-test/strategies/line.js +30 -0
- package/dist/dispatcher/hit-test/strategies/multi.d.ts +44 -0
- package/dist/dispatcher/hit-test/strategies/multi.js +141 -0
- package/dist/dispatcher/hit-test/strategies/point.d.ts +20 -0
- package/dist/dispatcher/hit-test/strategies/point.js +29 -0
- package/dist/dispatcher/hit-test/strategies/polygon.d.ts +52 -0
- package/dist/dispatcher/hit-test/strategies/polygon.js +138 -0
- package/dist/dispatcher/hit-test/topmost.d.ts +48 -0
- package/dist/dispatcher/hit-test/topmost.js +157 -0
- package/dist/dispatcher/hit-test/visibility-lookup.d.ts +23 -0
- package/dist/dispatcher/hit-test/visibility-lookup.js +40 -0
- package/dist/dispatcher/index.d.ts +15 -0
- package/dist/dispatcher/index.js +3 -0
- package/dist/dispatcher/input-router.d.ts +1 -0
- package/dist/dispatcher/input-router.js +288 -0
- package/dist/dispatcher/normalizer.d.ts +1 -0
- package/dist/dispatcher/normalizer.js +513 -0
- package/dist/dispatcher/types.d.ts +144 -0
- package/dist/dispatcher/types.js +15 -0
- package/dist/display/chunk-set.d.ts +24 -0
- package/dist/display/chunk-set.js +533 -0
- package/dist/display/chunk.d.ts +1 -0
- package/dist/display/chunk.js +104 -0
- package/dist/display/columnar/index.d.ts +12 -0
- package/dist/display/columnar/index.js +13 -0
- package/dist/display/columnar/prepare.d.ts +42 -0
- package/dist/display/columnar/prepare.js +116 -0
- package/dist/display/columnar/source.d.ts +1 -0
- package/dist/display/columnar/source.js +531 -0
- package/dist/display/columnar/table.d.ts +1 -0
- package/dist/display/columnar/table.js +471 -0
- package/dist/display/columnar/types.d.ts +223 -0
- package/dist/display/columnar/types.js +3 -0
- package/dist/display/dataset.d.ts +2 -0
- package/dist/display/dataset.js +891 -0
- package/dist/display/index.d.ts +13 -0
- package/dist/display/index.js +3 -0
- package/dist/display/interaction.d.ts +1 -0
- package/dist/display/interaction.js +90 -0
- package/dist/display/manager.d.ts +1 -0
- package/dist/display/manager.js +440 -0
- package/dist/display/packed-rtree.d.ts +1 -0
- package/dist/display/packed-rtree.js +244 -0
- package/dist/display/partition.d.ts +1 -0
- package/dist/display/partition.js +226 -0
- package/dist/display/provider.d.ts +1 -0
- package/dist/display/provider.js +342 -0
- package/dist/display/retained.d.ts +40 -0
- package/dist/display/retained.js +898 -0
- package/dist/display/selection.d.ts +13 -0
- package/dist/display/selection.js +226 -0
- package/dist/display/source.d.ts +1 -0
- package/dist/display/source.js +119 -0
- package/dist/display/spatial.d.ts +1 -0
- package/dist/display/spatial.js +71 -0
- package/dist/display/style.d.ts +1 -0
- package/dist/display/style.js +126 -0
- package/dist/display/thinning.d.ts +65 -0
- package/dist/display/thinning.js +910 -0
- package/dist/display/triangulation.d.ts +1 -0
- package/dist/display/triangulation.js +0 -0
- package/dist/display/types.d.ts +561 -0
- package/dist/display/types.js +43 -0
- package/dist/extension/feature-handler.d.ts +182 -0
- package/dist/extension/feature-handler.js +3 -0
- package/dist/extension/index.d.ts +9 -0
- package/dist/extension/index.js +3 -0
- package/dist/extension/renderers.d.ts +208 -0
- package/dist/extension/renderers.js +3 -0
- package/dist/geometry/angle.d.ts +47 -0
- package/dist/geometry/angle.js +44 -0
- package/dist/geometry/bbox.d.ts +48 -0
- package/dist/geometry/bbox.js +83 -0
- package/dist/geometry/boolean.d.ts +162 -0
- package/dist/geometry/boolean.js +331 -0
- package/dist/geometry/buffer.d.ts +72 -0
- package/dist/geometry/buffer.js +218 -0
- package/dist/geometry/circle.d.ts +55 -0
- package/dist/geometry/circle.js +107 -0
- package/dist/geometry/coords.d.ts +97 -0
- package/dist/geometry/coords.js +149 -0
- package/dist/geometry/distance.d.ts +79 -0
- package/dist/geometry/distance.js +111 -0
- package/dist/geometry/errors.d.ts +74 -0
- package/dist/geometry/errors.js +104 -0
- package/dist/geometry/index.d.ts +28 -0
- package/dist/geometry/index.js +38 -0
- package/dist/geometry/measure.d.ts +81 -0
- package/dist/geometry/measure.js +236 -0
- package/dist/geometry/predicates.d.ts +62 -0
- package/dist/geometry/predicates.js +132 -0
- package/dist/geometry/simplify.d.ts +74 -0
- package/dist/geometry/simplify.js +159 -0
- package/dist/geometry/split.d.ts +68 -0
- package/dist/geometry/split.js +430 -0
- package/dist/geometry/types.d.ts +95 -0
- package/dist/geometry/types.js +3 -0
- package/dist/geometry/units.d.ts +35 -0
- package/dist/geometry/units.js +41 -0
- package/dist/index.d.ts +72 -0
- package/dist/index.js +20 -0
- package/dist/maplibre-gl-draw.d.ts +47 -0
- package/dist/maplibre-gl-draw.js +407 -0
- package/dist/messages.d.ts +64 -0
- package/dist/messages.js +36 -0
- package/dist/modes/cursor.d.ts +1 -0
- package/dist/modes/cursor.js +72 -0
- package/dist/modes/draw/circle.d.ts +1 -0
- package/dist/modes/draw/circle.js +222 -0
- package/dist/modes/draw/commit-layer.d.ts +26 -0
- package/dist/modes/draw/commit-layer.js +31 -0
- package/dist/modes/draw/freehand.d.ts +1 -0
- package/dist/modes/draw/freehand.js +264 -0
- package/dist/modes/draw/image.d.ts +1 -0
- package/dist/modes/draw/image.js +60 -0
- package/dist/modes/draw/index.d.ts +9 -0
- package/dist/modes/draw/index.js +11 -0
- package/dist/modes/draw/line.d.ts +1 -0
- package/dist/modes/draw/line.js +363 -0
- package/dist/modes/draw/point.d.ts +1 -0
- package/dist/modes/draw/point.js +87 -0
- package/dist/modes/draw/polygon.d.ts +1 -0
- package/dist/modes/draw/polygon.js +378 -0
- package/dist/modes/draw/trace-support.d.ts +79 -0
- package/dist/modes/draw/trace-support.js +161 -0
- package/dist/modes/handler.d.ts +285 -0
- package/dist/modes/handler.js +3 -0
- package/dist/modes/index.d.ts +7 -0
- package/dist/modes/index.js +3 -0
- package/dist/modes/manager.d.ts +15 -0
- package/dist/modes/manager.js +196 -0
- package/dist/modes/select/box-selection.d.ts +52 -0
- package/dist/modes/select/box-selection.js +140 -0
- package/dist/modes/select/click-handler.d.ts +32 -0
- package/dist/modes/select/click-handler.js +166 -0
- package/dist/modes/select/cursor-handler.d.ts +15 -0
- package/dist/modes/select/cursor-handler.js +59 -0
- package/dist/modes/select/drag/auxiliary.d.ts +26 -0
- package/dist/modes/select/drag/auxiliary.js +56 -0
- package/dist/modes/select/drag/intermediate-writes.d.ts +1 -0
- package/dist/modes/select/drag/intermediate-writes.js +171 -0
- package/dist/modes/select/drag/move.d.ts +24 -0
- package/dist/modes/select/drag/move.js +59 -0
- package/dist/modes/select/drag/operation.d.ts +30 -0
- package/dist/modes/select/drag/operation.js +18 -0
- package/dist/modes/select/drag/radius.d.ts +15 -0
- package/dist/modes/select/drag/radius.js +49 -0
- package/dist/modes/select/drag/transform.d.ts +17 -0
- package/dist/modes/select/drag/transform.js +155 -0
- package/dist/modes/select/drag/vertex.d.ts +17 -0
- package/dist/modes/select/drag/vertex.js +163 -0
- package/dist/modes/select/drag-handler.d.ts +1 -0
- package/dist/modes/select/drag-handler.js +254 -0
- package/dist/modes/select/hit-helpers.d.ts +40 -0
- package/dist/modes/select/hit-helpers.js +51 -0
- package/dist/modes/select/mode.d.ts +1 -0
- package/dist/modes/select/mode.js +397 -0
- package/dist/modes/select/shortcut-handler.d.ts +40 -0
- package/dist/modes/select/shortcut-handler.js +128 -0
- package/dist/operations/index.d.ts +9 -0
- package/dist/operations/index.js +3 -0
- package/dist/operations/layer-operations.d.ts +1 -0
- package/dist/operations/layer-operations.js +350 -0
- package/dist/operations/resize.d.ts +71 -0
- package/dist/operations/resize.js +252 -0
- package/dist/operations/rotate.d.ts +17 -0
- package/dist/operations/rotate.js +166 -0
- package/dist/operations/selection-operations.d.ts +20 -0
- package/dist/operations/selection-operations.js +159 -0
- package/dist/operations/shared-vertex.d.ts +1 -0
- package/dist/operations/shared-vertex.js +210 -0
- package/dist/operations/trace-graph.d.ts +96 -0
- package/dist/operations/trace-graph.js +283 -0
- package/dist/operations/vertex.d.ts +1 -0
- package/dist/operations/vertex.js +538 -0
- package/dist/plugins/index.d.ts +10 -0
- package/dist/plugins/index.js +3 -0
- package/dist/plugins/mutation-hooks.d.ts +28 -0
- package/dist/plugins/mutation-hooks.js +84 -0
- package/dist/plugins/plugin-context.d.ts +1 -0
- package/dist/plugins/plugin-context.js +367 -0
- package/dist/plugins/plugin-manager.d.ts +103 -0
- package/dist/plugins/plugin-manager.js +316 -0
- package/dist/plugins/plugin.d.ts +529 -0
- package/dist/plugins/plugin.js +3 -0
- package/dist/shared/config/constants.d.ts +66 -0
- package/dist/shared/config/constants.js +60 -0
- package/dist/shared/config/feature-style.d.ts +155 -0
- package/dist/shared/config/feature-style.js +154 -0
- package/dist/shared/config/index.d.ts +17 -0
- package/dist/shared/config/index.js +8 -0
- package/dist/shared/config/rendering.d.ts +107 -0
- package/dist/shared/config/rendering.js +33 -0
- package/dist/shared/config/selection-highlight.d.ts +29 -0
- package/dist/shared/config/selection-highlight.js +35 -0
- package/dist/shared/config/selection.d.ts +273 -0
- package/dist/shared/config/selection.js +266 -0
- package/dist/shared/config/topology.d.ts +33 -0
- package/dist/shared/config/topology.js +17 -0
- package/dist/shared/config/trace.d.ts +40 -0
- package/dist/shared/config/trace.js +17 -0
- package/dist/shared/math/angle.d.ts +21 -0
- package/dist/shared/math/angle.js +34 -0
- package/dist/shared/math/circle.d.ts +6 -0
- package/dist/shared/math/circle.js +10 -0
- package/dist/shared/math/constants.d.ts +48 -0
- package/dist/shared/math/constants.js +59 -0
- package/dist/shared/math/distance.d.ts +78 -0
- package/dist/shared/math/distance.js +147 -0
- package/dist/shared/math/globe-subdivision.d.ts +62 -0
- package/dist/shared/math/globe-subdivision.js +99 -0
- package/dist/shared/math/index.d.ts +17 -0
- package/dist/shared/math/index.js +21 -0
- package/dist/shared/math/intersection.d.ts +63 -0
- package/dist/shared/math/intersection.js +236 -0
- package/dist/shared/math/longitude.d.ts +20 -0
- package/dist/shared/math/longitude.js +31 -0
- package/dist/shared/math/mercator-plane.d.ts +27 -0
- package/dist/shared/math/mercator-plane.js +26 -0
- package/dist/shared/math/obb.d.ts +65 -0
- package/dist/shared/math/obb.js +107 -0
- package/dist/shared/math/rotation.d.ts +93 -0
- package/dist/shared/math/rotation.js +186 -0
- package/dist/shared/math/segment-grid.d.ts +69 -0
- package/dist/shared/math/segment-grid.js +159 -0
- package/dist/shared/math/transform.d.ts +140 -0
- package/dist/shared/math/transform.js +189 -0
- package/dist/shared/types/events.d.ts +128 -0
- package/dist/shared/types/events.js +3 -0
- package/dist/shared/types/model.d.ts +950 -0
- package/dist/shared/types/model.js +3 -0
- package/dist/shared/types/selection-box.d.ts +23 -0
- package/dist/shared/types/selection-box.js +3 -0
- package/dist/shared/types/style.d.ts +68 -0
- package/dist/shared/types/style.js +3 -0
- package/dist/shared/utils/color.d.ts +49 -0
- package/dist/shared/utils/color.js +180 -0
- package/dist/shared/utils/coordinates.d.ts +52 -0
- package/dist/shared/utils/coordinates.js +75 -0
- package/dist/shared/utils/embedded-image.d.ts +34 -0
- package/dist/shared/utils/embedded-image.js +161 -0
- package/dist/shared/utils/event-emitter.d.ts +262 -0
- package/dist/shared/utils/event-emitter.js +44 -0
- package/dist/shared/utils/feature-bbox.d.ts +8 -0
- package/dist/shared/utils/feature-bbox.js +207 -0
- package/dist/shared/utils/feature-segments.d.ts +23 -0
- package/dist/shared/utils/feature-segments.js +179 -0
- package/dist/shared/utils/id.d.ts +1 -0
- package/dist/shared/utils/id.js +35 -0
- package/dist/shared/utils/image.d.ts +34 -0
- package/dist/shared/utils/image.js +106 -0
- package/dist/shared/utils/index.d.ts +15 -0
- package/dist/shared/utils/index.js +24 -0
- package/dist/shared/utils/map.d.ts +26 -0
- package/dist/shared/utils/map.js +35 -0
- package/dist/shared/utils/name-generator.d.ts +197 -0
- package/dist/shared/utils/name-generator.js +337 -0
- package/dist/shared/utils/pixel-ratio.d.ts +111 -0
- package/dist/shared/utils/pixel-ratio.js +85 -0
- package/dist/shared/utils/property.d.ts +88 -0
- package/dist/shared/utils/property.js +140 -0
- package/dist/shared/utils/vertex-ref.d.ts +23 -0
- package/dist/shared/utils/vertex-ref.js +20 -0
- package/dist/snapping/custom-targets.d.ts +1 -0
- package/dist/snapping/custom-targets.js +21 -0
- package/dist/snapping/geometry.d.ts +1 -0
- package/dist/snapping/geometry.js +61 -0
- package/dist/snapping/index.d.ts +14 -0
- package/dist/snapping/index.js +4 -0
- package/dist/snapping/indicator.d.ts +19 -0
- package/dist/snapping/indicator.js +145 -0
- package/dist/snapping/providers/display.d.ts +72 -0
- package/dist/snapping/providers/display.js +268 -0
- package/dist/snapping/providers/guide.d.ts +69 -0
- package/dist/snapping/providers/guide.js +187 -0
- package/dist/snapping/providers/intersection.d.ts +1 -0
- package/dist/snapping/providers/intersection.js +92 -0
- package/dist/snapping/providers/shared.d.ts +39 -0
- package/dist/snapping/providers/shared.js +146 -0
- package/dist/snapping/providers/store.d.ts +1 -0
- package/dist/snapping/providers/store.js +132 -0
- package/dist/snapping/service.d.ts +1 -0
- package/dist/snapping/service.js +272 -0
- package/dist/snapping/types.d.ts +267 -0
- package/dist/snapping/types.js +66 -0
- package/dist/store/change-merger.d.ts +1 -0
- package/dist/store/change-merger.js +102 -0
- package/dist/store/draw-store.d.ts +1 -0
- package/dist/store/draw-store.js +396 -0
- package/dist/store/event-bridge.d.ts +1 -0
- package/dist/store/event-bridge.js +161 -0
- package/dist/store/index.d.ts +12 -0
- package/dist/store/index.js +4 -0
- package/dist/store/local-visibility.d.ts +21 -0
- package/dist/store/local-visibility.js +27 -0
- package/dist/store/lock.d.ts +67 -0
- package/dist/store/lock.js +54 -0
- package/dist/store/memory/change-bus.d.ts +60 -0
- package/dist/store/memory/change-bus.js +232 -0
- package/dist/store/memory/file-store.d.ts +15 -0
- package/dist/store/memory/file-store.js +33 -0
- package/dist/store/memory/frozen.d.ts +21 -0
- package/dist/store/memory/frozen.js +51 -0
- package/dist/store/memory/ui-state.d.ts +51 -0
- package/dist/store/memory/ui-state.js +223 -0
- package/dist/store/memory.d.ts +26 -0
- package/dist/store/memory.js +708 -0
- package/dist/store/spatial/index.d.ts +6 -0
- package/dist/store/spatial/index.js +4 -0
- package/dist/store/spatial/spatial-index.d.ts +90 -0
- package/dist/store/spatial/spatial-index.js +148 -0
- package/dist/store/spatial/store-spatial-index.d.ts +60 -0
- package/dist/store/spatial/store-spatial-index.js +125 -0
- package/dist/store/store.d.ts +417 -0
- package/dist/store/store.js +3 -0
- package/dist/store/types.d.ts +8 -0
- package/dist/store/types.js +3 -0
- package/dist/store/writable-layer.d.ts +35 -0
- package/dist/store/writable-layer.js +20 -0
- package/dist/view/cache/buffer.d.ts +28 -0
- package/dist/view/cache/buffer.js +176 -0
- package/dist/view/cache/earcut.d.ts +1 -0
- package/dist/view/cache/earcut.js +122 -0
- package/dist/view/cache/style-rule.d.ts +1 -0
- package/dist/view/cache/style-rule.js +97 -0
- package/dist/view/cache/terrain-fill.d.ts +30 -0
- package/dist/view/cache/terrain-fill.js +60 -0
- package/dist/view/cache/texture.d.ts +14 -0
- package/dist/view/cache/texture.js +292 -0
- package/dist/view/coordinator.d.ts +27 -0
- package/dist/view/coordinator.js +72 -0
- package/dist/view/feature-companion.d.ts +173 -0
- package/dist/view/feature-companion.js +108 -0
- package/dist/view/globe-subdivision.d.ts +78 -0
- package/dist/view/globe-subdivision.js +128 -0
- package/dist/view/index.d.ts +47 -0
- package/dist/view/index.js +20 -0
- package/dist/view/layer/attach.d.ts +20 -0
- package/dist/view/layer/attach.js +47 -0
- package/dist/view/layer/blend.d.ts +57 -0
- package/dist/view/layer/blend.js +14 -0
- package/dist/view/layer/custom-layer.d.ts +1 -0
- package/dist/view/layer/custom-layer.js +509 -0
- package/dist/view/layer/depth-state.d.ts +14 -0
- package/dist/view/layer/depth-state.js +44 -0
- package/dist/view/layer/display-list.d.ts +1 -0
- package/dist/view/layer/display-list.js +111 -0
- package/dist/view/layer/drape-planner.d.ts +139 -0
- package/dist/view/layer/drape-planner.js +726 -0
- package/dist/view/layer/frame-render.d.ts +57 -0
- package/dist/view/layer/frame-render.js +209 -0
- package/dist/view/layer/frame-state.d.ts +147 -0
- package/dist/view/layer/frame-state.js +484 -0
- package/dist/view/layer/gl-state.d.ts +77 -0
- package/dist/view/layer/gl-state.js +132 -0
- package/dist/view/layer/index.d.ts +6 -0
- package/dist/view/layer/index.js +5 -0
- package/dist/view/layer/render-scope.d.ts +30 -0
- package/dist/view/layer/render-scope.js +28 -0
- package/dist/view/layer/render.d.ts +87 -0
- package/dist/view/layer/render.js +187 -0
- package/dist/view/layer/renderers.d.ts +81 -0
- package/dist/view/layer/renderers.js +142 -0
- package/dist/view/layer/slot-manager.d.ts +26 -0
- package/dist/view/layer/slot-manager.js +133 -0
- package/dist/view/layer/slots.d.ts +33 -0
- package/dist/view/layer/slots.js +50 -0
- package/dist/view/layer/store-retained-bbox.d.ts +36 -0
- package/dist/view/layer/store-retained-bbox.js +188 -0
- package/dist/view/layer/store-retained-chunk.d.ts +97 -0
- package/dist/view/layer/store-retained-chunk.js +94 -0
- package/dist/view/layer/store-retained-classify.d.ts +34 -0
- package/dist/view/layer/store-retained-classify.js +88 -0
- package/dist/view/layer/store-retained-collect.d.ts +24 -0
- package/dist/view/layer/store-retained-collect.js +121 -0
- package/dist/view/layer/store-retained-coord-patch.d.ts +119 -0
- package/dist/view/layer/store-retained-coord-patch.js +168 -0
- package/dist/view/layer/store-retained-immediate.d.ts +63 -0
- package/dist/view/layer/store-retained-immediate.js +49 -0
- package/dist/view/layer/store-retained-invalidation.d.ts +96 -0
- package/dist/view/layer/store-retained-invalidation.js +192 -0
- package/dist/view/layer/store-retained.d.ts +198 -0
- package/dist/view/layer/store-retained.js +430 -0
- package/dist/view/layer/terrain-resolver.d.ts +1 -0
- package/dist/view/layer/terrain-resolver.js +174 -0
- package/dist/view/renderers/batch-manager.d.ts +61 -0
- package/dist/view/renderers/batch-manager.js +718 -0
- package/dist/view/renderers/draw-factors.d.ts +60 -0
- package/dist/view/renderers/draw-factors.js +35 -0
- package/dist/view/renderers/drawer.d.ts +1 -0
- package/dist/view/renderers/drawer.js +346 -0
- package/dist/view/renderers/image.d.ts +1 -0
- package/dist/view/renderers/image.js +255 -0
- package/dist/view/renderers/line/dash.d.ts +31 -0
- package/dist/view/renderers/line/dash.js +152 -0
- package/dist/view/renderers/line/line-geometry.d.ts +39 -0
- package/dist/view/renderers/line/line-geometry.js +460 -0
- package/dist/view/renderers/line/line-gl.d.ts +1 -0
- package/dist/view/renderers/line/line-gl.js +236 -0
- package/dist/view/renderers/line/line-shader.d.ts +1 -0
- package/dist/view/renderers/line/line-shader.js +364 -0
- package/dist/view/renderers/line/line-types.d.ts +43 -0
- package/dist/view/renderers/line/line-types.js +3 -0
- package/dist/view/renderers/line/line-uniforms.d.ts +1 -0
- package/dist/view/renderers/line/line-uniforms.js +390 -0
- package/dist/view/renderers/line/sdf-line.d.ts +92 -0
- package/dist/view/renderers/line/sdf-line.js +567 -0
- package/dist/view/renderers/point/billboard-depth.d.ts +10 -0
- package/dist/view/renderers/point/billboard-depth.js +56 -0
- package/dist/view/renderers/point/point-instance.d.ts +124 -0
- package/dist/view/renderers/point/point-instance.js +738 -0
- package/dist/view/renderers/point/point-sdf.d.ts +58 -0
- package/dist/view/renderers/point/point-sdf.js +170 -0
- package/dist/view/renderers/point/point-shape.d.ts +99 -0
- package/dist/view/renderers/point/point-shape.js +504 -0
- package/dist/view/renderers/point/point-style.d.ts +1 -0
- package/dist/view/renderers/point/point-style.js +46 -0
- package/dist/view/renderers/polygon/batch.d.ts +26 -0
- package/dist/view/renderers/polygon/batch.js +336 -0
- package/dist/view/renderers/polygon/earcut-input.d.ts +37 -0
- package/dist/view/renderers/polygon/earcut-input.js +55 -0
- package/dist/view/renderers/polygon/earcut-sliced.d.ts +69 -0
- package/dist/view/renderers/polygon/earcut-sliced.js +960 -0
- package/dist/view/renderers/polygon/fill.d.ts +74 -0
- package/dist/view/renderers/polygon/fill.js +251 -0
- package/dist/view/renderers/polygon/sdf-polygon.d.ts +62 -0
- package/dist/view/renderers/polygon/sdf-polygon.js +919 -0
- package/dist/view/renderers/polygon/terrain-cull.d.ts +3 -0
- package/dist/view/renderers/polygon/terrain-cull.js +14 -0
- package/dist/view/renderers/polygon/triangulator.d.ts +41 -0
- package/dist/view/renderers/polygon/triangulator.js +3 -0
- package/dist/view/renderers/retained.d.ts +43 -0
- package/dist/view/renderers/retained.js +3 -0
- package/dist/view/renderers/stroke.d.ts +121 -0
- package/dist/view/renderers/stroke.js +621 -0
- package/dist/view/shaders/frame.d.ts +8 -0
- package/dist/view/shaders/frame.js +37 -0
- package/dist/view/shaders/helpers.d.ts +238 -0
- package/dist/view/shaders/helpers.js +611 -0
- package/dist/view/shaders/initializer.d.ts +27 -0
- package/dist/view/shaders/initializer.js +125 -0
- package/dist/view/shaders/projection.d.ts +123 -0
- package/dist/view/shaders/projection.js +299 -0
- package/dist/view/shaders/quad-grid.d.ts +77 -0
- package/dist/view/shaders/quad-grid.js +128 -0
- package/dist/view/shaders/quad.d.ts +189 -0
- package/dist/view/shaders/quad.js +582 -0
- package/dist/view/shaders/retained-origin.d.ts +50 -0
- package/dist/view/shaders/retained-origin.js +67 -0
- package/dist/view/shaders/terrain-shade.d.ts +23 -0
- package/dist/view/shaders/terrain-shade.js +93 -0
- package/dist/view/style-rule.d.ts +166 -0
- package/dist/view/style-rule.js +300 -0
- package/dist/view/terrain/anchor.d.ts +135 -0
- package/dist/view/terrain/anchor.js +226 -0
- package/dist/view/terrain/context.d.ts +132 -0
- package/dist/view/terrain/context.js +437 -0
- package/dist/view/terrain/dem-atlas.d.ts +97 -0
- package/dist/view/terrain/dem-atlas.js +534 -0
- package/dist/view/terrain/detect.d.ts +126 -0
- package/dist/view/terrain/detect.js +198 -0
- package/dist/view/terrain/drape/bin-store.d.ts +179 -0
- package/dist/view/terrain/drape/bin-store.js +529 -0
- package/dist/view/terrain/drape/binning.d.ts +259 -0
- package/dist/view/terrain/drape/binning.js +604 -0
- package/dist/view/terrain/drape/edge-constrain.d.ts +37 -0
- package/dist/view/terrain/drape/edge-constrain.js +175 -0
- package/dist/view/terrain/drape/geometry.d.ts +95 -0
- package/dist/view/terrain/drape/geometry.js +260 -0
- package/dist/view/terrain/drape/mesh.d.ts +50 -0
- package/dist/view/terrain/drape/mesh.js +86 -0
- package/dist/view/terrain/drape/pass.d.ts +122 -0
- package/dist/view/terrain/drape/pass.js +379 -0
- package/dist/view/terrain/drape/quad-glyphs.d.ts +64 -0
- package/dist/view/terrain/drape/quad-glyphs.js +117 -0
- package/dist/view/terrain/drape/quad.d.ts +249 -0
- package/dist/view/terrain/drape/quad.js +835 -0
- package/dist/view/terrain/drape/renderer.d.ts +184 -0
- package/dist/view/terrain/drape/renderer.js +706 -0
- package/dist/view/terrain/drape/shared.d.ts +80 -0
- package/dist/view/terrain/drape/shared.js +173 -0
- package/dist/view/terrain/drape/stitch.d.ts +155 -0
- package/dist/view/terrain/drape/stitch.js +228 -0
- package/dist/view/terrain/ground.d.ts +72 -0
- package/dist/view/terrain/ground.js +151 -0
- package/dist/view/terrain/metrics.d.ts +180 -0
- package/dist/view/terrain/metrics.js +231 -0
- package/dist/view/terrain/occlusion.d.ts +11 -0
- package/dist/view/terrain/occlusion.js +129 -0
- package/dist/view/terrain/polygon.d.ts +86 -0
- package/dist/view/terrain/polygon.js +301 -0
- package/dist/view/terrain/shade.d.ts +48 -0
- package/dist/view/terrain/shade.js +45 -0
- package/dist/view/terrain/state.d.ts +99 -0
- package/dist/view/terrain/state.js +186 -0
- package/dist/view/terrain/tessellation.d.ts +265 -0
- package/dist/view/terrain/tessellation.js +924 -0
- package/dist/view/terrain/tiling.d.ts +56 -0
- package/dist/view/terrain/tiling.js +155 -0
- package/dist/view/terrain/upstream-terrain.d.ts +82 -0
- package/dist/view/terrain/upstream-terrain.js +116 -0
- package/dist/view/ui/auxiliary-handles.d.ts +151 -0
- package/dist/view/ui/auxiliary-handles.js +22 -0
- package/dist/view/ui/bounds.d.ts +53 -0
- package/dist/view/ui/bounds.js +149 -0
- package/dist/view/ui/box-selection.d.ts +1 -0
- package/dist/view/ui/box-selection.js +83 -0
- package/dist/view/ui/handle-test.d.ts +1 -0
- package/dist/view/ui/handle-test.js +437 -0
- package/dist/view/ui/handle-thinning.d.ts +122 -0
- package/dist/view/ui/handle-thinning.js +430 -0
- package/dist/view/ui/handles.d.ts +25 -0
- package/dist/view/ui/handles.js +673 -0
- package/dist/view/ui/helper.d.ts +19 -0
- package/dist/view/ui/helper.js +76 -0
- package/dist/view/ui/index.d.ts +15 -0
- package/dist/view/ui/index.js +15 -0
- package/dist/view/ui/selection-scope.d.ts +25 -0
- package/dist/view/ui/selection-scope.js +34 -0
- package/dist/view/ui/selection-ui/bounding-box.d.ts +44 -0
- package/dist/view/ui/selection-ui/bounding-box.js +240 -0
- package/dist/view/ui/selection-ui/extension-registry.d.ts +76 -0
- package/dist/view/ui/selection-ui/extension-registry.js +78 -0
- package/dist/view/ui/selection-ui/index.d.ts +12 -0
- package/dist/view/ui/selection-ui/index.js +12 -0
- package/dist/view/ui/selection-ui/renderer.d.ts +29 -0
- package/dist/view/ui/selection-ui/renderer.js +227 -0
- package/dist/view/ui/selection-ui/types.d.ts +55 -0
- package/dist/view/ui/selection-ui/types.js +3 -0
- package/dist/view/ui/selection-ui-drawer.d.ts +52 -0
- package/dist/view/ui/selection-ui-drawer.js +329 -0
- package/dist/view/ui/tentative.d.ts +1 -0
- package/dist/view/ui/tentative.js +320 -0
- package/dist/view/viewport.d.ts +119 -0
- package/dist/view/viewport.js +254 -0
- package/package.json +113 -0
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
// SPDX-FileCopyrightText: 2026 SAKAIDA Atsushi
|
|
2
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
3
|
+
import { computeBoundingBox, computeCombinedBoundingBox, hasZeroArea, } from './selection-ui/index.js';
|
|
4
|
+
/**
|
|
5
|
+
* Returns the ids of the features the current selection covers, resolving a group or layer
|
|
6
|
+
* selection into its member features.
|
|
7
|
+
*
|
|
8
|
+
* The SSoT of the selection carries a kind (feature / group / layer). Selection display and
|
|
9
|
+
* manipulation on the map happen per feature, so a group / layer selection is resolved into
|
|
10
|
+
* the feature IDs of its members. This makes it "the SSoT holds a group/layer selection ->
|
|
11
|
+
* the map selects those members", so the display follows the SSoT (feature stays as is).
|
|
12
|
+
*
|
|
13
|
+
* @param store The Store to read the selection from
|
|
14
|
+
* @returns The feature ids. An empty array when nothing is selected
|
|
15
|
+
*/
|
|
16
|
+
export function getSelectedFeatureIds(store) {
|
|
17
|
+
const selection = store.getSelection();
|
|
18
|
+
switch (selection.type) {
|
|
19
|
+
case 'feature':
|
|
20
|
+
return selection.ids;
|
|
21
|
+
case 'group':
|
|
22
|
+
return selection.ids.flatMap((id) => store.getGroup(id)?.featureIds ?? []);
|
|
23
|
+
case 'layer':
|
|
24
|
+
return selection.ids.flatMap((id) => featureIdsInLayer(store, id));
|
|
25
|
+
default:
|
|
26
|
+
return [];
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
// All feature IDs under a layer (the features in order + the members of the groups).
|
|
30
|
+
function featureIdsInLayer(store, layerId) {
|
|
31
|
+
const layer = store.getLayer(layerId);
|
|
32
|
+
if (!layer)
|
|
33
|
+
return [];
|
|
34
|
+
const ids = [];
|
|
35
|
+
for (const itemId of layer.order) {
|
|
36
|
+
if (store.getFeature(itemId)) {
|
|
37
|
+
ids.push(itemId);
|
|
38
|
+
}
|
|
39
|
+
else {
|
|
40
|
+
const group = store.getGroup(itemId);
|
|
41
|
+
if (group)
|
|
42
|
+
ids.push(...group.featureIds);
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
return ids;
|
|
46
|
+
}
|
|
47
|
+
/**
|
|
48
|
+
* Obtain the selected features (a group / layer selection is resolved to its members)
|
|
49
|
+
*
|
|
50
|
+
* @internal
|
|
51
|
+
*/
|
|
52
|
+
export function getSelectedFeatures(store) {
|
|
53
|
+
return getSelectedFeatureIds(store)
|
|
54
|
+
.map((id) => store.getFeature(id))
|
|
55
|
+
.filter((f) => f !== undefined);
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* Compute the bounding box from the selected features
|
|
59
|
+
* When there are features other than Point, the bbox is computed from those alone
|
|
60
|
+
*
|
|
61
|
+
* @internal
|
|
62
|
+
*/
|
|
63
|
+
export function computeSelectionBoundingBox(selectedFeatures, extensions) {
|
|
64
|
+
if (selectedFeatures.length === 0) {
|
|
65
|
+
return null;
|
|
66
|
+
}
|
|
67
|
+
// Exclude features with zero area (a single coordinate)
|
|
68
|
+
const nonPointFeatures = selectedFeatures.filter((f) => {
|
|
69
|
+
const bbox = computeBoundingBox(f, extensions);
|
|
70
|
+
return bbox !== null && !hasZeroArea(bbox);
|
|
71
|
+
});
|
|
72
|
+
if (nonPointFeatures.length > 0) {
|
|
73
|
+
return computeCombinedBoundingBox(nonPointFeatures, extensions);
|
|
74
|
+
}
|
|
75
|
+
return computeCombinedBoundingBox(selectedFeatures, extensions);
|
|
76
|
+
}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* UI Rendering module
|
|
3
|
+
*
|
|
4
|
+
* Responsible for drawing the selection UI, bounding boxes, handles and tentative state.
|
|
5
|
+
*/
|
|
6
|
+
export { BoxSelectionRenderer } from './box-selection.js';
|
|
7
|
+
export type { HandleHitResult } from './handle-test.js';
|
|
8
|
+
export { getCursorForHandle, hitTestGlobalAuxiliaryHandles, hitTestHandles, } from './handle-test.js';
|
|
9
|
+
export type { HandleInfo } from './handles.js';
|
|
10
|
+
export { computeMidpointHandles, computeResizeHandles, computeRotateHandle, computeVertexHandles, SelectionHandlesRenderer, } from './handles.js';
|
|
11
|
+
export { computeSelectionBoundingBox, getSelectedFeatureIds, getSelectedFeatures, } from './helper.js';
|
|
12
|
+
export type { AdditionalHandleInfo, AdditionalResizeHandlesCalculator, BoundingBoxCoords, CustomBoundingBoxCalculator, CustomResizeCalculator, PointFrameExtent, PointFrameExtentProvider, ResizeStrategy, SelectionExtensionRegistry, } from './selection-ui/index.js';
|
|
13
|
+
export { computeBoundingBox, computeCombinedBoundingBox, createSelectionExtensionRegistry, DEFAULT_POINT_FRAME_SIZE, rotateBoundingBox, SelectionUIRenderer, } from './selection-ui/index.js';
|
|
14
|
+
export type { TentativeRendererDeps } from './tentative.js';
|
|
15
|
+
export { TentativeRenderer } from './tentative.js';
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
// SPDX-FileCopyrightText: 2026 SAKAIDA Atsushi
|
|
2
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
3
|
+
/**
|
|
4
|
+
* UI Rendering module
|
|
5
|
+
*
|
|
6
|
+
* Responsible for drawing the selection UI, bounding boxes, handles and tentative state.
|
|
7
|
+
*/
|
|
8
|
+
// Drawing the box selection
|
|
9
|
+
export { BoxSelectionRenderer } from './box-selection.js';
|
|
10
|
+
export { getCursorForHandle, hitTestGlobalAuxiliaryHandles, hitTestHandles, } from './handle-test.js';
|
|
11
|
+
export { computeMidpointHandles, computeResizeHandles, computeRotateHandle, computeVertexHandles, SelectionHandlesRenderer, } from './handles.js';
|
|
12
|
+
// Helpers for the selection information
|
|
13
|
+
export { computeSelectionBoundingBox, getSelectedFeatureIds, getSelectedFeatures, } from './helper.js';
|
|
14
|
+
export { computeBoundingBox, computeCombinedBoundingBox, createSelectionExtensionRegistry, DEFAULT_POINT_FRAME_SIZE, rotateBoundingBox, SelectionUIRenderer, } from './selection-ui/index.js';
|
|
15
|
+
export { TentativeRenderer } from './tentative.js';
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The selection scope of one draw instance
|
|
3
|
+
*
|
|
4
|
+
* What the selection UI (drawn by the CustomLayer) and the handle hit testing (run by the modes)
|
|
5
|
+
* must share: the extension points of the custom feature types, the registered auxiliary
|
|
6
|
+
* handles and the cache of the thinned handles. It is created once per draw instance and handed
|
|
7
|
+
* to both sides, so two instances on the same page never see each other's registrations or
|
|
8
|
+
* cached handle sets.
|
|
9
|
+
*/
|
|
10
|
+
import { type AuxiliaryHandleRegistry } from './auxiliary-handles.js';
|
|
11
|
+
import { type SelectionExtensionRegistry } from './selection-ui/extension-registry.js';
|
|
12
|
+
/**
|
|
13
|
+
* The registries the selection UI and the handle hit testing of one draw instance share:
|
|
14
|
+
* the selection extension points of custom feature types and the auxiliary handle providers.
|
|
15
|
+
*
|
|
16
|
+
* A mode reaches it as {@link ModeContext.selectionScope}.
|
|
17
|
+
*/
|
|
18
|
+
export interface SelectionScope {
|
|
19
|
+
/** Bounding box / resize / point frame extension points of the custom feature types */
|
|
20
|
+
readonly extensions: SelectionExtensionRegistry;
|
|
21
|
+
/** Providers of the auxiliary handles */
|
|
22
|
+
readonly auxiliaryHandles: AuxiliaryHandleRegistry;
|
|
23
|
+
/** Clears every registration and cached set (called when the draw instance is destroyed) */
|
|
24
|
+
clear(): void;
|
|
25
|
+
}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
// SPDX-FileCopyrightText: 2026 SAKAIDA Atsushi
|
|
2
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
3
|
+
/**
|
|
4
|
+
* The selection scope of one draw instance
|
|
5
|
+
*
|
|
6
|
+
* What the selection UI (drawn by the CustomLayer) and the handle hit testing (run by the modes)
|
|
7
|
+
* must share: the extension points of the custom feature types, the registered auxiliary
|
|
8
|
+
* handles and the cache of the thinned handles. It is created once per draw instance and handed
|
|
9
|
+
* to both sides, so two instances on the same page never see each other's registrations or
|
|
10
|
+
* cached handle sets.
|
|
11
|
+
*/
|
|
12
|
+
import { createAuxiliaryHandleRegistry, } from './auxiliary-handles.js';
|
|
13
|
+
import { HandleThinningCache } from './handle-thinning.js';
|
|
14
|
+
import { createSelectionExtensionRegistry, } from './selection-ui/extension-registry.js';
|
|
15
|
+
/**
|
|
16
|
+
* Creates the selection scope of one draw instance
|
|
17
|
+
*
|
|
18
|
+
* @internal
|
|
19
|
+
*/
|
|
20
|
+
export function createSelectionScope() {
|
|
21
|
+
const extensions = createSelectionExtensionRegistry();
|
|
22
|
+
const auxiliaryHandles = createAuxiliaryHandleRegistry();
|
|
23
|
+
const thinning = new HandleThinningCache();
|
|
24
|
+
return {
|
|
25
|
+
extensions,
|
|
26
|
+
auxiliaryHandles,
|
|
27
|
+
thinning,
|
|
28
|
+
clear() {
|
|
29
|
+
extensions.clear();
|
|
30
|
+
auxiliaryHandles.clear();
|
|
31
|
+
thinning.clear();
|
|
32
|
+
},
|
|
33
|
+
};
|
|
34
|
+
}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import type { Coordinate, Feature } from '../../../store/types.js';
|
|
2
|
+
import type { SelectionExtensionRegistry } from './extension-registry.js';
|
|
3
|
+
import type { BoundingBoxCoords } from './types.js';
|
|
4
|
+
/**
|
|
5
|
+
* Determines whether a selection box has no area, that is whether both ends of its diagonal
|
|
6
|
+
* are the same coordinate (a Point).
|
|
7
|
+
*
|
|
8
|
+
* @param bbox The corners of the box in degrees
|
|
9
|
+
* @returns `true` when the top-left and bottom-right corners are exactly equal
|
|
10
|
+
*/
|
|
11
|
+
export declare function hasZeroArea(bbox: BoundingBoxCoords): boolean;
|
|
12
|
+
/**
|
|
13
|
+
* Computes the selection box of a feature: its four corners and its center in degrees.
|
|
14
|
+
*
|
|
15
|
+
* A Point gives a box with no area at its position, a Circle the box of the circle, an
|
|
16
|
+
* Image an oriented box that takes the rotation into account, and the other built-in types
|
|
17
|
+
* the axis-aligned box of their coordinates.
|
|
18
|
+
* A custom feature uses the calculator registered in the draw instance's registry. Without a
|
|
19
|
+
* registry only the standard feature types are known (a custom type falls back to the
|
|
20
|
+
* extent of its coordinates).
|
|
21
|
+
*
|
|
22
|
+
* @param feature The feature
|
|
23
|
+
* @param extensions The selection extension points of the draw instance, for custom types
|
|
24
|
+
* @returns The box, or `null` when the feature has no coordinates to measure
|
|
25
|
+
*/
|
|
26
|
+
export declare function computeBoundingBox(feature: Feature, extensions?: SelectionExtensionRegistry): BoundingBoxCoords | null;
|
|
27
|
+
/**
|
|
28
|
+
* Compute the combined BoundingBox of several features
|
|
29
|
+
*
|
|
30
|
+
* A single feature returns its OBB as is. Several features return an AABB that contains
|
|
31
|
+
* all the vertices.
|
|
32
|
+
*/
|
|
33
|
+
export declare function computeCombinedBoundingBox(features: Feature[], extensions?: SelectionExtensionRegistry): BoundingBoxCoords | null;
|
|
34
|
+
/**
|
|
35
|
+
* Rotate a BoundingBox around its center
|
|
36
|
+
*
|
|
37
|
+
* Rotates in Web Mercator, the same plane and angle convention as the rotate operation
|
|
38
|
+
* (operations/rotate.ts), so the frame drawn during a rotation drag stays on the corners of
|
|
39
|
+
* the rotated feature at any latitude and size.
|
|
40
|
+
*
|
|
41
|
+
* @param angle Rotation (radians, counterclockwise in the transform plane)
|
|
42
|
+
* @param rotationCenter The center of the rotation. The frame's own center when omitted
|
|
43
|
+
*/
|
|
44
|
+
export declare function rotateBoundingBox(bbox: BoundingBoxCoords, angle: number, rotationCenter?: Coordinate): BoundingBoxCoords;
|
|
@@ -0,0 +1,240 @@
|
|
|
1
|
+
// SPDX-FileCopyrightText: 2026 SAKAIDA Atsushi
|
|
2
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
3
|
+
/**
|
|
4
|
+
* BoundingBox computation and rendering
|
|
5
|
+
*
|
|
6
|
+
* Provides the functions that compute BoundingBoxCoords from a feature, and the function
|
|
7
|
+
* that draws a BoundingBox with StrokeRenderer.
|
|
8
|
+
*
|
|
9
|
+
* Image (an OBB that takes the rotation into account) is computed by computeOrientedBoundingBox,
|
|
10
|
+
* and custom features use the calculator registered in the draw instance's
|
|
11
|
+
* SelectionExtensionRegistry.
|
|
12
|
+
*/
|
|
13
|
+
import { circleBoundingBox } from '../../../geometry/circle.js';
|
|
14
|
+
import { pixelsToDegreesLat, pixelsToDegreesLng } from '../../../shared/math/index.js';
|
|
15
|
+
import { fromPlane, toPlane } from '../../../shared/math/mercator-plane.js';
|
|
16
|
+
import { getCircleRadius, getCreatedZoom, getImageProperties, } from '../../../shared/utils/property.js';
|
|
17
|
+
import { getBoundingBox } from '../../../store/spatial/index.js';
|
|
18
|
+
/**
|
|
19
|
+
* Determines whether a selection box has no area, that is whether both ends of its diagonal
|
|
20
|
+
* are the same coordinate (a Point).
|
|
21
|
+
*
|
|
22
|
+
* @param bbox The corners of the box in degrees
|
|
23
|
+
* @returns `true` when the top-left and bottom-right corners are exactly equal
|
|
24
|
+
*/
|
|
25
|
+
export function hasZeroArea(bbox) {
|
|
26
|
+
return bbox.topLeft[0] === bbox.bottomRight[0] && bbox.topLeft[1] === bbox.bottomRight[1];
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Computes the selection box of a feature: its four corners and its center in degrees.
|
|
30
|
+
*
|
|
31
|
+
* A Point gives a box with no area at its position, a Circle the box of the circle, an
|
|
32
|
+
* Image an oriented box that takes the rotation into account, and the other built-in types
|
|
33
|
+
* the axis-aligned box of their coordinates.
|
|
34
|
+
* A custom feature uses the calculator registered in the draw instance's registry. Without a
|
|
35
|
+
* registry only the standard feature types are known (a custom type falls back to the
|
|
36
|
+
* extent of its coordinates).
|
|
37
|
+
*
|
|
38
|
+
* @param feature The feature
|
|
39
|
+
* @param extensions The selection extension points of the draw instance, for custom types
|
|
40
|
+
* @returns The box, or `null` when the feature has no coordinates to measure
|
|
41
|
+
*/
|
|
42
|
+
export function computeBoundingBox(feature, extensions) {
|
|
43
|
+
const customCalculator = extensions?.getBoundingBoxCalculator(feature.type);
|
|
44
|
+
if (customCalculator && extensions) {
|
|
45
|
+
return customCalculator(feature, extensions.getTileSize());
|
|
46
|
+
}
|
|
47
|
+
if (feature.type === 'Point') {
|
|
48
|
+
const coord = feature.coordinates;
|
|
49
|
+
return {
|
|
50
|
+
topLeft: coord,
|
|
51
|
+
topRight: coord,
|
|
52
|
+
bottomRight: coord,
|
|
53
|
+
bottomLeft: coord,
|
|
54
|
+
center: coord,
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
if (feature.type === 'Image') {
|
|
58
|
+
return computeOrientedBoundingBox(feature);
|
|
59
|
+
}
|
|
60
|
+
if (feature.type === 'Circle') {
|
|
61
|
+
return computeCircleBoundingBox(feature);
|
|
62
|
+
}
|
|
63
|
+
// LineString / Polygon / the Multi kinds compute an AABB
|
|
64
|
+
// (for the Multi kinds getBoundingBox flattens all the parts, so this is their union as is)
|
|
65
|
+
const bounds = getBoundingBox(feature);
|
|
66
|
+
if (bounds.minX === 0 && bounds.minY === 0 && bounds.maxX === 0 && bounds.maxY === 0) {
|
|
67
|
+
return null;
|
|
68
|
+
}
|
|
69
|
+
const centerLng = (bounds.minX + bounds.maxX) / 2;
|
|
70
|
+
const centerLat = (bounds.minY + bounds.maxY) / 2;
|
|
71
|
+
return {
|
|
72
|
+
topLeft: [bounds.minX, bounds.maxY],
|
|
73
|
+
topRight: [bounds.maxX, bounds.maxY],
|
|
74
|
+
bottomRight: [bounds.maxX, bounds.minY],
|
|
75
|
+
bottomLeft: [bounds.minX, bounds.minY],
|
|
76
|
+
center: [centerLng, centerLat],
|
|
77
|
+
};
|
|
78
|
+
}
|
|
79
|
+
/**
|
|
80
|
+
* The frame of a Circle: the extent of the geodesic circle as it is drawn, around its center
|
|
81
|
+
*/
|
|
82
|
+
function computeCircleBoundingBox(feature) {
|
|
83
|
+
const center = feature.coordinates;
|
|
84
|
+
const radiusMeters = getCircleRadius(feature);
|
|
85
|
+
const extent = radiusMeters && radiusMeters > 0 ? circleBoundingBox(center, radiusMeters) : null;
|
|
86
|
+
if (!extent) {
|
|
87
|
+
return {
|
|
88
|
+
topLeft: center,
|
|
89
|
+
topRight: center,
|
|
90
|
+
bottomRight: center,
|
|
91
|
+
bottomLeft: center,
|
|
92
|
+
center,
|
|
93
|
+
};
|
|
94
|
+
}
|
|
95
|
+
const [west, south, east, north] = extent;
|
|
96
|
+
return {
|
|
97
|
+
topLeft: [west, north],
|
|
98
|
+
topRight: [east, north],
|
|
99
|
+
bottomRight: [east, south],
|
|
100
|
+
bottomLeft: [west, south],
|
|
101
|
+
center,
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
/**
|
|
105
|
+
* Compute the OBB (Oriented Bounding Box) of an Image, taking the rotation into account
|
|
106
|
+
*
|
|
107
|
+
* Applies a planar rotation with a latitude correction instead of a spherical rotation
|
|
108
|
+
* (the same method as computeQuadVertices in quad-shader.ts).
|
|
109
|
+
*/
|
|
110
|
+
function computeOrientedBoundingBox(feature) {
|
|
111
|
+
const coord = feature.coordinates;
|
|
112
|
+
const [lng, lat] = coord;
|
|
113
|
+
const tileSize = 512;
|
|
114
|
+
const props = getImageProperties(feature);
|
|
115
|
+
const style = feature.style;
|
|
116
|
+
const imageWidth = style?.width || props.imageWidth || 100;
|
|
117
|
+
const imageHeight = style?.height || props.imageHeight || 100;
|
|
118
|
+
const scale = props.scale ?? 1;
|
|
119
|
+
// getImageProperties().createdZoom returns 0 when it is missing, so ?? does not work.
|
|
120
|
+
// getCreatedZoom(number|undefined) is used so that 14 is the default when it is missing.
|
|
121
|
+
const createdZoom = getCreatedZoom(feature) ?? 14;
|
|
122
|
+
// Only props.rotation is used (the same as ImageRenderer)
|
|
123
|
+
const rotation = props.rotation ?? 0;
|
|
124
|
+
const displayWidth = imageWidth * scale;
|
|
125
|
+
const displayHeight = imageHeight * scale;
|
|
126
|
+
const halfWidthDeg = pixelsToDegreesLng(displayWidth / 2, lat, createdZoom, tileSize);
|
|
127
|
+
const halfHeightDeg = pixelsToDegreesLat(displayHeight / 2, lat, createdZoom, tileSize);
|
|
128
|
+
const rotationRad = (rotation * Math.PI) / 180;
|
|
129
|
+
const cos = Math.cos(rotationRad);
|
|
130
|
+
const sin = Math.sin(rotationRad);
|
|
131
|
+
const latCos = Math.cos((lat * Math.PI) / 180);
|
|
132
|
+
// Normalize to the latitude degree scale
|
|
133
|
+
let hwNorm = halfWidthDeg * latCos;
|
|
134
|
+
let hhNorm = halfHeightDeg;
|
|
135
|
+
// Determine the scale factor from the latitude offset after the rotation
|
|
136
|
+
const MAX_LATITUDE = 89.9;
|
|
137
|
+
const baseCorners = [
|
|
138
|
+
{ x: -hwNorm, y: hhNorm },
|
|
139
|
+
{ x: hwNorm, y: hhNorm },
|
|
140
|
+
{ x: hwNorm, y: -hhNorm },
|
|
141
|
+
{ x: -hwNorm, y: -hhNorm },
|
|
142
|
+
];
|
|
143
|
+
let maxLatOffset = 0;
|
|
144
|
+
for (const c of baseCorners) {
|
|
145
|
+
const ry = c.x * sin + c.y * cos;
|
|
146
|
+
maxLatOffset = Math.max(maxLatOffset, Math.abs(ry));
|
|
147
|
+
}
|
|
148
|
+
const maxAllowedOffset = MAX_LATITUDE - Math.abs(lat);
|
|
149
|
+
if (maxLatOffset > maxAllowedOffset && maxLatOffset > 0) {
|
|
150
|
+
const scaleFactor = maxAllowedOffset / maxLatOffset;
|
|
151
|
+
hwNorm *= scaleFactor;
|
|
152
|
+
hhNorm *= scaleFactor;
|
|
153
|
+
}
|
|
154
|
+
const localCorners = [
|
|
155
|
+
{ x: -hwNorm, y: hhNorm }, // top-left
|
|
156
|
+
{ x: hwNorm, y: hhNorm }, // top-right
|
|
157
|
+
{ x: hwNorm, y: -hhNorm }, // bottom-right
|
|
158
|
+
{ x: -hwNorm, y: -hhNorm }, // bottom-left
|
|
159
|
+
];
|
|
160
|
+
const rotatedCorners = localCorners.map((c) => {
|
|
161
|
+
const rx = c.x * cos - c.y * sin;
|
|
162
|
+
const ry = c.x * sin + c.y * cos;
|
|
163
|
+
return [lng + rx / latCos, lat + ry];
|
|
164
|
+
});
|
|
165
|
+
return {
|
|
166
|
+
topLeft: rotatedCorners[0],
|
|
167
|
+
topRight: rotatedCorners[1],
|
|
168
|
+
bottomRight: rotatedCorners[2],
|
|
169
|
+
bottomLeft: rotatedCorners[3],
|
|
170
|
+
center: coord,
|
|
171
|
+
};
|
|
172
|
+
}
|
|
173
|
+
/**
|
|
174
|
+
* Compute the combined BoundingBox of several features
|
|
175
|
+
*
|
|
176
|
+
* A single feature returns its OBB as is. Several features return an AABB that contains
|
|
177
|
+
* all the vertices.
|
|
178
|
+
*/
|
|
179
|
+
export function computeCombinedBoundingBox(features, extensions) {
|
|
180
|
+
if (features.length === 0)
|
|
181
|
+
return null;
|
|
182
|
+
if (features.length === 1)
|
|
183
|
+
return computeBoundingBox(features[0], extensions);
|
|
184
|
+
let minLng = Number.POSITIVE_INFINITY;
|
|
185
|
+
let maxLng = Number.NEGATIVE_INFINITY;
|
|
186
|
+
let minLat = Number.POSITIVE_INFINITY;
|
|
187
|
+
let maxLat = Number.NEGATIVE_INFINITY;
|
|
188
|
+
for (const feature of features) {
|
|
189
|
+
const bbox = computeBoundingBox(feature, extensions);
|
|
190
|
+
if (!bbox)
|
|
191
|
+
continue;
|
|
192
|
+
const corners = [bbox.topLeft, bbox.topRight, bbox.bottomRight, bbox.bottomLeft];
|
|
193
|
+
for (const corner of corners) {
|
|
194
|
+
minLng = Math.min(minLng, corner[0]);
|
|
195
|
+
maxLng = Math.max(maxLng, corner[0]);
|
|
196
|
+
minLat = Math.min(minLat, corner[1]);
|
|
197
|
+
maxLat = Math.max(maxLat, corner[1]);
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
if (!Number.isFinite(minLng))
|
|
201
|
+
return null;
|
|
202
|
+
const centerLng = (minLng + maxLng) / 2;
|
|
203
|
+
const centerLat = (minLat + maxLat) / 2;
|
|
204
|
+
return {
|
|
205
|
+
topLeft: [minLng, maxLat],
|
|
206
|
+
topRight: [maxLng, maxLat],
|
|
207
|
+
bottomRight: [maxLng, minLat],
|
|
208
|
+
bottomLeft: [minLng, minLat],
|
|
209
|
+
center: [centerLng, centerLat],
|
|
210
|
+
};
|
|
211
|
+
}
|
|
212
|
+
/**
|
|
213
|
+
* Rotate a BoundingBox around its center
|
|
214
|
+
*
|
|
215
|
+
* Rotates in Web Mercator, the same plane and angle convention as the rotate operation
|
|
216
|
+
* (operations/rotate.ts), so the frame drawn during a rotation drag stays on the corners of
|
|
217
|
+
* the rotated feature at any latitude and size.
|
|
218
|
+
*
|
|
219
|
+
* @param angle Rotation (radians, counterclockwise in the transform plane)
|
|
220
|
+
* @param rotationCenter The center of the rotation. The frame's own center when omitted
|
|
221
|
+
*/
|
|
222
|
+
export function rotateBoundingBox(bbox, angle, rotationCenter) {
|
|
223
|
+
const center = rotationCenter ?? bbox.center;
|
|
224
|
+
const cos = Math.cos(angle);
|
|
225
|
+
const sin = Math.sin(angle);
|
|
226
|
+
const [cx, cy] = toPlane(center);
|
|
227
|
+
const rotatePoint = (coord) => {
|
|
228
|
+
const [x, y] = toPlane(coord);
|
|
229
|
+
const dx = x - cx;
|
|
230
|
+
const dy = y - cy;
|
|
231
|
+
return fromPlane(cx + dx * cos - dy * sin, cy + dx * sin + dy * cos);
|
|
232
|
+
};
|
|
233
|
+
return {
|
|
234
|
+
topLeft: rotatePoint(bbox.topLeft),
|
|
235
|
+
topRight: rotatePoint(bbox.topRight),
|
|
236
|
+
bottomRight: rotatePoint(bbox.bottomRight),
|
|
237
|
+
bottomLeft: rotatePoint(bbox.bottomLeft),
|
|
238
|
+
center: rotatePoint(bbox.center),
|
|
239
|
+
};
|
|
240
|
+
}
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The registry of the Selection UI extension points
|
|
3
|
+
*
|
|
4
|
+
* A mechanism for the custom feature types of extension implementations to provide their own
|
|
5
|
+
* boundingBox computation / resize handles / resize strategy / point frame extent.
|
|
6
|
+
*
|
|
7
|
+
* One registry belongs to one draw instance (it is created by createMapLibreGLDraw and handed
|
|
8
|
+
* to the CustomLayer, the modes and the extension API). Two draw instances on the same page
|
|
9
|
+
* never see each other's registrations, and destroying an instance clears its registry.
|
|
10
|
+
* The tile size of the instance's map is held here as well, because the custom bounding box
|
|
11
|
+
* calculators take it as an argument.
|
|
12
|
+
*/
|
|
13
|
+
import type { Feature } from '../../../store/types.js';
|
|
14
|
+
import type { AdditionalResizeHandlesCalculator, CustomBoundingBoxCalculator, CustomResizeCalculator, PointFrameExtent, PointFrameExtentProvider, ResizeStrategy } from './types.js';
|
|
15
|
+
/**
|
|
16
|
+
* The side of the square selection frame of a point, in CSS px: 12.
|
|
17
|
+
*
|
|
18
|
+
* The same value as DEFAULT_POINT_STYLE.size. Types with no registered extent become this
|
|
19
|
+
* square (the same look as the former fixed value).
|
|
20
|
+
*/
|
|
21
|
+
export declare const DEFAULT_POINT_FRAME_SIZE = 12;
|
|
22
|
+
/**
|
|
23
|
+
* The Selection UI extension points of one draw instance
|
|
24
|
+
*
|
|
25
|
+
* Every register method returns a function that cancels the registration. Cancelling after
|
|
26
|
+
* the same type has been registered again does not remove the later registration.
|
|
27
|
+
*/
|
|
28
|
+
export interface SelectionExtensionRegistry {
|
|
29
|
+
/** Registers how the selection box of a feature type is computed */
|
|
30
|
+
registerBoundingBox(type: string, calculator: CustomBoundingBoxCalculator): () => void;
|
|
31
|
+
/** Returns the bounding box calculator of a type, or `undefined` */
|
|
32
|
+
getBoundingBoxCalculator(type: string): CustomBoundingBoxCalculator | undefined;
|
|
33
|
+
/** Registers the resize handles a feature type adds to the four corner handles */
|
|
34
|
+
registerAdditionalResizeHandles(type: string, calculator: AdditionalResizeHandlesCalculator): () => void;
|
|
35
|
+
/** Returns the additional resize handles calculator of a type, or `undefined` */
|
|
36
|
+
getAdditionalResizeHandlesCalculator(type: string): AdditionalResizeHandlesCalculator | undefined;
|
|
37
|
+
/** Registers how a feature type is resized, replacing the built-in computation */
|
|
38
|
+
registerCustomResize(type: string, calculator: CustomResizeCalculator): () => void;
|
|
39
|
+
/** Returns the custom resize calculator of a type, or `undefined` */
|
|
40
|
+
getCustomResizeCalculator(type: string): CustomResizeCalculator | undefined;
|
|
41
|
+
/** Registers whether a feature type resizes by its coordinates or by its scale */
|
|
42
|
+
registerResizeStrategy(type: string, strategy: ResizeStrategy): () => void;
|
|
43
|
+
/** Returns the resize strategy of a type, or `undefined` */
|
|
44
|
+
getResizeStrategy(type: string): ResizeStrategy | undefined;
|
|
45
|
+
/** Registers the size of the selection frame of a point-like feature type */
|
|
46
|
+
registerPointFrameExtent(type: string, provider: PointFrameExtentProvider): () => void;
|
|
47
|
+
/** Returns the point frame extent provider of a type, or `undefined` */
|
|
48
|
+
getPointFrameExtentProvider(type: string): PointFrameExtentProvider | undefined;
|
|
49
|
+
/**
|
|
50
|
+
* Resolve the half width and half height of the selection box of a zero-area point
|
|
51
|
+
*
|
|
52
|
+
* Types with no registration, types that return null and values that are not finite
|
|
53
|
+
* degrade to the default square (the frame is not broken while the actual size on the
|
|
54
|
+
* extension side is not yet determined).
|
|
55
|
+
*/
|
|
56
|
+
resolvePointFrameExtent(feature: Feature): PointFrameExtent;
|
|
57
|
+
/** The tile size in px of the instance's map (passed to the custom bounding box calculators) */
|
|
58
|
+
getTileSize(): number;
|
|
59
|
+
/** Sets the tile size in px (the draw instance sets it from the map) */
|
|
60
|
+
setTileSize(tileSize: number): void;
|
|
61
|
+
/** Cancels every registration (called when the draw instance is destroyed) */
|
|
62
|
+
clear(): void;
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Creates an empty {@link SelectionExtensionRegistry} with a tile size of 512 px, for testing a
|
|
66
|
+
* custom feature handler in isolation.
|
|
67
|
+
*
|
|
68
|
+
* @returns A new registry with no registration
|
|
69
|
+
*/
|
|
70
|
+
export declare function createSelectionExtensionRegistry(): SelectionExtensionRegistry;
|
|
71
|
+
/**
|
|
72
|
+
* Resolve the extent of a point's selection box with an optional provider
|
|
73
|
+
*
|
|
74
|
+
* Without a registry (callers outside a draw instance) the default square is returned.
|
|
75
|
+
*/
|
|
76
|
+
export declare function resolvePointFrameExtentWith(provider: PointFrameExtentProvider | undefined, feature: Feature): PointFrameExtent;
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
// SPDX-FileCopyrightText: 2026 SAKAIDA Atsushi
|
|
2
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
3
|
+
/**
|
|
4
|
+
* The side of the square selection frame of a point, in CSS px: 12.
|
|
5
|
+
*
|
|
6
|
+
* The same value as DEFAULT_POINT_STYLE.size. Types with no registered extent become this
|
|
7
|
+
* square (the same look as the former fixed value).
|
|
8
|
+
*/
|
|
9
|
+
export const DEFAULT_POINT_FRAME_SIZE = 12;
|
|
10
|
+
/** The tile size used until the map reports its own (maplibre's default) */
|
|
11
|
+
const DEFAULT_REGISTRY_TILE_SIZE = 512;
|
|
12
|
+
/**
|
|
13
|
+
* A map whose registrations return a cancel function
|
|
14
|
+
*/
|
|
15
|
+
function registerIn(map, type, value) {
|
|
16
|
+
map.set(type, value);
|
|
17
|
+
return () => {
|
|
18
|
+
if (map.get(type) === value)
|
|
19
|
+
map.delete(type);
|
|
20
|
+
};
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Creates an empty {@link SelectionExtensionRegistry} with a tile size of 512 px, for testing a
|
|
24
|
+
* custom feature handler in isolation.
|
|
25
|
+
*
|
|
26
|
+
* @returns A new registry with no registration
|
|
27
|
+
*/
|
|
28
|
+
export function createSelectionExtensionRegistry() {
|
|
29
|
+
const boundingBoxes = new Map();
|
|
30
|
+
const additionalHandles = new Map();
|
|
31
|
+
const customResizes = new Map();
|
|
32
|
+
const resizeStrategies = new Map();
|
|
33
|
+
const pointFrameExtents = new Map();
|
|
34
|
+
let tileSize = DEFAULT_REGISTRY_TILE_SIZE;
|
|
35
|
+
return {
|
|
36
|
+
registerBoundingBox: (type, calculator) => registerIn(boundingBoxes, type, calculator),
|
|
37
|
+
getBoundingBoxCalculator: (type) => boundingBoxes.get(type),
|
|
38
|
+
registerAdditionalResizeHandles: (type, calculator) => registerIn(additionalHandles, type, calculator),
|
|
39
|
+
getAdditionalResizeHandlesCalculator: (type) => additionalHandles.get(type),
|
|
40
|
+
registerCustomResize: (type, calculator) => registerIn(customResizes, type, calculator),
|
|
41
|
+
getCustomResizeCalculator: (type) => customResizes.get(type),
|
|
42
|
+
registerResizeStrategy: (type, strategy) => registerIn(resizeStrategies, type, strategy),
|
|
43
|
+
getResizeStrategy: (type) => resizeStrategies.get(type),
|
|
44
|
+
registerPointFrameExtent: (type, provider) => registerIn(pointFrameExtents, type, provider),
|
|
45
|
+
getPointFrameExtentProvider: (type) => pointFrameExtents.get(type),
|
|
46
|
+
resolvePointFrameExtent(feature) {
|
|
47
|
+
return resolvePointFrameExtentWith(pointFrameExtents.get(feature.type), feature);
|
|
48
|
+
},
|
|
49
|
+
getTileSize: () => tileSize,
|
|
50
|
+
setTileSize(value) {
|
|
51
|
+
tileSize = value;
|
|
52
|
+
},
|
|
53
|
+
clear() {
|
|
54
|
+
boundingBoxes.clear();
|
|
55
|
+
additionalHandles.clear();
|
|
56
|
+
customResizes.clear();
|
|
57
|
+
resizeStrategies.clear();
|
|
58
|
+
pointFrameExtents.clear();
|
|
59
|
+
},
|
|
60
|
+
};
|
|
61
|
+
}
|
|
62
|
+
/**
|
|
63
|
+
* Resolve the extent of a point's selection box with an optional provider
|
|
64
|
+
*
|
|
65
|
+
* Without a registry (callers outside a draw instance) the default square is returned.
|
|
66
|
+
*/
|
|
67
|
+
export function resolvePointFrameExtentWith(provider, feature) {
|
|
68
|
+
const extent = provider?.(feature);
|
|
69
|
+
if (!extent ||
|
|
70
|
+
!Number.isFinite(extent.halfWidth) ||
|
|
71
|
+
!Number.isFinite(extent.halfHeight) ||
|
|
72
|
+
extent.halfWidth < 0 ||
|
|
73
|
+
extent.halfHeight < 0) {
|
|
74
|
+
const half = DEFAULT_POINT_FRAME_SIZE / 2;
|
|
75
|
+
return { halfWidth: half, halfHeight: half };
|
|
76
|
+
}
|
|
77
|
+
return extent;
|
|
78
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Selection UI module
|
|
3
|
+
*
|
|
4
|
+
* Visual feedback for the selection state (BoundingBox / custom calculators / Renderer).
|
|
5
|
+
* The files are split per feature, and this index is a barrel that re-exports their public
|
|
6
|
+
* symbols.
|
|
7
|
+
*/
|
|
8
|
+
export { computeBoundingBox, computeCombinedBoundingBox, hasZeroArea, rotateBoundingBox, } from './bounding-box.js';
|
|
9
|
+
export type { SelectionExtensionRegistry } from './extension-registry.js';
|
|
10
|
+
export { createSelectionExtensionRegistry, DEFAULT_POINT_FRAME_SIZE, resolvePointFrameExtentWith, } from './extension-registry.js';
|
|
11
|
+
export { SelectionUIRenderer } from './renderer.js';
|
|
12
|
+
export type { AdditionalHandleInfo, AdditionalResizeHandlesCalculator, BoundingBoxCoords, CustomBoundingBoxCalculator, CustomResizeCalculator, PointFrameExtent, PointFrameExtentProvider, ResizeStrategy, } from './types.js';
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
// SPDX-FileCopyrightText: 2026 SAKAIDA Atsushi
|
|
2
|
+
// SPDX-License-Identifier: AGPL-3.0-only
|
|
3
|
+
/**
|
|
4
|
+
* Selection UI module
|
|
5
|
+
*
|
|
6
|
+
* Visual feedback for the selection state (BoundingBox / custom calculators / Renderer).
|
|
7
|
+
* The files are split per feature, and this index is a barrel that re-exports their public
|
|
8
|
+
* symbols.
|
|
9
|
+
*/
|
|
10
|
+
export { computeBoundingBox, computeCombinedBoundingBox, hasZeroArea, rotateBoundingBox, } from './bounding-box.js';
|
|
11
|
+
export { createSelectionExtensionRegistry, DEFAULT_POINT_FRAME_SIZE, resolvePointFrameExtentWith, } from './extension-registry.js';
|
|
12
|
+
export { SelectionUIRenderer } from './renderer.js';
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* SelectionUIRenderer
|
|
3
|
+
*
|
|
4
|
+
* Draws the visual feedback of the selection state (the BoundingBox + the OBB while rotating).
|
|
5
|
+
* The BoundingBox computation logic itself is separated into ./bounding-box.ts, and this
|
|
6
|
+
* file concentrates on orchestrating the rendering and the application of the margin.
|
|
7
|
+
*/
|
|
8
|
+
import type { ProjectionData } from 'maplibre-gl';
|
|
9
|
+
import type { SelectionUIConfig } from '../../../shared/config/selection.js';
|
|
10
|
+
import { type CoordinateTransform } from '../../../shared/math/index.js';
|
|
11
|
+
import type { DragState, Feature } from '../../../store/types.js';
|
|
12
|
+
import type { StrokeRenderer } from '../../renderers/stroke.js';
|
|
13
|
+
import type { SelectionExtensionRegistry } from './extension-registry.js';
|
|
14
|
+
import type { BoundingBoxCoords } from './types.js';
|
|
15
|
+
export declare class SelectionUIRenderer {
|
|
16
|
+
#private;
|
|
17
|
+
constructor(strokeRenderer: StrokeRenderer, config: SelectionUIConfig, extensions: SelectionExtensionRegistry);
|
|
18
|
+
/** Compute the BoundingBox of a feature (also usable from outside) */
|
|
19
|
+
computeFeatureBoundingBox(feature: Feature): BoundingBoxCoords | null;
|
|
20
|
+
/** Compute the combined BoundingBox of several features (also usable from outside) */
|
|
21
|
+
computeCombinedFeatureBoundingBox(features: Feature[]): BoundingBoxCoords | null;
|
|
22
|
+
setTransform(transform: CoordinateTransform): void;
|
|
23
|
+
setProjectionData(projectionData: ProjectionData): void;
|
|
24
|
+
updateConfig(config: SelectionUIConfig): void;
|
|
25
|
+
/**
|
|
26
|
+
* Draw the UI of the selected features
|
|
27
|
+
*/
|
|
28
|
+
draw(features: Feature[], zoom: number, dragState?: DragState | null): void;
|
|
29
|
+
}
|