diff --git a/src/app/(default)/editArea/[slug]/general/components/AreaLatLngForm.tsx b/src/app/(default)/editArea/[slug]/general/components/AreaLatLngForm.tsx
index b0f9e0436..40a638e28 100644
--- a/src/app/(default)/editArea/[slug]/general/components/AreaLatLngForm.tsx
+++ b/src/app/(default)/editArea/[slug]/general/components/AreaLatLngForm.tsx
@@ -56,7 +56,6 @@ export const AreaLatLngForm: React.FC<{ initLat: number, initLng: number, uuid:
{
setPickerSelected(false)
}}
diff --git a/src/components/maps/CoordinatePickerMap.tsx b/src/components/maps/CoordinatePickerMap.tsx
index 844d5b17b..ca93c6cfc 100644
--- a/src/components/maps/CoordinatePickerMap.tsx
+++ b/src/components/maps/CoordinatePickerMap.tsx
@@ -1,6 +1,6 @@
import React, { useCallback, useState, useRef, useEffect } from 'react'
import { Map, FullscreenControl, ScaleControl, NavigationControl, Marker, GeolocateControl, GeolocateResultEvent } from 'react-map-gl/maplibre'
-import maplibregl, { MapLibreEvent } from 'maplibre-gl'
+import { MapLibreEvent } from 'maplibre-gl'
import dynamic from 'next/dynamic'
import { useDebouncedCallback } from 'use-debounce'
import { MAP_STYLES, type MapStyles } from './MapSelector'
@@ -10,64 +10,40 @@ import AlertDialog from '../ui/micro/AlertDialogue'
import useResponsive from '@/js/hooks/useResponsive'
import { MapPin, Crosshair } from '@phosphor-icons/react'
-export interface CameraInfo {
- center: {
- lng: number
- lat: number
- }
- zoom: number
-}
-
interface CoordinatePickerMapProps {
showFullscreenControl?: boolean
- initialCenter?: [number, number]
- initialViewState?: {
- bounds: maplibregl.LngLatBoundsLike
- fitBoundsOptions: maplibregl.FitBoundsOptions
- }
onCoordinateConfirmed?: (coordinates: [number, number] | null) => void
name?: string
}
export const CoordinatePickerMap: React.FC = ({
- showFullscreenControl = true, initialCenter, onCoordinateConfirmed
+ showFullscreenControl = true, onCoordinateConfirmed
}) => {
const initialZoom = 14
const defaultCoords = { lng: 0, lat: 0 }
const [newSelectedCoord, setNewSelectedCoord] = useState<{ lng: number, lat: number }>(defaultCoords)
const [cursor, setCursor] = useState('default')
- const [dynamicInitialCenter, setDynamicInitialCenter] = useState<[number, number] | null>(initialCenter ?? null)
+ const [center, setCenter] = useState<{ lat: number, lng: number } | null>(null)
const { isMobile } = useResponsive()
const [mapStyle, setMapStyle] = useState(MAP_STYLES.light.style)
const triggerButtonRef = useRef(null)
const { watch, setValue } = useFormContext()
- // Use latlngStr from form context as it may differ from initialCenter if updated without page reload
+ // Watch the 'latlngStr' value from form context
const watchedCoords = watch('latlngStr') as string
- const initialCoordinates = dynamicInitialCenter != null
- ? { lng: dynamicInitialCenter[0], lat: dynamicInitialCenter[1] }
- : { lng: 0, lat: 0 }
-
useEffect(() => {
if (watchedCoords != null) {
const [lat, lng] = watchedCoords.split(',').map(Number)
-
- // Update dynamicInitialCenter if it's different from watchedCoords
- if (dynamicInitialCenter == null || lat !== dynamicInitialCenter[1] || lng !== dynamicInitialCenter[0]) {
- setDynamicInitialCenter([lng, lat])
- }
-
+ setCenter({ lat, lng })
setNewSelectedCoord({ lat, lng })
}
- }, [watchedCoords, dynamicInitialCenter])
+ }, [watchedCoords])
const onLoad = useCallback((e: MapLibreEvent) => {
- if (e.target == null) return
- if (dynamicInitialCenter != null) {
- e.target.jumpTo({ center: { lng: dynamicInitialCenter?.[0] ?? 0, lat: dynamicInitialCenter?.[1] ?? 0 }, zoom: initialZoom })
- }
- }, [dynamicInitialCenter])
+ if (e.target == null || center == null) return
+ e.target.jumpTo({ center: { lat: center.lat, lng: center.lng }, zoom: initialZoom })
+ }, [center])
const updateCoordinates = useDebouncedCallback((lng, lat) => {
setNewSelectedCoord({ lng, lat })
@@ -75,7 +51,6 @@ export const CoordinatePickerMap: React.FC = ({
const confirmSelection = (): void => {
setValue('latlngStr', `${newSelectedCoord.lat?.toFixed(5) ?? 0},${newSelectedCoord.lng?.toFixed(5) ?? 0}`, { shouldDirty: true, shouldValidate: true })
- setDynamicInitialCenter([newSelectedCoord.lng, newSelectedCoord.lat])
if (onCoordinateConfirmed != null) {
onCoordinateConfirmed([newSelectedCoord.lng ?? 0, newSelectedCoord.lat ?? 0])
}
@@ -101,6 +76,13 @@ export const CoordinatePickerMap: React.FC = ({
}
}
+ // Compare newSelectedCoord with watchedCoords to decide whether to show the crosshair
+ const isNewCoord = (): boolean => {
+ if (watchedCoords === null) return false
+ const [lat, lng] = watchedCoords.split(',').map(Number)
+ return !(newSelectedCoord.lat === lat && newSelectedCoord.lng === lng)
+ }
+
const anchorClass = isMobile
? 'fixed bottom-1/4 left-1/2 transform -translate-x-1/2'
: 'fixed bottom-1/4 left-1/2 transform -translate-x-1/2'
@@ -111,8 +93,8 @@ export const CoordinatePickerMap: React.FC = ({
id='coordinate-picker-map'
onLoad={onLoad}
initialViewState={{
- longitude: initialCoordinates.lng,
- latitude: initialCoordinates.lat,
+ longitude: center?.lng ?? 0,
+ latitude: center?.lat ?? 0,
zoom: initialZoom
}}
onDragStart={() => {
@@ -132,13 +114,12 @@ export const CoordinatePickerMap: React.FC = ({
{showFullscreenControl && }
- {(dynamicInitialCenter != null) && (
-
+ {center != null && (
+
)}
- {/* Show crosshair marker if the selected coordinates are different from the initial center */}
- {(newSelectedCoord.lng !== dynamicInitialCenter?.[0] && newSelectedCoord.lat !== dynamicInitialCenter?.[1]) && (
+ {isNewCoord() && (