UNPKG

@sanity/google-maps-input

Version:

Sanity plugin providing input handlers for geo-related input types using Google Maps

1 lines • 48.4 kB
{"version":3,"file":"index.cjs","sources":["../src/loader/loadGoogleMapsApi.ts","../src/loader/LoadError.tsx","../src/loader/GoogleMapsLoadProxy.tsx","../src/global-workaround.ts","../src/input/GeopointInput.styles.tsx","../src/map/SearchInput.styles.tsx","../src/map/SearchInput.tsx","../src/map/util.ts","../src/map/Map.styles.tsx","../src/map/Map.tsx","../src/map/Marker.tsx","../src/input/GeopointSelect.tsx","../src/input/GeopointInput.tsx","../src/map/Arrow.tsx","../src/diff/GeopointMove.tsx","../src/diff/GeopointFieldDiff.styles.tsx","../src/diff/GeopointArrayDiff.tsx","../src/diff/GeopointFieldDiff.tsx","../src/plugin.tsx"],"sourcesContent":["declare global {\n // eslint-disable-next-line\n interface Window {\n gm_authFailure: any\n ___sanity_googleMapsApiCallback: any\n }\n}\n\nconst callbackName = '___sanity_googleMapsApiCallback'\nconst authFailureCallbackName = 'gm_authFailure'\n\nexport class AuthError extends Error {}\n\nfunction _loadGoogleMapsApi(config: {locale: string; apiKey: string}) {\n return new Promise<typeof window.google.maps>((resolve, reject) => {\n window[authFailureCallbackName] = () => {\n reject(new AuthError('Authentication error when loading Google Maps API.'))\n }\n\n window[callbackName] = () => {\n resolve(window.google.maps)\n }\n\n const script = document.createElement('script')\n script.onerror = (\n event: Event | string,\n source?: string,\n lineno?: number,\n colno?: number,\n error?: Error,\n ) => reject(new Error(coeerceError(event, error)))\n\n script.src = `https://maps.googleapis.com/maps/api/js?key=${config.apiKey}&libraries=places&callback=${callbackName}&language=${config.locale}`\n document.getElementsByTagName('head')[0].appendChild(script)\n }).finally(() => {\n delete window[callbackName]\n delete window[authFailureCallbackName]\n })\n}\n\nlet memo: Promise<typeof window.google.maps> | null = null\nexport function loadGoogleMapsApi(config: {\n locale: string\n apiKey: string\n}): Promise<typeof window.google.maps> {\n if (memo) {\n return memo\n }\n memo = _loadGoogleMapsApi(config)\n memo.catch(() => {\n memo = null\n })\n return memo\n}\nfunction coeerceError(event: Event | string, error?: Error): string {\n if (error) {\n return error.message\n }\n\n if (typeof event === 'string') {\n return event\n }\n\n return isErrorEvent(event) ? event.message : 'Failed to load Google Maps API'\n}\n\nfunction isErrorEvent(event: unknown): event is ErrorEvent {\n if (typeof event !== 'object' || event === null) {\n return false\n }\n\n if (!('message' in event)) {\n return false\n }\n\n return typeof (event as ErrorEvent).message === 'string'\n}\n","import {Card, Box, Text, Code} from '@sanity/ui'\n\ntype Props = {error: {message?: string}; isAuthError: false} | {isAuthError: true}\n\nexport function LoadError(props: Props) {\n return (\n <Card tone=\"critical\" radius={1}>\n <Box as=\"header\" paddingX={4} paddingTop={4} paddingBottom={1}>\n <Text as=\"h2\" weight=\"bold\">\n Google Maps failed to load\n </Text>\n </Box>\n\n <Box paddingX={4} paddingTop={4} paddingBottom={1}>\n {props.isAuthError ? (\n <AuthError />\n ) : (\n <>\n <Text as=\"h3\">Error details:</Text>\n <pre>\n <Code size={1}>{'error' in props && props.error?.message}</Code>\n </pre>\n </>\n )}\n </Box>\n </Card>\n )\n}\n\nfunction AuthError() {\n return (\n <Text>\n <p>The error appears to be related to authentication</p>\n <p>Common causes include:</p>\n <ul>\n <li>Incorrect API key</li>\n <li>Referer not allowed</li>\n <li>Missing authentication scope</li>\n </ul>\n <p>Check the browser developer tools for more information.</p>\n </Text>\n )\n}\n","import {type ReactElement, useEffect, useState} from 'react'\nimport type {GoogleMapsInputConfig} from '../types'\nimport {AuthError, loadGoogleMapsApi} from './loadGoogleMapsApi'\nimport {LoadError as LoadErrorView} from './LoadError'\n\ninterface LoadProps {\n children: (api: typeof window.google.maps) => ReactElement\n config: GoogleMapsInputConfig\n}\n\nconst browserLocale = (typeof window !== 'undefined' && window.navigator.language) || 'en'\n\ntype LoadState =\n | {\n type: 'loading'\n }\n | {\n type: 'loaded'\n api: typeof window.google.maps\n }\n | {\n type: 'error'\n error: {type: 'loadError' | 'authError'; message: string}\n }\n\nfunction useLoadGoogleMapsApi(config: {defaultLocale?: string; apiKey: string}): LoadState {\n const locale = config.defaultLocale || browserLocale || 'en-US'\n\n const [state, setState] = useState<LoadState>({type: 'loading'})\n\n useEffect(() => {\n if (typeof window === 'undefined') {\n return\n }\n\n loadGoogleMapsApi({locale, apiKey: config.apiKey}).then(\n (api) => setState({type: 'loaded', api}),\n (err) =>\n setState({\n type: 'error',\n error: {type: err instanceof AuthError ? 'authError' : 'loadError', message: err.message},\n }),\n )\n }, [locale, config.apiKey])\n return state\n}\n\nexport function GoogleMapsLoadProxy(props: LoadProps) {\n const loadState = useLoadGoogleMapsApi(props.config)\n switch (loadState.type) {\n case 'error':\n return (\n <LoadErrorView error={loadState.error} isAuthError={loadState.error.type === 'authError'} />\n )\n case 'loading':\n return <div>Loading Google Maps API</div>\n case 'loaded':\n return props.children(loadState.api)\n default:\n return null\n }\n}\n","import type {GoogleMapsInputConfig} from './types'\n\nlet config: GoogleMapsInputConfig\n\nexport function getGeoConfig(): GoogleMapsInputConfig {\n return config as GoogleMapsInputConfig\n}\n\nexport function setGeoConfig(newConfig: GoogleMapsInputConfig): void {\n config = newConfig\n}\n","import {styled} from 'styled-components'\n\nexport const PreviewImage = styled.img`\n width: 100%;\n height: auto;\n vertical-align: top;\n`\n\nexport const DialogInnerContainer = styled.div`\n height: 40rem;\n`\n","import {styled} from 'styled-components'\n\nexport const WrapperContainer = styled.div`\n position: absolute;\n right: 10px;\n top: 10px;\n width: 220px;\n`\n","import {TextInput} from '@sanity/ui'\nimport {WrapperContainer} from './SearchInput.styles'\nimport {createRef, PureComponent} from 'react'\n\ninterface Props {\n api: typeof window.google.maps\n map: google.maps.Map\n onChange: (result: google.maps.places.PlaceResult) => void\n}\n\nexport class SearchInput extends PureComponent<Props> {\n searchInputRef = createRef<HTMLInputElement>()\n autoComplete: google.maps.places.Autocomplete | undefined\n\n handleChange = () => {\n if (!this.autoComplete) {\n return\n }\n\n this.props.onChange(this.autoComplete.getPlace())\n\n if (this.searchInputRef.current) {\n this.searchInputRef.current.value = ''\n }\n }\n\n componentDidMount() {\n const input = this.searchInputRef.current\n if (!input) {\n return\n }\n\n const {api, map} = this.props\n const {Circle, places, event} = api\n const searchBounds = new Circle({center: map.getCenter(), radius: 100}).getBounds()!\n this.autoComplete = new places.Autocomplete(input, {\n bounds: searchBounds,\n types: [], // return all kinds of places\n })\n\n event.addListener(this.autoComplete, 'place_changed', this.handleChange)\n }\n\n render() {\n return (\n <WrapperContainer>\n <TextInput\n name=\"place\"\n ref={this.searchInputRef}\n placeholder=\"Search for place or address\"\n padding={4}\n />\n </WrapperContainer>\n )\n }\n}\n","import type {LatLng} from '../types'\n\nexport function latLngAreEqual(\n latLng1: LatLng | google.maps.LatLng,\n latLng2: LatLng | google.maps.LatLng,\n): boolean {\n const lat1 = typeof latLng1.lat === 'function' ? latLng1.lat() : latLng1.lat\n const lng1 = typeof latLng1.lng === 'function' ? latLng1.lng() : latLng1.lng\n\n const lat2 = typeof latLng2.lat === 'function' ? latLng2.lat() : latLng2.lat\n const lng2 = typeof latLng2.lng === 'function' ? latLng2.lng() : latLng2.lng\n\n return lat1 === lat2 && lng1 === lng2\n}\n","import {styled} from 'styled-components'\n\nexport const MapContainer = styled.div`\n position: absolute;\n top: 0;\n left: 0;\n height: 100%;\n width: 100%;\n box-sizing: border-box;\n`\n","import {createRef, PureComponent, type ReactElement} from 'react'\nimport type {LatLng} from '../types'\nimport {latLngAreEqual} from './util'\nimport {MapContainer} from './Map.styles'\n\ninterface MapProps {\n api: typeof window.google.maps\n location: LatLng\n bounds?: google.maps.LatLngBounds\n defaultZoom?: number\n mapTypeControl?: boolean\n scrollWheel?: boolean\n controlSize?: number\n onClick?: (event: google.maps.MapMouseEvent) => void\n children?: (map: google.maps.Map) => ReactElement\n}\n\ninterface MapState {\n map: google.maps.Map | undefined\n}\n\nexport class GoogleMap extends PureComponent<MapProps, MapState> {\n static defaultProps = {\n defaultZoom: 8,\n scrollWheel: true,\n }\n\n state: MapState = {map: undefined}\n clickHandler: google.maps.MapsEventListener | undefined\n mapRef = createRef<HTMLDivElement>()\n mapEl: HTMLDivElement | null = null\n\n componentDidMount() {\n this.attachClickHandler()\n }\n\n attachClickHandler = () => {\n const map = this.state.map\n if (!map) {\n return\n }\n\n const {api, onClick} = this.props\n const {event} = api\n\n if (this.clickHandler) {\n this.clickHandler.remove()\n }\n\n if (onClick) {\n this.clickHandler = event.addListener(map, 'click', onClick)\n }\n }\n\n componentDidUpdate(prevProps: MapProps) {\n const map = this.state.map\n if (!map) {\n return\n }\n\n const {onClick, location, bounds} = this.props\n\n if (prevProps.onClick !== onClick) {\n this.attachClickHandler()\n }\n\n if (!latLngAreEqual(prevProps.location, location)) {\n map.panTo(this.getCenter())\n }\n\n if (bounds && (!prevProps.bounds || !bounds.equals(prevProps.bounds))) {\n map.fitBounds(bounds)\n }\n }\n\n componentWillUnmount() {\n if (this.clickHandler) {\n this.clickHandler.remove()\n }\n }\n\n getCenter(): google.maps.LatLng {\n const {location, api} = this.props\n return new api.LatLng(location.lat, location.lng)\n }\n\n constructMap(el: HTMLDivElement) {\n const {defaultZoom, api, mapTypeControl, controlSize, bounds, scrollWheel} = this.props\n\n const map = new api.Map(el, {\n zoom: defaultZoom,\n center: this.getCenter(),\n scrollwheel: scrollWheel,\n streetViewControl: false,\n mapTypeControl,\n controlSize,\n })\n\n if (bounds) {\n map.fitBounds(bounds)\n }\n\n return map\n }\n\n setMapElement = (element: HTMLDivElement | null) => {\n if (element && element !== this.mapEl) {\n const map = this.constructMap(element)\n this.setState({map}, this.attachClickHandler)\n }\n\n this.mapEl = element\n }\n\n render() {\n const {children} = this.props\n const {map} = this.state\n return (\n <>\n <MapContainer ref={this.setMapElement} />\n {children && map ? children(map) : null}\n </>\n )\n }\n}\n","import {PureComponent, type MutableRefObject} from 'react'\nimport type {LatLng} from '../types'\nimport {latLngAreEqual} from './util'\n\nconst markerPath =\n 'M 3.052 3.7 C 1.56 5.293 0.626 7.612 0.663 9.793 C 0.738 14.352 2.793 16.077 6.078 22.351 C 7.263 25.111 8.497 28.032 9.672 32.871 C 9.835 33.584 9.994 34.246 10.069 34.305 C 10.143 34.362 10.301 33.697 10.465 32.983 C 11.639 28.145 12.875 25.226 14.059 22.466 C 17.344 16.192 19.398 14.466 19.474 9.908 C 19.511 7.727 18.574 5.405 17.083 3.814 C 15.379 1.994 12.809 0.649 10.069 0.593 C 7.328 0.536 4.756 1.882 3.052 3.7 Z'\n\ninterface Props {\n api: typeof window.google.maps\n map: google.maps.Map\n onMove?: (event: google.maps.MapMouseEvent) => void\n onClick?: (event: google.maps.MapMouseEvent) => void\n position: LatLng | google.maps.LatLng\n zIndex?: number\n opacity?: number\n label?: string\n markerRef?: MutableRefObject<google.maps.Marker | undefined>\n color?: {background: string; border: string; text: string}\n}\n\nexport class Marker extends PureComponent<Props> {\n marker: google.maps.Marker | undefined\n\n eventHandlers: {\n move?: google.maps.MapsEventListener\n click?: google.maps.MapsEventListener\n } = {}\n\n componentDidMount() {\n const {position, api, map, onMove, zIndex, opacity, label, markerRef, color} = this.props\n const {Marker: GMarker} = api\n\n let icon: google.maps.Symbol | undefined\n if (color) {\n icon = {\n path: markerPath,\n fillOpacity: 1,\n fillColor: color.background,\n strokeColor: color.border,\n strokeWeight: 2,\n anchor: new api.Point(10, 35),\n labelOrigin: new api.Point(10, 11),\n }\n }\n\n this.marker = new GMarker({\n draggable: Boolean(onMove),\n position,\n map,\n zIndex,\n opacity,\n label,\n icon,\n })\n\n if (markerRef) {\n markerRef.current = this.marker\n }\n\n this.attachMoveHandler()\n this.attachClickHandler()\n }\n\n componentDidUpdate(prevProps: Props) {\n if (!this.marker) {\n return\n }\n\n const {position, onMove, label, zIndex, opacity, map} = this.props\n\n if (prevProps.onMove !== onMove) {\n this.attachMoveHandler()\n }\n\n if (!latLngAreEqual(prevProps.position, position)) {\n this.marker.setPosition(position)\n }\n\n if (prevProps.label !== label) {\n this.marker.setLabel(label || null)\n }\n\n if (prevProps.zIndex !== zIndex) {\n this.marker.setZIndex(zIndex || null)\n }\n\n if (prevProps.opacity !== opacity) {\n this.marker.setOpacity(opacity || null)\n }\n\n if (prevProps.map !== map) {\n this.marker.setMap(map)\n }\n }\n\n componentWillUnmount() {\n if (this.eventHandlers.move) {\n this.eventHandlers.move.remove()\n }\n\n if (this.marker) {\n this.marker.setMap(null)\n }\n }\n\n attachMoveHandler() {\n const {api, onMove} = this.props\n if (this.eventHandlers.move) {\n this.eventHandlers.move.remove()\n }\n if (this.marker && onMove) {\n this.eventHandlers.move = api.event.addListener(this.marker, 'dragend', onMove)\n }\n }\n\n attachClickHandler() {\n const {api, onClick} = this.props\n if (this.eventHandlers.click) {\n this.eventHandlers.click.remove()\n }\n if (this.marker && onClick) {\n this.eventHandlers.click = api.event.addListener(this.marker, 'click', onClick)\n }\n }\n\n // eslint-disable-next-line class-methods-use-this\n render(): any {\n return null\n }\n}\n","import {type FC, useCallback} from 'react'\nimport {SearchInput} from '../map/SearchInput'\nimport {GoogleMap} from '../map/Map'\nimport {Marker} from '../map/Marker'\nimport type {LatLng, Geopoint} from '../types'\n\nconst fallbackLatLng: LatLng = {lat: 40.7058254, lng: -74.1180863}\n\ninterface SelectProps {\n api: typeof window.google.maps\n value?: Geopoint\n onChange?: (latLng: google.maps.LatLng) => void\n defaultLocation?: LatLng\n defaultZoom?: number\n}\n\nexport const GeopointSelect: FC<SelectProps> = ({\n api,\n value,\n onChange,\n defaultLocation = {lng: 10.74609, lat: 59.91273},\n defaultZoom = 8,\n}) => {\n const getCenter = useCallback(() => {\n const point: LatLng = {...fallbackLatLng, ...defaultLocation, ...value}\n return point\n }, [value, defaultLocation])\n\n const setValue = useCallback(\n (geoPoint: google.maps.LatLng) => {\n if (onChange) {\n onChange(geoPoint)\n }\n },\n [onChange],\n )\n\n const handlePlaceChanged = useCallback(\n (place: google.maps.places.PlaceResult) => {\n if (!place.geometry?.location) {\n return\n }\n setValue(place.geometry.location)\n },\n [setValue],\n )\n\n const handleMarkerDragEnd = useCallback(\n (event: google.maps.MapMouseEvent) => {\n if (event.latLng) setValue(event.latLng)\n },\n [setValue],\n )\n\n const handleMapClick = useCallback(\n (event: google.maps.MapMouseEvent) => {\n if (event.latLng) setValue(event.latLng)\n },\n [setValue],\n )\n\n return (\n <GoogleMap api={api} location={getCenter()} onClick={handleMapClick} defaultZoom={defaultZoom}>\n {(map) => (\n <>\n <SearchInput api={api} map={map} onChange={handlePlaceChanged} />\n {value && (\n <Marker\n api={api}\n map={map}\n position={value}\n onMove={onChange ? handleMarkerDragEnd : undefined}\n />\n )}\n </>\n )}\n </GoogleMap>\n )\n}\n","import {useCallback, useEffect, useId, useRef, useState} from 'react'\nimport {Box, Button, Dialog, Grid, Stack} from '@sanity/ui'\nimport {EditIcon, TrashIcon} from '@sanity/icons'\nimport {ObjectInputProps, set, setIfMissing, unset, ChangeIndicator, Path} from 'sanity'\nimport {GoogleMapsLoadProxy} from '../loader/GoogleMapsLoadProxy'\nimport type {Geopoint, GeopointSchemaType, GoogleMapsInputConfig, LatLng} from '../types'\nimport {getGeoConfig} from '../global-workaround'\nimport {DialogInnerContainer, PreviewImage} from './GeopointInput.styles'\nimport {GeopointSelect} from './GeopointSelect'\n\nconst EMPTY_PATH: Path = []\n\nconst getStaticImageUrl = (value: LatLng, apiKey: string) => {\n const loc = `${value.lat},${value.lng}`\n const qs = new URLSearchParams({\n key: apiKey,\n center: loc,\n markers: loc,\n zoom: '13',\n scale: '2',\n size: '640x300',\n })\n\n return `https://maps.googleapis.com/maps/api/staticmap?${qs.toString()}`\n}\n\nexport type GeopointInputProps = ObjectInputProps<Geopoint, GeopointSchemaType> & {\n geoConfig: GoogleMapsInputConfig\n}\n\nexport function GeopointInput(props: GeopointInputProps) {\n const {\n changed,\n elementProps,\n focused,\n geoConfig: config,\n onChange,\n onPathFocus,\n path,\n readOnly,\n schemaType,\n value,\n } = props\n\n const {\n id,\n ref: inputRef,\n onBlur: handleBlur,\n onFocus: handleFocus,\n 'aria-describedby': ariaDescribedBy,\n } = elementProps\n\n const schemaTypeName = schemaType.name\n const dialogId = useId()\n const dialogRef = useRef<HTMLDivElement | null>(null)\n const handleFocusButton = useCallback(() => inputRef?.current?.focus(), [inputRef])\n const [modalOpen, setModalOpen] = useState(false)\n\n const handleCloseModal = useCallback(() => {\n if (dialogRef.current) dialogRef.current.blur()\n setModalOpen(false)\n handleFocusButton()\n }, [setModalOpen, handleFocusButton])\n\n const handleToggleModal = useCallback(\n () => setModalOpen((currentState) => !currentState),\n [setModalOpen],\n )\n\n const handleChange = useCallback(\n (latLng: google.maps.LatLng) => {\n onChange([\n setIfMissing({_type: schemaTypeName}),\n set(latLng.lat(), ['lat']),\n set(latLng.lng(), ['lng']),\n ])\n },\n [schemaTypeName, onChange],\n )\n\n const handleClear = useCallback(() => {\n onChange(unset())\n }, [onChange])\n\n useEffect(() => {\n if (modalOpen) {\n onPathFocus(EMPTY_PATH)\n }\n }, [modalOpen, onPathFocus])\n\n if (!config || !config.apiKey) {\n return (\n <div>\n <p>\n The <a href=\"https://sanity.io/docs/schema-types/geopoint-type\">Geopoint type</a> needs a\n Google Maps API key with access to:\n </p>\n <ul>\n <li>Google Maps JavaScript API</li>\n <li>Google Places API Web Service</li>\n <li>Google Static Maps API</li>\n </ul>\n <p>\n Please enter the API key with access to these services in your googleMapsInput plugin\n config.\n </p>\n </div>\n )\n }\n\n return (\n <Stack space={3}>\n {value && (\n <ChangeIndicator path={path} isChanged={changed} hasFocus={!!focused}>\n <PreviewImage\n src={getStaticImageUrl(value, config.apiKey)}\n alt=\"Map location\"\n onClick={handleFocusButton}\n onDoubleClick={handleToggleModal}\n />\n </ChangeIndicator>\n )}\n\n <Box>\n <Grid columns={value ? 2 : 1} gap={3}>\n <Button\n aria-describedby={ariaDescribedBy}\n disabled={readOnly}\n icon={value && EditIcon}\n id={id}\n mode=\"ghost\"\n onClick={handleToggleModal}\n onFocus={handleFocus}\n padding={3}\n ref={inputRef}\n text={value ? 'Edit' : 'Set location'}\n />\n\n {value && (\n <Button\n disabled={readOnly}\n icon={TrashIcon}\n mode=\"ghost\"\n onClick={handleClear}\n padding={3}\n text=\"Remove\"\n tone=\"critical\"\n />\n )}\n </Grid>\n </Box>\n\n {modalOpen && (\n <Dialog\n header=\"Place the marker on the map\"\n id={`${dialogId}_dialog`}\n onBlur={handleBlur}\n onClose={handleCloseModal}\n ref={dialogRef}\n width={1}\n >\n <DialogInnerContainer>\n <GoogleMapsLoadProxy config={getGeoConfig()}>\n {(api) => (\n <GeopointSelect\n api={api}\n value={value || undefined}\n onChange={readOnly ? undefined : handleChange}\n defaultLocation={config.defaultLocation}\n defaultZoom={config.defaultZoom}\n />\n )}\n </GoogleMapsLoadProxy>\n </DialogInnerContainer>\n </Dialog>\n )}\n </Stack>\n )\n}\n","import {type MutableRefObject, PureComponent} from 'react'\nimport type {LatLng} from '../types'\nimport {latLngAreEqual} from './util'\n\ninterface Props {\n api: typeof window.google.maps\n map: google.maps.Map\n from: LatLng\n to: LatLng\n color?: {background: string; border: string; text: string}\n zIndex?: number\n arrowRef?: MutableRefObject<google.maps.Polyline | undefined>\n onClick?: (event: google.maps.MapMouseEvent) => void\n}\n\nexport class Arrow extends PureComponent<Props> {\n line: google.maps.Polyline | undefined\n\n eventHandlers: {\n click?: google.maps.MapsEventListener\n } = {}\n\n componentDidMount() {\n const {from, to, api, map, zIndex, onClick, color, arrowRef} = this.props\n const lineSymbol = {\n path: api.SymbolPath.FORWARD_OPEN_ARROW,\n }\n\n this.line = new api.Polyline({\n map,\n zIndex,\n path: [from, to],\n icons: [{icon: lineSymbol, offset: '50%'}],\n strokeOpacity: 0.55,\n strokeColor: color ? color.text : 'black',\n })\n\n if (onClick) {\n this.eventHandlers.click = api.event.addListener(this.line, 'click', onClick)\n }\n\n if (arrowRef) {\n arrowRef.current = this.line\n }\n }\n\n componentDidUpdate(prevProps: Props) {\n if (!this.line) {\n return\n }\n\n const {from, to, map} = this.props\n if (!latLngAreEqual(prevProps.from, from) || !latLngAreEqual(prevProps.to, to)) {\n this.line.setPath([from, to])\n }\n\n if (prevProps.map !== map) {\n this.line.setMap(map)\n }\n }\n\n componentWillUnmount() {\n if (this.line) {\n this.line.setMap(null)\n }\n\n if (this.eventHandlers.click) {\n this.eventHandlers.click.remove()\n }\n }\n\n // eslint-disable-next-line class-methods-use-this\n render(): any {\n return null\n }\n}\n","import {useRef} from 'react'\nimport {useUserColor, type ObjectDiff} from 'sanity'\nimport {Marker} from '../map/Marker'\nimport {Arrow} from '../map/Arrow'\nimport type {Geopoint} from '../types'\n\ninterface GeopointMoveProps {\n api: typeof window.google.maps\n map: google.maps.Map\n diff: ObjectDiff<Geopoint>\n label?: string\n}\n\nexport function GeopointMove({diff, api, map, label}: GeopointMoveProps) {\n const {fromValue: from, toValue: to} = diff\n const annotation = diff.isChanged ? diff.annotation : undefined\n const userColor = useUserColor(annotation ? annotation.author : null) || undefined\n const fromRef = useRef<google.maps.Marker>()\n const toRef = useRef<google.maps.Marker>()\n\n return (\n <>\n {from && (\n <Marker\n api={api}\n map={map}\n position={from}\n zIndex={0}\n opacity={0.55}\n markerRef={fromRef}\n color={userColor}\n />\n )}\n {from && to && <Arrow api={api} map={map} from={from} to={to} zIndex={1} color={userColor} />}\n {to && (\n <Marker\n api={api}\n map={map}\n position={to}\n zIndex={2}\n markerRef={toRef}\n label={label}\n color={userColor}\n />\n )}\n </>\n )\n}\n","import {styled} from 'styled-components'\n\nexport const RootContainer = styled.div`\n position: relative;\n min-height: 200px;\n\n &:empty {\n background-color: var(--card-skeleton-color-from);\n display: table;\n width: 100%;\n }\n\n &:empty:after {\n content: 'Missing/invalid data';\n display: table-cell;\n vertical-align: middle;\n text-align: center;\n position: relative;\n }\n`\n","import type {\n ArrayDiff,\n Diff,\n DiffComponent,\n DiffProps as GenericDiffProps,\n ObjectDiff,\n} from 'sanity'\nimport {GoogleMapsLoadProxy} from '../loader/GoogleMapsLoadProxy'\nimport {GoogleMap} from '../map/Map'\nimport type {Geopoint} from '../types'\nimport {getGeoConfig} from '../global-workaround'\nimport {GeopointMove} from './GeopointMove'\nimport {RootContainer} from './GeopointFieldDiff.styles'\n\nexport type DiffProps = GenericDiffProps<ArrayDiff<Geopoint>>\n\nexport const GeopointArrayDiff: DiffComponent<ArrayDiff<Geopoint>> = ({\n diff,\n schemaType,\n}: DiffProps) => {\n return (\n <RootContainer>\n <GoogleMapsLoadProxy config={getGeoConfig()}>\n {(api) => <GeopointDiff api={api} diff={diff} schemaType={schemaType} />}\n </GoogleMapsLoadProxy>\n </RootContainer>\n )\n}\n\nfunction GeopointDiff({api, diff}: DiffProps & {api: typeof google.maps}) {\n const fromValue = (diff.fromValue || []).filter(hasCoordinates)\n const toValue = (diff.toValue || []).filter(hasCoordinates)\n if (fromValue.length === 0 && toValue.length === 0) {\n return null\n }\n\n const bounds = getBounds(fromValue, toValue, api)\n return (\n <GoogleMap\n api={api}\n location={bounds.getCenter().toJSON()}\n mapTypeControl={false}\n controlSize={20}\n bounds={bounds}\n >\n {(map) => (\n <>\n {diff.items.map(({toIndex, diff: pointDiff}) => {\n if (!isChangeDiff(pointDiff)) {\n return null\n }\n\n return (\n <GeopointMove\n key={toIndex}\n api={api}\n map={map}\n diff={pointDiff}\n label={`${toIndex}`}\n />\n )\n })}\n </>\n )}\n </GoogleMap>\n )\n}\n\nfunction isChangeDiff(diff: Diff): diff is ObjectDiff<Geopoint> {\n return diff.action !== 'unchanged' && diff.type === 'object'\n}\n\nfunction hasCoordinates(point: Partial<Geopoint>): point is Geopoint {\n return typeof point.lat === 'number' && typeof point.lng === 'number'\n}\n\nfunction getBounds(\n fromValue: google.maps.LatLngLiteral[] | null | undefined,\n toValue: google.maps.LatLngLiteral[] | null | undefined,\n api: typeof window.google.maps,\n): google.maps.LatLngBounds {\n const bounds = new api.LatLngBounds()\n const points = [...(fromValue || []), ...(toValue || [])]\n points.forEach((point) => bounds.extend(point))\n return bounds\n}\n","import {\n type DiffComponent,\n type ObjectDiff,\n type DiffProps as GenericDiffProps,\n DiffTooltip,\n getAnnotationAtPath,\n} from 'sanity'\nimport {GoogleMapsLoadProxy} from '../loader/GoogleMapsLoadProxy'\nimport {GoogleMap} from '../map/Map'\nimport type {Geopoint} from '../types'\nimport {getGeoConfig} from '../global-workaround'\nimport {GeopointMove} from './GeopointMove'\nimport {RootContainer} from './GeopointFieldDiff.styles'\n\nexport type DiffProps = GenericDiffProps<ObjectDiff<Geopoint>>\n\nexport const GeopointFieldDiff: DiffComponent<ObjectDiff<Geopoint>> = ({\n diff,\n schemaType,\n}: DiffProps) => {\n return (\n <RootContainer>\n <GoogleMapsLoadProxy config={getGeoConfig()}>\n {(api) => <GeopointDiff api={api} diff={diff} schemaType={schemaType} />}\n </GoogleMapsLoadProxy>\n </RootContainer>\n )\n}\n\nfunction GeopointDiff({api, diff}: DiffProps & {api: typeof window.google.maps}) {\n const {fromValue, toValue} = diff\n const annotation =\n getAnnotationAtPath(diff, ['lat']) ||\n getAnnotationAtPath(diff, ['lng']) ||\n getAnnotationAtPath(diff, [])\n\n const center = getCenter(diff, api)\n const bounds = fromValue && toValue ? getBounds(fromValue, toValue, api) : undefined\n\n return (\n <DiffTooltip annotations={annotation ? [annotation] : []} description={getAction(diff)}>\n <div>\n <GoogleMap\n api={api}\n location={center}\n mapTypeControl={false}\n controlSize={20}\n bounds={bounds}\n scrollWheel={false}\n >\n {(map) => <GeopointMove api={api} map={map} diff={diff} />}\n </GoogleMap>\n </div>\n </DiffTooltip>\n )\n}\n\nfunction getBounds(\n fromValue: google.maps.LatLngLiteral,\n toValue: google.maps.LatLngLiteral,\n api: typeof window.google.maps,\n): google.maps.LatLngBounds {\n return new api.LatLngBounds().extend(fromValue).extend(toValue)\n}\n\nfunction getCenter(\n diff: DiffProps['diff'],\n api: typeof window.google.maps,\n): google.maps.LatLngLiteral {\n const {fromValue, toValue} = diff\n if (fromValue && toValue) {\n return getBounds(fromValue, toValue, api).getCenter().toJSON()\n }\n\n if (fromValue) {\n return fromValue\n }\n\n if (toValue) {\n return toValue\n }\n\n throw new Error('Neither a from or a to value present')\n}\n\nfunction getAction(diff: ObjectDiff<Geopoint>) {\n const {fromValue, toValue} = diff\n if (fromValue && toValue) {\n return 'Moved'\n } else if (fromValue) {\n return 'Removed'\n } else if (toValue) {\n return 'Added'\n }\n\n return 'Unchanged'\n}\n","import {definePlugin, type SchemaType} from 'sanity'\nimport {GeopointInput, type GeopointInputProps} from './input/GeopointInput'\nimport {setGeoConfig} from './global-workaround'\nimport type {GeopointSchemaType, GoogleMapsInputConfig} from './types'\n\nexport const googleMapsInput = definePlugin<GoogleMapsInputConfig>((config) => {\n setGeoConfig(config)\n return {\n name: 'google-maps-input',\n form: {\n components: {\n input(props) {\n if (isGeopoint(props.schemaType)) {\n const castedProps = props as unknown as Omit<GeopointInputProps, 'geoConfig'>\n return <GeopointInput {...castedProps} geoConfig={config} />\n }\n return props.renderDefault(props)\n },\n },\n },\n }\n})\n\nfunction isGeopoint(schemaType: SchemaType): schemaType is GeopointSchemaType {\n return isType('geopoint', schemaType)\n}\n\nfunction isType(name: string, schema?: SchemaType): boolean {\n if (schema?.name === name) {\n return true\n // eslint-disable-next-line no-negated-condition\n } else if (!schema?.name) {\n return false\n }\n return isType(name, schema?.type)\n}\n"],"names":["config","AuthError","jsxs","Card","jsx","Box","Text","Fragment","Code","useState","useEffect","LoadErrorView","styled","PureComponent","__publicField","createRef","TextInput","getCenter","useCallback","__spreadValues","useId","useRef","setIfMissing","set","unset","Stack","ChangeIndicator","Grid","Button","EditIcon","TrashIcon","Dialog","useUserColor","GeopointDiff","getBounds","getAnnotationAtPath","DiffTooltip","definePlugin"],"mappings":"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"}