@mailwoman/react 10.0.0 → 10.1.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/README.md +17 -16
- package/fonts.css +97 -22
- package/lib/common/About.tsx +7 -7
- package/lib/common/ClientOnly.tsx +2 -14
- package/lib/common/CopyButton.tsx +3 -1
- package/lib/common/LoadingIndicator.tsx +4 -2
- package/lib/common/PresetChips.tsx +9 -8
- package/lib/common/confidence-tiers.ts +7 -6
- package/lib/common/cx.ts +3 -1
- package/lib/common/text-tokens.ts +7 -4
- package/lib/common/useBuildInfo.ts +54 -0
- package/lib/common/useClipboard.ts +2 -11
- package/lib/common.ts +22 -0
- package/lib/index.ts +27 -17
- package/lib/map/AppIdentity.tsx +85 -0
- package/lib/map/BackendControl.tsx +9 -10
- package/lib/map/CompareToggle.tsx +8 -31
- package/lib/map/DebugInfo.tsx +88 -0
- package/lib/map/Geocoder.tsx +60 -46
- package/lib/map/GeocoderControls.tsx +430 -134
- package/lib/map/GraticuleLayer.tsx +54 -0
- package/lib/map/MapCanvas.tsx +23 -12
- package/lib/map/MapChipRow.tsx +4 -8
- package/lib/map/MapCompass.tsx +15 -24
- package/lib/map/MapControlStack.tsx +8 -9
- package/lib/map/MapFooter.tsx +2 -16
- package/lib/map/MapProgressBar.tsx +10 -13
- package/lib/map/MapSearchBar.tsx +31 -17
- package/lib/map/MapSheet.tsx +24 -15
- package/lib/map/OverlayLayers.tsx +1 -1
- package/lib/map/PlaceAutocomplete.tsx +10 -21
- package/lib/map/PlaceMarker.tsx +4 -2
- package/lib/map/ResolvedPlaceLayers.tsx +5 -14
- package/lib/map/ResultCamera.tsx +8 -31
- package/lib/map/ResultOverlay.tsx +2 -12
- package/lib/map/ResultPanel.tsx +1 -20
- package/lib/map/VersionPicker.tsx +10 -19
- package/lib/map/fake-runtime.ts +10 -12
- package/lib/map/geometry.ts +14 -47
- package/lib/map/graticule.ts +80 -0
- package/lib/map/map-debug.ts +1 -1
- package/lib/map/place-render.ts +28 -60
- package/lib/map/types.ts +58 -104
- package/lib/map/useCompareState.ts +5 -4
- package/lib/map/useGeocode.ts +7 -5
- package/lib/map/useMapBearing.ts +13 -13
- package/lib/map/useMapLabelPick.ts +21 -30
- package/lib/map/useMapPlaceRender.ts +2 -6
- package/lib/map/usePlaceAutocomplete.ts +44 -50
- package/lib/map.ts +95 -0
- package/lib/pipeline/CandidatePicker.tsx +13 -5
- package/lib/pipeline/ConfidenceCell.tsx +1 -1
- package/lib/pipeline/FailureDiagnostic.tsx +8 -2
- package/lib/pipeline/QueryForm.tsx +5 -2
- package/lib/pipeline/ResolvedPlace.tsx +1 -1
- package/lib/pipeline/SpanHighlight.tsx +7 -5
- package/lib/pipeline/TimingPanel.tsx +1 -1
- package/lib/pipeline/TreeView.tsx +1 -1
- package/lib/pipeline/copy.ts +22 -25
- package/lib/pipeline/presets.ts +15 -13
- package/lib/pipeline/types.ts +21 -14
- package/lib/pipeline/useParsePipeline.ts +16 -13
- package/lib/pipeline.ts +36 -0
- package/lib/poi/AbstainPanel.tsx +1 -1
- package/lib/poi/LiveResultsBlock.tsx +2 -1
- package/lib/poi/POIExplorer.tsx +24 -15
- package/lib/poi/QueryInput.tsx +1 -1
- package/lib/poi/SubjectPanel.tsx +4 -3
- package/lib/poi/runtime.ts +5 -16
- package/lib/poi/types.ts +39 -27
- package/lib/poi/usePOISearch.ts +39 -44
- package/lib/poi.ts +39 -0
- package/lib/runtime/useReleaseRuntime.ts +125 -74
- package/lib/search/SearchModal.tsx +317 -0
- package/lib/search/search.css +144 -0
- package/lib/search/types.ts +67 -0
- package/lib/search.ts +11 -0
- package/out/common/About.d.ts +5 -5
- package/out/common/About.d.ts.map +1 -1
- package/out/common/About.js +1 -1
- package/out/common/About.js.map +1 -1
- package/out/common/ClientOnly.d.ts +2 -11
- package/out/common/ClientOnly.d.ts.map +1 -1
- package/out/common/ClientOnly.js +1 -13
- package/out/common/ClientOnly.js.map +1 -1
- package/out/common/CopyButton.d.ts +3 -1
- package/out/common/CopyButton.d.ts.map +1 -1
- package/out/common/CopyButton.js.map +1 -1
- package/out/common/LoadingIndicator.d.ts +4 -2
- package/out/common/LoadingIndicator.d.ts.map +1 -1
- package/out/common/LoadingIndicator.js.map +1 -1
- package/out/common/PresetChips.d.ts +9 -8
- package/out/common/PresetChips.d.ts.map +1 -1
- package/out/common/PresetChips.js.map +1 -1
- package/out/common/confidence-tiers.d.ts +7 -6
- package/out/common/confidence-tiers.d.ts.map +1 -1
- package/out/common/confidence-tiers.js +7 -6
- package/out/common/confidence-tiers.js.map +1 -1
- package/out/common/cx.d.ts +3 -1
- package/out/common/cx.d.ts.map +1 -1
- package/out/common/cx.js +3 -1
- package/out/common/cx.js.map +1 -1
- package/out/common/text-tokens.d.ts +4 -3
- package/out/common/text-tokens.d.ts.map +1 -1
- package/out/common/text-tokens.js +6 -3
- package/out/common/text-tokens.js.map +1 -1
- package/out/common/useBuildInfo.d.ts +27 -0
- package/out/common/useBuildInfo.d.ts.map +1 -0
- package/out/common/useBuildInfo.js +32 -0
- package/out/common/useBuildInfo.js.map +1 -0
- package/out/common/useClipboard.d.ts +1 -3
- package/out/common/useClipboard.d.ts.map +1 -1
- package/out/common/useClipboard.js +2 -11
- package/out/common/useClipboard.js.map +1 -1
- package/out/common.d.ts +22 -0
- package/out/common.d.ts.map +1 -0
- package/out/common.js +15 -0
- package/out/common.js.map +1 -0
- package/out/index.d.ts +26 -16
- package/out/index.d.ts.map +1 -1
- package/out/index.js +21 -15
- package/out/index.js.map +1 -1
- package/out/map/AppIdentity.d.ts +42 -0
- package/out/map/AppIdentity.d.ts.map +1 -0
- package/out/map/AppIdentity.js +16 -0
- package/out/map/AppIdentity.js.map +1 -0
- package/out/map/BackendControl.d.ts +9 -10
- package/out/map/BackendControl.d.ts.map +1 -1
- package/out/map/BackendControl.js +1 -1
- package/out/map/BackendControl.js.map +1 -1
- package/out/map/CompareToggle.d.ts +8 -31
- package/out/map/CompareToggle.d.ts.map +1 -1
- package/out/map/CompareToggle.js +4 -1
- package/out/map/CompareToggle.js.map +1 -1
- package/out/map/DebugInfo.d.ts +34 -0
- package/out/map/DebugInfo.d.ts.map +1 -0
- package/out/map/DebugInfo.js +39 -0
- package/out/map/DebugInfo.js.map +1 -0
- package/out/map/Geocoder.d.ts +41 -30
- package/out/map/Geocoder.d.ts.map +1 -1
- package/out/map/Geocoder.js +20 -36
- package/out/map/Geocoder.js.map +1 -1
- package/out/map/GeocoderControls.d.ts +14 -42
- package/out/map/GeocoderControls.d.ts.map +1 -1
- package/out/map/GeocoderControls.js +250 -38
- package/out/map/GeocoderControls.js.map +1 -1
- package/out/map/GraticuleLayer.d.ts +28 -0
- package/out/map/GraticuleLayer.d.ts.map +1 -0
- package/out/map/GraticuleLayer.js +25 -0
- package/out/map/GraticuleLayer.js.map +1 -0
- package/out/map/MapCanvas.d.ts +23 -12
- package/out/map/MapCanvas.d.ts.map +1 -1
- package/out/map/MapCanvas.js +5 -2
- package/out/map/MapCanvas.js.map +1 -1
- package/out/map/MapChipRow.d.ts +4 -8
- package/out/map/MapChipRow.d.ts.map +1 -1
- package/out/map/MapChipRow.js.map +1 -1
- package/out/map/MapCompass.d.ts +11 -20
- package/out/map/MapCompass.d.ts.map +1 -1
- package/out/map/MapCompass.js +5 -1
- package/out/map/MapCompass.js.map +1 -1
- package/out/map/MapControlStack.d.ts +8 -9
- package/out/map/MapControlStack.d.ts.map +1 -1
- package/out/map/MapControlStack.js +4 -1
- package/out/map/MapControlStack.js.map +1 -1
- package/out/map/MapFooter.d.ts +2 -15
- package/out/map/MapFooter.d.ts.map +1 -1
- package/out/map/MapFooter.js +0 -14
- package/out/map/MapFooter.js.map +1 -1
- package/out/map/MapProgressBar.d.ts +10 -13
- package/out/map/MapProgressBar.d.ts.map +1 -1
- package/out/map/MapProgressBar.js.map +1 -1
- package/out/map/MapSearchBar.d.ts +16 -17
- package/out/map/MapSearchBar.d.ts.map +1 -1
- package/out/map/MapSearchBar.js +6 -0
- package/out/map/MapSearchBar.js.map +1 -1
- package/out/map/MapSheet.d.ts +15 -12
- package/out/map/MapSheet.d.ts.map +1 -1
- package/out/map/MapSheet.js +8 -12
- package/out/map/MapSheet.js.map +1 -1
- package/out/map/OverlayLayers.d.ts +1 -1
- package/out/map/OverlayLayers.js +1 -1
- package/out/map/PlaceAutocomplete.d.ts +10 -21
- package/out/map/PlaceAutocomplete.d.ts.map +1 -1
- package/out/map/PlaceAutocomplete.js +2 -1
- package/out/map/PlaceAutocomplete.js.map +1 -1
- package/out/map/PlaceMarker.d.ts +4 -2
- package/out/map/PlaceMarker.d.ts.map +1 -1
- package/out/map/PlaceMarker.js +3 -1
- package/out/map/PlaceMarker.js.map +1 -1
- package/out/map/ResolvedPlaceLayers.d.ts +5 -14
- package/out/map/ResolvedPlaceLayers.d.ts.map +1 -1
- package/out/map/ResolvedPlaceLayers.js +1 -1
- package/out/map/ResolvedPlaceLayers.js.map +1 -1
- package/out/map/ResultCamera.d.ts +8 -31
- package/out/map/ResultCamera.d.ts.map +1 -1
- package/out/map/ResultCamera.js +3 -28
- package/out/map/ResultCamera.js.map +1 -1
- package/out/map/ResultOverlay.d.ts +2 -12
- package/out/map/ResultOverlay.d.ts.map +1 -1
- package/out/map/ResultOverlay.js +1 -2
- package/out/map/ResultOverlay.js.map +1 -1
- package/out/map/ResultPanel.d.ts +1 -20
- package/out/map/ResultPanel.d.ts.map +1 -1
- package/out/map/ResultPanel.js.map +1 -1
- package/out/map/VersionPicker.d.ts +7 -19
- package/out/map/VersionPicker.d.ts.map +1 -1
- package/out/map/VersionPicker.js +5 -2
- package/out/map/VersionPicker.js.map +1 -1
- package/out/map/fake-runtime.d.ts +9 -11
- package/out/map/fake-runtime.d.ts.map +1 -1
- package/out/map/fake-runtime.js +9 -12
- package/out/map/fake-runtime.js.map +1 -1
- package/out/map/geometry.d.ts +13 -34
- package/out/map/geometry.d.ts.map +1 -1
- package/out/map/geometry.js +9 -34
- package/out/map/geometry.js.map +1 -1
- package/out/map/graticule.d.ts +17 -0
- package/out/map/graticule.d.ts.map +1 -0
- package/out/map/graticule.js +67 -0
- package/out/map/graticule.js.map +1 -0
- package/out/map/map-debug.d.ts +1 -1
- package/out/map/map-debug.js +1 -1
- package/out/map/place-render.d.ts +23 -43
- package/out/map/place-render.d.ts.map +1 -1
- package/out/map/place-render.js +4 -39
- package/out/map/place-render.js.map +1 -1
- package/out/map/types.d.ts +58 -102
- package/out/map/types.d.ts.map +1 -1
- package/out/map/types.js +1 -10
- package/out/map/types.js.map +1 -1
- package/out/map/useCompareState.d.ts +5 -4
- package/out/map/useCompareState.d.ts.map +1 -1
- package/out/map/useCompareState.js +3 -3
- package/out/map/useCompareState.js.map +1 -1
- package/out/map/useGeocode.d.ts +5 -3
- package/out/map/useGeocode.d.ts.map +1 -1
- package/out/map/useGeocode.js +4 -4
- package/out/map/useGeocode.js.map +1 -1
- package/out/map/useMapBearing.d.ts +11 -11
- package/out/map/useMapBearing.d.ts.map +1 -1
- package/out/map/useMapBearing.js +6 -11
- package/out/map/useMapBearing.js.map +1 -1
- package/out/map/useMapLabelPick.d.ts +4 -14
- package/out/map/useMapLabelPick.d.ts.map +1 -1
- package/out/map/useMapLabelPick.js +21 -30
- package/out/map/useMapLabelPick.js.map +1 -1
- package/out/map/useMapPlaceRender.d.ts +2 -6
- package/out/map/useMapPlaceRender.d.ts.map +1 -1
- package/out/map/useMapPlaceRender.js +2 -6
- package/out/map/useMapPlaceRender.js.map +1 -1
- package/out/map/usePlaceAutocomplete.d.ts +30 -28
- package/out/map/usePlaceAutocomplete.d.ts.map +1 -1
- package/out/map/usePlaceAutocomplete.js +6 -33
- package/out/map/usePlaceAutocomplete.js.map +1 -1
- package/out/map.d.ts +69 -0
- package/out/map.d.ts.map +1 -0
- package/out/map.js +46 -0
- package/out/map.js.map +1 -0
- package/out/pipeline/CandidatePicker.d.ts +12 -2
- package/out/pipeline/CandidatePicker.d.ts.map +1 -1
- package/out/pipeline/CandidatePicker.js +1 -1
- package/out/pipeline/CandidatePicker.js.map +1 -1
- package/out/pipeline/ConfidenceCell.d.ts +1 -1
- package/out/pipeline/ConfidenceCell.js +1 -1
- package/out/pipeline/FailureDiagnostic.d.ts +8 -2
- package/out/pipeline/FailureDiagnostic.d.ts.map +1 -1
- package/out/pipeline/FailureDiagnostic.js +3 -0
- package/out/pipeline/FailureDiagnostic.js.map +1 -1
- package/out/pipeline/QueryForm.d.ts +5 -2
- package/out/pipeline/QueryForm.d.ts.map +1 -1
- package/out/pipeline/QueryForm.js.map +1 -1
- package/out/pipeline/SpanHighlight.d.ts +4 -3
- package/out/pipeline/SpanHighlight.d.ts.map +1 -1
- package/out/pipeline/SpanHighlight.js +3 -2
- package/out/pipeline/SpanHighlight.js.map +1 -1
- package/out/pipeline/TimingPanel.d.ts +1 -1
- package/out/pipeline/TreeView.d.ts +1 -1
- package/out/pipeline/copy.d.ts +1 -1
- package/out/pipeline/copy.d.ts.map +1 -1
- package/out/pipeline/copy.js +4 -3
- package/out/pipeline/copy.js.map +1 -1
- package/out/pipeline/presets.d.ts +5 -4
- package/out/pipeline/presets.d.ts.map +1 -1
- package/out/pipeline/presets.js +15 -13
- package/out/pipeline/presets.js.map +1 -1
- package/out/pipeline/types.d.ts +21 -14
- package/out/pipeline/types.d.ts.map +1 -1
- package/out/pipeline/types.js +2 -4
- package/out/pipeline/types.js.map +1 -1
- package/out/pipeline/useParsePipeline.d.ts +14 -9
- package/out/pipeline/useParsePipeline.d.ts.map +1 -1
- package/out/pipeline/useParsePipeline.js +7 -8
- package/out/pipeline/useParsePipeline.js.map +1 -1
- package/out/pipeline.d.ts +33 -0
- package/out/pipeline.d.ts.map +1 -0
- package/out/pipeline.js +21 -0
- package/out/pipeline.js.map +1 -0
- package/out/poi/AbstainPanel.d.ts +1 -1
- package/out/poi/LiveResultsBlock.d.ts +2 -1
- package/out/poi/LiveResultsBlock.d.ts.map +1 -1
- package/out/poi/LiveResultsBlock.js.map +1 -1
- package/out/poi/POIExplorer.d.ts +22 -12
- package/out/poi/POIExplorer.d.ts.map +1 -1
- package/out/poi/POIExplorer.js +9 -8
- package/out/poi/POIExplorer.js.map +1 -1
- package/out/poi/QueryInput.d.ts +1 -1
- package/out/poi/SubjectPanel.d.ts +2 -2
- package/out/poi/SubjectPanel.d.ts.map +1 -1
- package/out/poi/SubjectPanel.js +2 -1
- package/out/poi/SubjectPanel.js.map +1 -1
- package/out/poi/runtime.d.ts +5 -14
- package/out/poi/runtime.d.ts.map +1 -1
- package/out/poi/runtime.js +5 -16
- package/out/poi/runtime.js.map +1 -1
- package/out/poi/types.d.ts +39 -27
- package/out/poi/types.d.ts.map +1 -1
- package/out/poi/types.js +2 -4
- package/out/poi/types.js.map +1 -1
- package/out/poi/usePOISearch.d.ts +28 -17
- package/out/poi/usePOISearch.d.ts.map +1 -1
- package/out/poi/usePOISearch.js +6 -32
- package/out/poi/usePOISearch.js.map +1 -1
- package/out/poi.d.ts +23 -0
- package/out/poi.d.ts.map +1 -0
- package/out/poi.js +15 -0
- package/out/poi.js.map +1 -0
- package/out/runtime/useReleaseRuntime.d.ts +64 -65
- package/out/runtime/useReleaseRuntime.d.ts.map +1 -1
- package/out/runtime/useReleaseRuntime.js +31 -26
- package/out/runtime/useReleaseRuntime.js.map +1 -1
- package/out/{runtime/index.d.ts → runtime.d.ts} +1 -1
- package/out/runtime.d.ts.map +1 -0
- package/out/{runtime/index.js → runtime.js} +1 -1
- package/out/runtime.js.map +1 -0
- package/out/search/SearchModal.d.ts +33 -0
- package/out/search/SearchModal.d.ts.map +1 -0
- package/out/search/SearchModal.js +187 -0
- package/out/search/SearchModal.js.map +1 -0
- package/out/search/types.d.ts +64 -0
- package/out/search/types.d.ts.map +1 -0
- package/out/search/types.js +13 -0
- package/out/search/types.js.map +1 -0
- package/out/search.d.ts +11 -0
- package/out/search.d.ts.map +1 -0
- package/out/search.js +9 -0
- package/out/search.js.map +1 -0
- package/package.json +60 -142
- package/styles.css +482 -266
- package/tokens/index.css +24 -6
- package/tokens/tokens.json +114 -6
- package/lib/common/index.ts +0 -22
- package/lib/map/index.ts +0 -95
- package/lib/pipeline/index.ts +0 -36
- package/lib/poi/index.ts +0 -39
- package/out/common/index.d.ts +0 -22
- package/out/common/index.d.ts.map +0 -1
- package/out/common/index.js +0 -15
- package/out/common/index.js.map +0 -1
- package/out/map/index.d.ts +0 -69
- package/out/map/index.d.ts.map +0 -1
- package/out/map/index.js +0 -46
- package/out/map/index.js.map +0 -1
- package/out/pipeline/index.d.ts +0 -33
- package/out/pipeline/index.d.ts.map +0 -1
- package/out/pipeline/index.js +0 -21
- package/out/pipeline/index.js.map +0 -1
- package/out/poi/index.d.ts +0 -23
- package/out/poi/index.d.ts.map +0 -1
- package/out/poi/index.js +0 -15
- package/out/poi/index.js.map +0 -1
- package/out/runtime/index.d.ts.map +0 -1
- package/out/runtime/index.js.map +0 -1
- package/styleframe.config.ts +0 -329
- package/vitest.node.config.ts +0 -20
- /package/lib/{runtime/index.ts → runtime.ts} +0 -0
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @copyright Sister Software
|
|
3
|
+
* @license AGPL-3.0
|
|
4
|
+
* @author Teffen Ellis, et al.
|
|
5
|
+
*
|
|
6
|
+
* Renders the footer identity with the app name, an optional documentation link and the build
|
|
7
|
+
* commit. This component does not depend on the map.
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
import type { ReactNode } from "react"
|
|
11
|
+
|
|
12
|
+
import { useBuildInfo } from "#common/useBuildInfo"
|
|
13
|
+
|
|
14
|
+
/**
|
|
15
|
+
* The number of commit characters shown in the footer.
|
|
16
|
+
*/
|
|
17
|
+
const DISPLAYED_LENGTH = 6
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Props for {@link AppIdentity}.
|
|
21
|
+
*/
|
|
22
|
+
export interface AppIdentityProps {
|
|
23
|
+
/**
|
|
24
|
+
* The app's display name, such as `Mailwoman Earth`.
|
|
25
|
+
*/
|
|
26
|
+
name: ReactNode
|
|
27
|
+
/**
|
|
28
|
+
* The documentation link's target.
|
|
29
|
+
* The link is omitted when this is unset.
|
|
30
|
+
*/
|
|
31
|
+
docsURL?: string
|
|
32
|
+
/**
|
|
33
|
+
* The documentation link's text. @default "Developer Documentation"
|
|
34
|
+
*/
|
|
35
|
+
docsLabel?: string
|
|
36
|
+
/**
|
|
37
|
+
* The URL of the build record. @default "/build.json"
|
|
38
|
+
*/
|
|
39
|
+
buildInfoURL?: string
|
|
40
|
+
/**
|
|
41
|
+
* Builds the commit link.
|
|
42
|
+
* Without it, the commit is shown as plain text.
|
|
43
|
+
*/
|
|
44
|
+
commitHref?: (commit: string) => string
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
/**
|
|
48
|
+
* Renders the app name, documentation link and short build commit.
|
|
49
|
+
* The commit is omitted when no build record loads.
|
|
50
|
+
*/
|
|
51
|
+
export function AppIdentity({
|
|
52
|
+
name,
|
|
53
|
+
docsURL,
|
|
54
|
+
docsLabel = "Developer Documentation",
|
|
55
|
+
buildInfoURL,
|
|
56
|
+
commitHref,
|
|
57
|
+
}: AppIdentityProps): ReactNode {
|
|
58
|
+
const build = useBuildInfo(buildInfoURL)
|
|
59
|
+
const commit = build?.commit
|
|
60
|
+
|
|
61
|
+
return (
|
|
62
|
+
<>
|
|
63
|
+
<strong>{name}</strong>
|
|
64
|
+
{docsURL ? (
|
|
65
|
+
<>
|
|
66
|
+
{" "}
|
|
67
|
+
<a href={docsURL}>{docsLabel}</a>
|
|
68
|
+
</>
|
|
69
|
+
) : null}
|
|
70
|
+
{commit ? (
|
|
71
|
+
<>
|
|
72
|
+
{" ("}
|
|
73
|
+
{commitHref ? (
|
|
74
|
+
<a href={commitHref(commit)} title={`Built from ${commit}`}>
|
|
75
|
+
<code>{commit.slice(0, DISPLAYED_LENGTH)}</code>
|
|
76
|
+
</a>
|
|
77
|
+
) : (
|
|
78
|
+
<code title={`Built from ${commit}`}>{commit.slice(0, DISPLAYED_LENGTH)}</code>
|
|
79
|
+
)}
|
|
80
|
+
{")"}
|
|
81
|
+
</>
|
|
82
|
+
) : null}
|
|
83
|
+
</>
|
|
84
|
+
)
|
|
85
|
+
}
|
|
@@ -3,33 +3,32 @@
|
|
|
3
3
|
* @license AGPL-3.0
|
|
4
4
|
* @author Teffen Ellis, et al.
|
|
5
5
|
*
|
|
6
|
-
*
|
|
7
|
-
* panel (`_app.tsx:1255-1280`), as a dumb presentational unit. It shows which backend the runtime
|
|
8
|
-
* resolved to (WebGPU / WASM, with the int8 size the host formats into the label) and lets the visitor
|
|
9
|
-
* opt out of WebGPU. Props in, one boolean event out — the host re-loads the bundle on the toggle.
|
|
10
|
-
*
|
|
11
|
-
* NODE-SAFE: pure React, no maplibre.
|
|
6
|
+
* Shows the active inference backend and a checkbox that forces WASM. The host applies the change.
|
|
12
7
|
*/
|
|
13
8
|
|
|
14
9
|
import type { ReactNode } from "react"
|
|
15
10
|
|
|
11
|
+
/**
|
|
12
|
+
* Props for {@link BackendControl}.
|
|
13
|
+
*/
|
|
16
14
|
export interface BackendControlProps {
|
|
17
15
|
/**
|
|
18
|
-
* The backend the runtime
|
|
16
|
+
* The backend the runtime chose, such as `webgpu (28 MB int8)`.
|
|
17
|
+
* It is empty until known.
|
|
19
18
|
*/
|
|
20
19
|
activeBackend?: string
|
|
21
20
|
/**
|
|
22
|
-
* Whether the
|
|
21
|
+
* Whether the WASM backend is forced.
|
|
23
22
|
*/
|
|
24
23
|
forceWASM: boolean
|
|
25
24
|
/**
|
|
26
|
-
*
|
|
25
|
+
* Called when the visitor toggles the "Force WASM" checkbox.
|
|
27
26
|
*/
|
|
28
27
|
onForceWASMChange: (forceWASM: boolean) => void
|
|
29
28
|
}
|
|
30
29
|
|
|
31
30
|
/**
|
|
32
|
-
*
|
|
31
|
+
* Renders the backend indicator and the "Force WASM" checkbox.
|
|
33
32
|
*/
|
|
34
33
|
export function BackendControl({ activeBackend, forceWASM, onForceWASMChange }: BackendControlProps): ReactNode {
|
|
35
34
|
return (
|
|
@@ -3,55 +3,32 @@
|
|
|
3
3
|
* @license AGPL-3.0
|
|
4
4
|
* @author Teffen Ellis, et al.
|
|
5
5
|
*
|
|
6
|
-
*
|
|
7
|
-
* control panel (`_app.tsx:1281-1339`), as a dumb presentational unit. Turning it on reveals a second
|
|
8
|
-
* version picker (the primary version filtered out); the actual second parse is a host concern the
|
|
9
|
-
* composed demo surfaces through `panels.compare`. Props in, two events out.
|
|
10
|
-
*
|
|
11
|
-
* NODE-SAFE: pure React, no maplibre.
|
|
6
|
+
* Renders a compare-mode checkbox and a selector for the second model version, leaving the comparison itself to the host.
|
|
12
7
|
*/
|
|
13
8
|
|
|
14
9
|
import type { ReactNode } from "react"
|
|
15
10
|
|
|
16
11
|
import type { VersionOption } from "#map/types"
|
|
17
12
|
|
|
13
|
+
/**
|
|
14
|
+
* Props for {@link CompareToggle}.
|
|
15
|
+
*/
|
|
18
16
|
export interface CompareToggleProps {
|
|
19
|
-
/**
|
|
20
|
-
* The selectable model bundles (the primary version is filtered out of the compare list).
|
|
21
|
-
*/
|
|
22
17
|
versions: ReadonlyArray<VersionOption>
|
|
23
|
-
/**
|
|
24
|
-
* The primary version, excluded from the compare options.
|
|
25
|
-
*/
|
|
26
18
|
primaryVersion: string | null
|
|
27
|
-
/**
|
|
28
|
-
* Whether compare mode is on.
|
|
29
|
-
*/
|
|
30
19
|
compareMode: boolean
|
|
31
|
-
/**
|
|
32
|
-
* Fired when the visitor flips compare mode.
|
|
33
|
-
*/
|
|
34
20
|
onCompareModeChange: (compareMode: boolean) => void
|
|
35
|
-
/**
|
|
36
|
-
* The version chosen to compare against, or `null` when none is chosen.
|
|
37
|
-
*/
|
|
38
21
|
compareVersion: string | null
|
|
39
|
-
/**
|
|
40
|
-
* Fired with the chosen compare version (or `null` when the empty option is picked).
|
|
41
|
-
*/
|
|
42
22
|
onCompareVersionChange: (version: string | null) => void
|
|
43
|
-
/**
|
|
44
|
-
* Disable the compare-version select (e.g. while a parse or compare load runs).
|
|
45
|
-
*/
|
|
46
23
|
disabled?: boolean
|
|
47
|
-
/**
|
|
48
|
-
* A status line rendered under the select (e.g. the compare backend, or a "Loading…" line).
|
|
49
|
-
*/
|
|
50
24
|
status?: ReactNode
|
|
51
25
|
}
|
|
52
26
|
|
|
53
27
|
/**
|
|
54
|
-
*
|
|
28
|
+
* Renders the compare checkbox.
|
|
29
|
+
*
|
|
30
|
+
* In compare mode, it also renders the version selector. and no control at all
|
|
31
|
+
* when fewer than two versions exist.
|
|
55
32
|
*/
|
|
56
33
|
export function CompareToggle({
|
|
57
34
|
versions,
|
|
@@ -0,0 +1,88 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @copyright Sister Software
|
|
3
|
+
* @license AGPL-3.0
|
|
4
|
+
* @author Teffen Ellis, et al.
|
|
5
|
+
*
|
|
6
|
+
* Display and log build, model and runtime details for bug reports.
|
|
7
|
+
* Report the actual execution backend because successful loading does not imply WebGPU ran.
|
|
8
|
+
*/
|
|
9
|
+
|
|
10
|
+
import { type ReactNode, useEffect, useMemo } from "react"
|
|
11
|
+
|
|
12
|
+
import { useBuildInfo } from "#common/useBuildInfo"
|
|
13
|
+
|
|
14
|
+
export interface DebugInfoProps {
|
|
15
|
+
/**
|
|
16
|
+
* The backend the runtime resolved to (e.g. `webgpu (28 MB int8)`); empty before it is known.
|
|
17
|
+
*/
|
|
18
|
+
activeBackend?: string
|
|
19
|
+
/**
|
|
20
|
+
* Whether the CPU/wasm backend is currently forced.
|
|
21
|
+
*
|
|
22
|
+
* This explains a `wasm` backend that would otherwise indicate a WebGPU failure.
|
|
23
|
+
*/
|
|
24
|
+
forceWASM?: boolean
|
|
25
|
+
/**
|
|
26
|
+
* The model version the runtime loaded.
|
|
27
|
+
*
|
|
28
|
+
* The training series.
|
|
29
|
+
* It differs from the npm version.
|
|
30
|
+
*/
|
|
31
|
+
selectedVersion?: string | null
|
|
32
|
+
/**
|
|
33
|
+
* Whether the asset bundle finished loading.
|
|
34
|
+
*/
|
|
35
|
+
ready?: boolean
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
/**
|
|
39
|
+
* One row of the record, as a label and a value.
|
|
40
|
+
*/
|
|
41
|
+
function Row({ label, value }: { label: string; value: string }): ReactNode {
|
|
42
|
+
return (
|
|
43
|
+
<div className="mw-debug-info__row">
|
|
44
|
+
<span className="mw-debug-info__label">{label}</span>
|
|
45
|
+
<code className="mw-debug-info__value">{value}</code>
|
|
46
|
+
</div>
|
|
47
|
+
)
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
export function DebugInfo({ activeBackend, forceWASM, selectedVersion, ready }: DebugInfoProps): ReactNode {
|
|
51
|
+
const build = useBuildInfo()
|
|
52
|
+
|
|
53
|
+
// Memoized on the primitives it reads, so the log below fires when a value changes
|
|
54
|
+
// rather than on every render.
|
|
55
|
+
// A record rebuilt each render would be a new object each time and log continuously.
|
|
56
|
+
const record = useMemo(
|
|
57
|
+
() => ({
|
|
58
|
+
app: build?.app ?? "—",
|
|
59
|
+
commit: build?.commit ?? build?.revision ?? "—",
|
|
60
|
+
buildTime: build?.buildTime ?? "—",
|
|
61
|
+
model: selectedVersion ?? "—",
|
|
62
|
+
backend: activeBackend || (ready ? "unknown" : "loading…"),
|
|
63
|
+
forceWASM: Boolean(forceWASM),
|
|
64
|
+
webgpuInBrowser: typeof navigator !== "undefined" && "gpu" in navigator,
|
|
65
|
+
userAgent: typeof navigator !== "undefined" ? navigator.userAgent : "—",
|
|
66
|
+
}),
|
|
67
|
+
[build?.app, build?.commit, build?.revision, build?.buildTime, selectedVersion, activeBackend, forceWASM, ready]
|
|
68
|
+
)
|
|
69
|
+
|
|
70
|
+
useEffect(() => {
|
|
71
|
+
// eslint-disable-next-line no-console -- this is the feature: the record has to reach the console a reporter copies.
|
|
72
|
+
console.info("[mailwoman] debug info", record)
|
|
73
|
+
}, [record])
|
|
74
|
+
|
|
75
|
+
return (
|
|
76
|
+
<div className="mw-debug-info">
|
|
77
|
+
<Row label="Build" value={record.app} />
|
|
78
|
+
<Row label="Commit" value={record.commit.slice(0, 12)} />
|
|
79
|
+
<Row label="Built" value={record.buildTime} />
|
|
80
|
+
<Row label="Model" value={record.model} />
|
|
81
|
+
<Row label="Backend" value={record.backend} />
|
|
82
|
+
{/* A browser with no WebGPU at all explains a `wasm` backend that is otherwise indistinguishable from a
|
|
83
|
+
WebGPU session that threw. */}
|
|
84
|
+
<Row label="WebGPU available" value={record.webgpuInBrowser ? "yes" : "no"} />
|
|
85
|
+
<Row label="Force WASM" value={record.forceWASM ? "on" : "off"} />
|
|
86
|
+
</div>
|
|
87
|
+
)
|
|
88
|
+
}
|
package/lib/map/Geocoder.tsx
CHANGED
|
@@ -2,21 +2,6 @@
|
|
|
2
2
|
* @copyright Sister Software
|
|
3
3
|
* @license AGPL-3.0
|
|
4
4
|
* @author Teffen Ellis, et al.
|
|
5
|
-
*
|
|
6
|
-
* `<Geocoder>` — the WHOLE geocoder, composed. It is the map analogue of `PipelineExplorer`
|
|
7
|
-
* and takes the SAME DI shape: an injected {@link GeocoderRuntime} (the host owns ONNX / httpvfs / R2 /
|
|
8
|
-
* the composed map style) plus a {@link GeocoderPanels} bag (the host's ModelVisualizer / VersionCompare /
|
|
9
|
-
* About / Permalink). Everything here is composition + a `ClientOnly` boundary:
|
|
10
|
-
*
|
|
11
|
-
* - the floating {@link GeocoderControls} panel (version / compare / backend / query+autocomplete / result),
|
|
12
|
-
* - the declarative {@link MapCanvas} with the phase-2 overlays ({@link OverlayLayers}) and the
|
|
13
|
-
* resolved-place marker/outline/camera ({@link ResolvedPlaceLayers}) driven by the parse state,
|
|
14
|
-
* - the hooks that wire them: {@link useGeocode} (parse + viewport bias + map place),
|
|
15
|
-
* {@link usePlaceAutocomplete}, {@link useCompareState}.
|
|
16
|
-
*
|
|
17
|
-
* Because it pulls {@link MapCanvas} (→ `react-map-gl` → `maplibre-gl`, WebGL + DOM at import), it lives on
|
|
18
|
-
* the `@mailwoman/react/map` subpath ONLY — never the package root. The whole thing renders in Storybook
|
|
19
|
-
* over a fake runtime (offline stub style + canned geocode) with no network, no ONNX, no gazetteer.
|
|
20
5
|
*/
|
|
21
6
|
|
|
22
7
|
import { type ReactNode, useCallback, useEffect, useRef, useState } from "react"
|
|
@@ -31,46 +16,69 @@ import { usePlaceAutocomplete } from "#map/usePlaceAutocomplete"
|
|
|
31
16
|
import { ClientOnly } from "../common/ClientOnly.tsx"
|
|
32
17
|
import type { Preset } from "../common/PresetChips.tsx"
|
|
33
18
|
import { GeocoderControls } from "./GeocoderControls.tsx"
|
|
19
|
+
import { GraticuleLayer } from "./GraticuleLayer.tsx"
|
|
34
20
|
import { MapCanvas } from "./MapCanvas.tsx"
|
|
35
21
|
import { OverlayLayers } from "./OverlayLayers.tsx"
|
|
36
22
|
import { ResolvedPlaceLayers } from "./ResolvedPlaceLayers.tsx"
|
|
37
23
|
|
|
24
|
+
/**
|
|
25
|
+
* Props for {@linkcode Geocoder}.
|
|
26
|
+
*/
|
|
38
27
|
export interface GeocoderProps {
|
|
39
28
|
/**
|
|
40
|
-
* The
|
|
29
|
+
* The geocoder runtime supplies the map style and overlays.
|
|
30
|
+
*
|
|
31
|
+
* It also supplies the parser and version and backend controls.
|
|
41
32
|
*/
|
|
42
33
|
runtime: GeocoderRuntime
|
|
43
34
|
/**
|
|
44
|
-
*
|
|
35
|
+
* Panels supplied by the host.
|
|
45
36
|
*/
|
|
46
37
|
panels?: GeocoderPanels
|
|
47
38
|
/**
|
|
48
|
-
*
|
|
39
|
+
* The address that pre-fills the search field.
|
|
40
|
+
* It is not run automatically.
|
|
49
41
|
*/
|
|
50
42
|
defaultAddress?: string
|
|
51
43
|
/**
|
|
52
|
-
*
|
|
44
|
+
* A query to run once when the runtime is ready, such as a permalink's `?q=` value.
|
|
45
|
+
*
|
|
46
|
+
* Unlike {@link GeocoderProps.defaultAddress}, this query is submitted,
|
|
47
|
+
* so a shared link reproduces its result.
|
|
48
|
+
*/
|
|
49
|
+
initialQuery?: string | null
|
|
50
|
+
/**
|
|
51
|
+
* The example chips.
|
|
52
|
+
*
|
|
53
|
+
* @default []
|
|
53
54
|
*/
|
|
54
55
|
presets?: ReadonlyArray<Preset>
|
|
55
56
|
/**
|
|
56
|
-
*
|
|
57
|
-
*
|
|
57
|
+
* Whether the developer panel starts open.
|
|
58
|
+
*
|
|
59
|
+
* @default false
|
|
58
60
|
*/
|
|
59
61
|
developer?: boolean
|
|
60
62
|
/**
|
|
61
|
-
*
|
|
62
|
-
*
|
|
63
|
+
* Called with each user-submitted query.
|
|
64
|
+
*
|
|
65
|
+
* The host decides how to write the query to its URL.
|
|
66
|
+
* This package never touches `location`.
|
|
63
67
|
*/
|
|
64
68
|
onSubmitQuery?: (query: string) => void
|
|
65
69
|
/**
|
|
66
|
-
*
|
|
67
|
-
*
|
|
70
|
+
* The minimum map zoom at which the viewport is sent as a location bias.
|
|
71
|
+
*
|
|
72
|
+
* @default 4
|
|
68
73
|
*/
|
|
69
74
|
minBiasZoom?: number
|
|
70
75
|
/**
|
|
71
|
-
*
|
|
72
|
-
*
|
|
73
|
-
*
|
|
76
|
+
* Whether the map moves to each resolved place.
|
|
77
|
+
*
|
|
78
|
+
* Set it to false when the host controls the camera or a test needs a fixed view.
|
|
79
|
+
* The marker and outline render either way.
|
|
80
|
+
*
|
|
81
|
+
* @default true
|
|
74
82
|
*/
|
|
75
83
|
applyResultCamera?: boolean
|
|
76
84
|
}
|
|
@@ -80,6 +88,7 @@ interface GeocoderInnerProps extends Required<
|
|
|
80
88
|
> {
|
|
81
89
|
panels: GeocoderPanels
|
|
82
90
|
presets: ReadonlyArray<Preset>
|
|
91
|
+
initialQuery: string | null
|
|
83
92
|
onSubmitQuery?: (query: string) => void
|
|
84
93
|
}
|
|
85
94
|
|
|
@@ -91,23 +100,25 @@ function GeocoderInner({
|
|
|
91
100
|
minBiasZoom,
|
|
92
101
|
applyResultCamera,
|
|
93
102
|
developer,
|
|
103
|
+
initialQuery,
|
|
94
104
|
onSubmitQuery,
|
|
95
105
|
}: GeocoderInnerProps): ReactNode {
|
|
96
106
|
const mapRef = useRef<MapRef>(null)
|
|
97
|
-
// The
|
|
98
|
-
//
|
|
99
|
-
// handle also puts it in state — one poll, two consumers.
|
|
107
|
+
// The controls render outside `<MapCanvas>` and cannot call `useMap()`.
|
|
108
|
+
// The map is kept in state so they re-render when it loads.
|
|
100
109
|
const [map, setMap] = useState<ReturnType<MapRef["getMap"]> | null>(null)
|
|
101
110
|
|
|
102
|
-
// The
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
// TEST INJECTION POINT: the e2e viewport-bias suite drives the REAL map (pan + zoom past the bias threshold)
|
|
106
|
-
// before submitting, and a browser test cannot reach a React ref — so the same handle is republished on
|
|
107
|
-
// `globalThis.__mailwomanMapCanvas`, and cleared on unmount so a torn-down geocoder leaves no stale handle.
|
|
111
|
+
// The graticule is inserted before the first non-background layer, so it draws under the data layers.
|
|
112
|
+
const [baseLayerID, setBaseLayerID] = useState<string | undefined>(undefined)
|
|
113
|
+
|
|
108
114
|
const onMapLoad = useCallback((event: { target: ReturnType<MapRef["getMap"]> }) => {
|
|
115
|
+
// Browser tests read the map from this global.
|
|
109
116
|
;(globalThis as { __mailwomanMapCanvas?: ReturnType<MapRef["getMap"]> }).__mailwomanMapCanvas = event.target
|
|
110
117
|
setMap(event.target)
|
|
118
|
+
|
|
119
|
+
const layers = event.target.getStyle()?.layers ?? []
|
|
120
|
+
|
|
121
|
+
setBaseLayerID(layers.find((layer) => layer.type !== "background")?.id)
|
|
111
122
|
}, [])
|
|
112
123
|
|
|
113
124
|
useEffect(
|
|
@@ -118,8 +129,6 @@ function GeocoderInner({
|
|
|
118
129
|
[]
|
|
119
130
|
)
|
|
120
131
|
|
|
121
|
-
// Read the viewport bias at submit time — through the map handle, never a threaded state value, so granting/zooming
|
|
122
|
-
// mid-session doesn't re-create the parse callback. Below the min-bias zoom, a whole-globe center is noise → null.
|
|
123
132
|
const getBias = useCallback((): MapBias | null => {
|
|
124
133
|
const live = mapRef.current?.getMap()
|
|
125
134
|
|
|
@@ -165,10 +174,11 @@ function GeocoderInner({
|
|
|
165
174
|
zoom: runtime.initialZoom ?? 3,
|
|
166
175
|
}}
|
|
167
176
|
style={{ width: "100%", height: "100%" }}
|
|
168
|
-
//
|
|
169
|
-
//
|
|
177
|
+
// The attribution is compact.
|
|
178
|
+
// The MapLibre logo is hidden.
|
|
170
179
|
mapProps={{ attributionControl: { compact: true }, maplibreLogo: false, onLoad: onMapLoad }}
|
|
171
180
|
>
|
|
181
|
+
<GraticuleLayer beforeID={baseLayerID} />
|
|
172
182
|
<OverlayLayers overlays={runtime.overlays} />
|
|
173
183
|
<ResolvedPlaceLayers spec={spec} applyCamera={applyResultCamera} />
|
|
174
184
|
{panels.mapControls}
|
|
@@ -183,26 +193,28 @@ function GeocoderInner({
|
|
|
183
193
|
panels={panels}
|
|
184
194
|
presets={presets}
|
|
185
195
|
placeholder={defaultAddress}
|
|
196
|
+
initialQuery={initialQuery}
|
|
186
197
|
map={map}
|
|
187
198
|
onSubmitQuery={onSubmitQuery}
|
|
188
199
|
onSelectVersion={onSelectVersion}
|
|
189
200
|
onForceWASMChange={onForceWASMChange}
|
|
190
201
|
developer={developer}
|
|
191
202
|
/>
|
|
192
|
-
|
|
193
203
|
{panels.debugDrawer ? panels.debugDrawer({ result: geocode.result }) : null}
|
|
194
204
|
</div>
|
|
195
205
|
)
|
|
196
206
|
}
|
|
197
207
|
|
|
198
|
-
|
|
199
|
-
* Stable empty defaults — a fresh `{}`/`[]` per render would churn every downstream memo dep.
|
|
200
|
-
*/
|
|
208
|
+
// These defaults are module constants so each render sees the same reference and memo dependencies stay stable.
|
|
201
209
|
const NO_PANELS: GeocoderPanels = {}
|
|
202
210
|
const NO_PRESETS: ReadonlyArray<Preset> = []
|
|
203
211
|
|
|
204
212
|
/**
|
|
205
|
-
*
|
|
213
|
+
* Renders the map and search controls as one geocoder.
|
|
214
|
+
* It also renders host panels.
|
|
215
|
+
*
|
|
216
|
+
* It renders only on the client because MapLibre needs browser APIs.
|
|
217
|
+
* Import it from `@mailwoman/react/map`.
|
|
206
218
|
*/
|
|
207
219
|
export function Geocoder({
|
|
208
220
|
runtime,
|
|
@@ -212,6 +224,7 @@ export function Geocoder({
|
|
|
212
224
|
minBiasZoom = 4,
|
|
213
225
|
applyResultCamera = true,
|
|
214
226
|
developer = false,
|
|
227
|
+
initialQuery = null,
|
|
215
228
|
onSubmitQuery,
|
|
216
229
|
}: GeocoderProps): ReactNode {
|
|
217
230
|
return (
|
|
@@ -231,6 +244,7 @@ export function Geocoder({
|
|
|
231
244
|
minBiasZoom={minBiasZoom}
|
|
232
245
|
applyResultCamera={applyResultCamera}
|
|
233
246
|
developer={developer}
|
|
247
|
+
initialQuery={initialQuery}
|
|
234
248
|
onSubmitQuery={onSubmitQuery}
|
|
235
249
|
/>
|
|
236
250
|
)}
|