From a158d5d1c55c0139d5d16fe97d30860e272d4778 Mon Sep 17 00:00:00 2001 From: zaidmukaddam Date: Mon, 19 Aug 2024 18:20:36 +0530 Subject: [PATCH] Updated Google Maps API script to include marker library and use Advanced Markers --- app/api/chat/route.ts | 1 - app/page.tsx | 51 +++++++++++++++++++++++-------------------- package.json | 1 + pnpm-lock.yaml | 19 +++++++++++----- tsconfig.json | 3 ++- 5 files changed, 43 insertions(+), 32 deletions(-) diff --git a/app/api/chat/route.ts b/app/api/chat/route.ts index 4beb6fc..4711956 100644 --- a/app/api/chat/route.ts +++ b/app/api/chat/route.ts @@ -1,4 +1,3 @@ -import { anthropic } from "@ai-sdk/anthropic"; import { openai } from '@ai-sdk/openai' import { convertToCoreMessages, streamText, tool } from "ai"; import { CodeInterpreter } from "@e2b/code-interpreter"; diff --git a/app/page.tsx b/app/page.tsx index 3f6606b..5e04956 100644 --- a/app/page.tsx +++ b/app/page.tsx @@ -260,57 +260,60 @@ export default function Home() { const isValidCoordinate = (coord: number) => { return typeof coord === 'number' && !isNaN(coord) && isFinite(coord); }; - + const loadGoogleMapsScript = (callback: () => void) => { if (window.google && window.google.maps) { callback(); return; } - + const existingScript = document.getElementById('googleMapsScript'); if (existingScript) { existingScript.remove(); } - + window.initMap = callback; const script = document.createElement('script'); script.id = 'googleMapsScript'; - script.src = `https://maps.googleapis.com/maps/api/js?key=${process.env.NEXT_PUBLIC_GOOGLE_MAPS_API_KEY}&libraries=places&callback=initMap`; + script.src = `https://maps.googleapis.com/maps/api/js?key=${process.env.NEXT_PUBLIC_GOOGLE_MAPS_API_KEY}&libraries=places,marker&callback=initMap`; script.async = true; script.defer = true; document.head.appendChild(script); }; - + const MapComponent = React.memo(({ center, places }: { center: { lat: number; lng: number }, places: any[] }) => { const mapRef = useRef(null); const [mapError, setMapError] = useState(null); const googleMapRef = useRef(null); - const markersRef = useRef([]); - + const markersRef = useRef([]); + const memoizedCenter = useMemo(() => center, [center]); const memoizedPlaces = useMemo(() => places, [places]); - - const initializeMap = useCallback(() => { + + const initializeMap = useCallback(async () => { if (mapRef.current && isValidCoordinate(memoizedCenter.lat) && isValidCoordinate(memoizedCenter.lng)) { + const { Map } = await google.maps.importLibrary("maps") as google.maps.MapsLibrary; + const { AdvancedMarkerElement } = await google.maps.importLibrary("marker") as google.maps.MarkerLibrary; + if (!googleMapRef.current) { - googleMapRef.current = new window.google.maps.Map(mapRef.current, { + googleMapRef.current = new Map(mapRef.current, { center: memoizedCenter, zoom: 14, + mapId: "347ff92e0c7225cf", }); } else { googleMapRef.current.setCenter(memoizedCenter); } - + // Clear existing markers - markersRef.current.forEach(marker => marker.setMap(null)); + markersRef.current.forEach(marker => marker.map = null); markersRef.current = []; - + memoizedPlaces.forEach((place) => { if (isValidCoordinate(place.location.lat) && isValidCoordinate(place.location.lng)) { - const MarkerClass = window.google.maps.marker?.AdvancedMarkerElement || window.google.maps.Marker; - const marker = new MarkerClass({ - position: place.location, + const marker = new AdvancedMarkerElement({ map: googleMapRef.current, + position: place.location, title: place.name, }); markersRef.current.push(marker); @@ -320,7 +323,7 @@ export default function Home() { setMapError('Invalid coordinates provided'); } }, [memoizedCenter, memoizedPlaces]); - + useEffect(() => { loadGoogleMapsScript(() => { try { @@ -330,17 +333,17 @@ export default function Home() { setMapError('Failed to initialize Google Maps'); } }); - + return () => { // Clean up markers when component unmounts - markersRef.current.forEach(marker => marker.setMap(null)); + markersRef.current.forEach(marker => marker.map = null); }; }, [initializeMap]); - + if (mapError) { return
{mapError}
; } - + return
; }); @@ -349,7 +352,7 @@ export default function Home() { const MapSkeleton = () => ( ); - + const PlaceDetails = ({ place }: { place: any }) => (
@@ -398,7 +401,7 @@ export default function Home() {
); } - + if (isLoading) { return ( @@ -411,7 +414,7 @@ export default function Home() { ); } - + return ( diff --git a/package.json b/package.json index d78bb5b..a16e312 100644 --- a/package.json +++ b/package.json @@ -43,6 +43,7 @@ "zod": "^3.23.8" }, "devDependencies": { + "@types/google.maps": "^3.55.12", "@types/node": "^20", "@types/react": "^18", "@types/react-dom": "^18", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 4bb8271..11505ab 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -52,7 +52,7 @@ dependencies: version: 1.4.0 ai: specifier: latest - version: 3.3.9(react@18.3.1)(svelte@4.2.18)(vue@3.4.35)(zod@3.23.8) + version: 3.3.10(react@18.3.1)(svelte@4.2.18)(vue@3.4.35)(zod@3.23.8) class-variance-authority: specifier: ^0.7.0 version: 0.7.0 @@ -103,6 +103,9 @@ dependencies: version: 3.23.8 devDependencies: + '@types/google.maps': + specifier: ^3.55.12 + version: 3.55.12 '@types/node': specifier: ^20 version: 20.14.13 @@ -269,8 +272,8 @@ packages: zod-to-json-schema: 3.22.5(zod@3.23.8) dev: false - /@ai-sdk/vue@0.0.37(vue@3.4.35)(zod@3.23.8): - resolution: {integrity: sha512-m7dMi6qRoWPuru9TyWUm5jXAPGSDb1SHZp/Q+uYjhNY1dZwgsZxJvSeakogzR37uhiRCg3Kg8fCypQJe+dikPA==} + /@ai-sdk/vue@0.0.38(vue@3.4.35)(zod@3.23.8): + resolution: {integrity: sha512-iqVPsRDXkrfIFzwrWoUKqBzMqSHxJQoompdj0LCC9v3s9c4ndn9Vx67nB5g2ee3fO3bY/O9vLebDwYyVKM4glg==} engines: {node: '>=18'} peerDependencies: vue: ^3.3.4 @@ -1324,6 +1327,10 @@ packages: resolution: {integrity: sha512-/kYRxGDLWzHOB7q+wtSUQlFrtcdUccpfy+X+9iMBpHK8QLLhx2wIPYuS5DYtR9Wa/YlZAbIovy7qVdB1Aq6Lyw==} dev: false + /@types/google.maps@3.55.12: + resolution: {integrity: sha512-Q8MsLE+YYIrE1H8wdN69YHHAF8h7ApvF5MiMXh/zeCpP9Ut745mV9M0F4X4eobZ2WJe9k8tW2ryYjLa87IO2Sg==} + dev: true + /@types/googlemaps@3.43.3: resolution: {integrity: sha512-ZWNoz/O8MPEpiajvj7QiqCY8tTLFNqNZ/a+s+zTV58wFVNAvvqV4bdGfnsjTb5Cs4V6wEsLrX8XRhmnyYJ2Tdg==} deprecated: 'Types for the Google Maps browser API have moved to @types/google.maps. Note: these types are not for the googlemaps npm package, which is a Node API.' @@ -1569,8 +1576,8 @@ packages: engines: {node: '>=0.4.0'} hasBin: true - /ai@3.3.9(react@18.3.1)(svelte@4.2.18)(vue@3.4.35)(zod@3.23.8): - resolution: {integrity: sha512-PS6xHzYIH+iVLG3xd/jwsqZW7+X8GrSrsJwVB4ACMbxhZN8KRs4yUcnGEDPcvRkEL3PqHHJFUo9iVysdZwOUwg==} + /ai@3.3.10(react@18.3.1)(svelte@4.2.18)(vue@3.4.35)(zod@3.23.8): + resolution: {integrity: sha512-NuUUymuQb5KWZii8xMARfhloXmzlRNJiibv7Ci5N6WsMs2DmiVUlybUEL+DOYfIdDRzqCC2mxE0agpdgCbA2kA==} engines: {node: '>=18'} peerDependencies: openai: ^4.42.0 @@ -1596,7 +1603,7 @@ packages: '@ai-sdk/solid': 0.0.36(zod@3.23.8) '@ai-sdk/svelte': 0.0.38(svelte@4.2.18)(zod@3.23.8) '@ai-sdk/ui-utils': 0.0.33(zod@3.23.8) - '@ai-sdk/vue': 0.0.37(vue@3.4.35)(zod@3.23.8) + '@ai-sdk/vue': 0.0.38(vue@3.4.35)(zod@3.23.8) '@opentelemetry/api': 1.9.0 eventsource-parser: 1.1.2 json-schema: 0.4.0 diff --git a/tsconfig.json b/tsconfig.json index 88730b6..4ca486d 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -20,7 +20,8 @@ ], "paths": { "@/*": ["./*"] - } + }, + "types": ["google.maps"] }, "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"], "exclude": ["node_modules"]