1. قبل البدء
في هذا الدرس التطبيقي حول الترميز، ستتعرّف على كل ما تحتاج إليه للبدء في استخدام مكتبة vis.gl/react-google-map
لخدمة Google Maps JavaScript API، والتي تتيح لك إضافة خريطة من Google إلى تطبيق React. ستتعرّف على كيفية إعداد المكتبة وتحميل Maps JavaScript API وعرض أول خريطة والعمل مع العلامات وتجميع العلامات ورسم الأشكال على الخريطة والتعامل مع تفاعلات المستخدمين.
المتطلبات الأساسية
- معرفة أساسية بلغات JavaScript وHTML وCSS
ما ستتعلمه
- كيفية بدء استخدام مكتبة
vis.gl/react-google-map
في "منصة خرائط Google" - كيفية تحميل Maps JavaScript API بشكل تعريفي
- كيفية تحميل خريطة في تطبيق React
- كيفية استخدام العلامات والعلامات المخصّصة وتجميع العلامات
- كيفية استخدام نظام الأحداث في Maps JavaScript API لتوفير تفاعل المستخدم
- كيفية التحكّم في الخريطة بشكل ديناميكي
- كيفية الرسم على الخريطة
ما تحتاج إليه
- حساب على Google Cloud تم تفعيل الفوترة فيه
- مفتاح Google Maps Platform API مع تفعيل Maps JavaScript API
- Node.js مثبَّت على جهاز الكمبيوتر
- محرّر نصوص أو بيئة تطوير متكاملة (IDE) من اختيارك
- مكتبة
vis.gl/react-google-map
لواجهة Google Maps JavaScript API - مكتبة
googlemaps/markerclusterer
إعداد Google Maps Platform
إذا لم يكن لديك حساب على Google Cloud Platform ومشروع مفعَّل فيه نظام الفوترة، يُرجى الاطّلاع على دليل البدء باستخدام Google Maps Platform لإنشاء حساب فوترة ومشروع.
- في Cloud Console، انقر على القائمة المنسدلة الخاصة بالمشروع واختَر المشروع الذي تريد استخدامه في هذا الدرس العملي.
- فعِّل واجهات برمجة التطبيقات وحِزم تطوير البرامج (SDK) في Google Maps Platform المطلوبة لهذا الدرس العملي في Google Cloud Marketplace. لإجراء ذلك، اتّبِع الخطوات الواردة في هذا الفيديو أو هذه المستندات.
- أنشئ مفتاح واجهة برمجة التطبيقات في صفحة بيانات الاعتماد في Cloud Console. يمكنك اتّباع الخطوات الواردة في هذا الفيديو أو هذه المستندات. تتطلّب جميع الطلبات إلى "منصة خرائط Google" مفتاح واجهة برمجة تطبيقات.
2. طريقة الإعداد
تنزيل مشروع البداية
لتنزيل نموذج مشروع البداية ورمز الحلّ، اتّبِع الخطوات التالية:
- نزِّل مستودع GitHub أو أنشئ نسخة منه. يقع مشروع البداية في الدليل
/starter
ويتضمّن بنية الملف الأساسية التي تحتاج إليها لإكمال الدرس العملي. يمكنك إنجاز جميع أعمالك في الدليل/starter/src
.
git clone https://github.com/googlemaps-samples/codelab-maps-platform-101-react-js.git
بدلاً من ذلك، انقر على هذا الزر لتنزيل الرمز المصدر.
- انتقِل إلى الدليل
/starter
وثبِّت npm. يؤدي ذلك إلى تثبيت جميع العناصر التابعة اللازمة والمدرَجة في الملفpackage.json
.
cd starter && npm install
- أثناء البقاء في دليل
/starter
، اتّبِع الخطوات التالية:
npm start
تم إعداد مشروع البداية لتتمكّن من استخدام خادم تطوير Vite الذي يجمع التعليمات البرمجية التي تكتبها ويشغّلها محليًا. يعيد خادم تطوير Vite أيضًا تحميل تطبيقك تلقائيًا في المتصفح في أي وقت تجري فيه تغييرات على الرمز. إذا اتّبعت الرابط المقدَّم في نهاية عملية الإنشاء، من المفترض أن تجد صفحة ويب مكتوبًا فيها: "مرحبًا بالعالم".
- إذا كنت تريد تنفيذ رمز الحل الكامل، انتقِل إلى الدليل
/solution
وأكمِل خطوات الإعداد نفسها.
3- تحميل Maps JavaScript API
أساس استخدام "منصة خرائط Google" على الويب هو Maps JavaScript API. توفّر واجهة برمجة التطبيقات هذه واجهة JavaScript لاستخدام جميع ميزات "منصة خرائط Google"، بما في ذلك الخريطة والعلامات وأدوات الرسم وخدمات "منصة خرائط Google" الأخرى، مثل Places.
لتحميل Maps JavaScript API باستخدام إطار عمل React، عليك استخدام المكوّن APIProvider
الذي يشكّل جزءًا من مكتبة vis.gl/react-google-map
. يمكن إضافة هذا المكوّن على أي مستوى من التطبيق، عادةً في مكان ما في الأعلى، ويعرض جميع المكوّنات الفرعية بدون تعديل. بالإضافة إلى معالجة تحميل Maps JavaScript API، يوفّر أيضًا معلومات السياق ووظائف المكوّنات وخطافات المكتبة الأخرى. يتم تضمين APIProvider
في مكتبة vis.gl/react-google-map
، لذا تم تثبيته عند تنفيذ npm install
في وقت سابق.
لاستخدام مكوّن APIProvider
، اتّبِع الخطوات التالية:
- افتح ملف
/src/app.tsx
. هذا الملف هو المكان الذي ستنفّذ فيه جميع المهام المطلوبة في هذا الدرس البرمجي. - في أعلى الملف، استورِد الفئة
APIProvider
من مكتبة@
vis.gl/react-google-maps
:
import {APIProvider} from '@vis.gl/react-google-maps';
- في تعريف الدالة
App
، اضبط المَعلمةapiKey
الخاصة بالمكوّنAPIProvider
باستخدام مفتاح واجهة برمجة التطبيقات الذي تم إنشاؤه في الخطوة السابقة والخاصيةonLoad
باستخدام رسالة سجلّ وحدة التحكّم:
<APIProvider apiKey={'Your API key here'} onLoad={() => console.log('Maps API has loaded.')}>
يتضمّن المكوّن APIProvider
سلسلة من السمات التي تحدّد خيارات مختلفة لتحميل Maps JavaScript API، بما في ذلك مفتاح واجهة برمجة التطبيقات في Google Maps Platform، وإصدار واجهة برمجة التطبيقات الذي تريد تحميله، وأي مكتبات إضافية توفّرها Maps JavaScript API وتريد تحميلها.
مفتاح Google Maps API هو السمة الوحيدة المطلوبة لكي تعمل APIProvider
، وقد أدرجنا السمة onLoad
لأغراض توضيحية. لمزيد من المعلومات، يُرجى الاطّلاع على مكوّن <APIProvider>
.
يجب أن يظهر ملف app.tsx
على النحو التالي:
import React from 'react';
import {createRoot} from "react-dom/client";
import {APIProvider} from '@vis.gl/react-google-maps';
const App = () => (
<APIProvider apiKey={'Your API key here'} onLoad={() => console.log('Maps API has loaded.')}>
<h1>Hello, world!</h1>
</APIProvider>
);
const root = createRoot(document.getElementById('app'));
root.render(<App />);
export default App;
في حال نجاح كل شيء، من المفترض أن ترى العبارة console.log
في وحدة تحكّم المتصفّح. بعد تحميل Maps JavaScript API، يمكنك عرض الخريطة الديناميكية في الخطوة التالية.
4. عرض خريطة
حان الوقت لعرض خريطتك الأولى.
الجزء الأكثر استخدامًا في Maps JavaScript API هو google.maps.Map
، وهو الفئة التي تتيح لك إنشاء مثيلات الخرائط ومعالجتها. تغلّف مكتبة vis.gl/react-google-map
هذه الفئة في المكوّن Map
. أولاً، استورِد الصفين Map
وMapCameraChangedEvent
.
import {APIProvider, Map, MapCameraChangedEvent} from '@vis.gl/react-google-maps';
يتيح المكوّن Map
مجموعة متنوعة من الإعدادات المختلفة للخريطة. في هذا الدرس العملي، ستستخدم الإعدادات التالية:
defaultCenter
، التي تحدّد خط العرض وخط الطول لمركز الخريطة.defaultZoom
، الذي يضبط مستوى التكبير أو التصغير الأولي للخريطة.- لعرض خريطة، ضَع الرمز التالي ضمن علامتَي
APIProvider
لتوسيط الخريطة على "سيدني"، أستراليا، ومنحها مستوى تكبير13
، وهو مستوى التكبير المناسب لعرض وسط المدينة:
<Map
defaultZoom={13}
defaultCenter={ { lat: -33.860664, lng: 151.208138 } }
onCameraChanged={ (ev: MapCameraChangedEvent) =>
console.log('camera changed:', ev.detail.center, 'zoom:', ev.detail.zoom)
}>
</Map>
من المفترض أن تظهر لك الآن خريطة سيدني في المتصفّح:
للتلخيص، في هذا القسم، عرضتَ خريطة باستخدام مكوّن <Map>
وضبطتَ حالتها الأولية باستخدام السمات. استخدمت أيضًا الأحداث لتسجيل وقت تغيير الكاميرا.
يجب أن يبدو ملف app.tsx
على النحو التالي:
import React from 'react';
import {createRoot} from "react-dom/client";
import {APIProvider, Map, MapCameraChangedEvent} from '@vis.gl/react-google-maps';
const App = () => (
<APIProvider apiKey={'Your API key here'} onLoad={() => console.log('Maps API has loaded.')}>
<Map
defaultZoom={13}
defaultCenter={ { lat: -33.860664, lng: 151.208138 } }
onCameraChanged={ (ev: MapCameraChangedEvent) =>
console.log('camera changed:', ev.detail.center, 'zoom:', ev.detail.zoom)
}>
</Map>
</APIProvider>
);
const root = createRoot(document.getElementById('app'));
root.render(<App />);
export default App;
5- إضافة تصميم الخرائط باستخدام السحابة الإلكترونية
يجب توفير رقم تعريف خريطة لاستخدام "محدّدات المواقع المتقدّمة" التي تستخدمها لوضع علامات على نقاط الاهتمام في خريطة سيدني. يُستخدَم معرّف الخريطة أيضًا لتصميم الخرائط باستخدام السحابة الإلكترونية.
يمكنك تخصيص نمط الخريطة باستخدام تصميم الخرائط باستخدام السحابة الإلكترونية.
إنشاء رقم تعريف خريطة
إذا لم يسبق لك إنشاء معرّف خريطة مرتبط بنمط خريطة، يمكنك الاطّلاع على دليل معرّفات الخرائط لإكمال الخطوات التالية:
- أنشئ معرّف خريطة.
- ربط رقم تعريف خريطة بنمط خريطة
لاستخدام معرّف الخريطة الذي أنشأته، اضبط السمة mapId
للمكوّن <Map>
:
<Map
defaultZoom={13}
defaultCenter={ { lat: -33.860664, lng: 151.208138 } }
mapId='DEMO_MAP_ID'
onCameraChanged={ (ev: MapCameraChangedEvent) =>
console.log('camera changed:', ev.detail.center, 'zoom:', ev.detail.zoom)
}>
</Map>
من المفترض أن يظهر لك النمط الذي اخترته على الخريطة.
6. إضافة علامات إلى الخريطة
هناك العديد من الإجراءات التي ينفّذها المطوّرون باستخدام Maps JavaScript API، ولكن وضع العلامات على الخريطة هو بالتأكيد الأكثر شيوعًا. تتيح لك العلامات عرض نقاط معيّنة على الخريطة، وهي عنصر شائع في واجهة المستخدم للتعامل مع تفاعل المستخدم. إذا سبق لك استخدام "خرائط Google"، من المحتمل أنّك على دراية بالعلامة التلقائية التي تبدو على النحو التالي:
لاستخدام مكوّن AdvancedMarker
لوضع علامات على الخريطة، اتّبِع الخطوات التالية:
- أنشئ قائمة بالكائنات لتمثيل نقاط الاهتمام في منطقة "سيدني"، وضَعها أسفل عمليات الاستيراد مباشرةً، خارج تعريف
App
:
type Poi ={ key: string, location: google.maps.LatLngLiteral }
const locations: Poi[] = [
{key: 'operaHouse', location: { lat: -33.8567844, lng: 151.213108 }},
{key: 'tarongaZoo', location: { lat: -33.8472767, lng: 151.2188164 }},
{key: 'manlyBeach', location: { lat: -33.8209738, lng: 151.2563253 }},
{key: 'hyderPark', location: { lat: -33.8690081, lng: 151.2052393 }},
{key: 'theRocks', location: { lat: -33.8587568, lng: 151.2058246 }},
{key: 'circularQuay', location: { lat: -33.858761, lng: 151.2055688 }},
{key: 'harbourBridge', location: { lat: -33.852228, lng: 151.2038374 }},
{key: 'kingsCross', location: { lat: -33.8737375, lng: 151.222569 }},
{key: 'botanicGardens', location: { lat: -33.864167, lng: 151.216387 }},
{key: 'museumOfSydney', location: { lat: -33.8636005, lng: 151.2092542 }},
{key: 'maritimeMuseum', location: { lat: -33.869395, lng: 151.198648 }},
{key: 'kingStreetWharf', location: { lat: -33.8665445, lng: 151.1989808 }},
{key: 'aquarium', location: { lat: -33.869627, lng: 151.202146 }},
{key: 'darlingHarbour', location: { lat: -33.87488, lng: 151.1987113 }},
{key: 'barangaroo', location: { lat: - 33.8605523, lng: 151.1972205 }},
];
const App = () => (
...
);
- يمكنك تخصيص الدبابيس باستخدام العنصر
<Pin>
باتّباع الخطوات التالية:
<Pin background={'#FBBC04'} glyphColor={'#000'} borderColor={'#000'} />
- أنشئ مكوّنًا مخصّصًا لعرض قائمتك باستخدام "علامات متقدّمة"، وضَع هذا المكوّن أسفل تعريف
App
:
const App = () => (
...
);
const PoiMarkers = (props: {pois: Poi[]}) => {
return (
<>
{props.pois.map( (poi: Poi) => (
<AdvancedMarker
key={poi.key}
position={poi.location}>
<Pin background={'#FBBC04'} glyphColor={'#000'} borderColor={'#000'} />
</AdvancedMarker>
))}
</>
);
};
- أضِف المكوّن
PoiMarkers
كعنصر ثانوي للمكوّنMap
:
<Map
... map properties ...
>
<PoiMarkers pois={locations} />
</Map>
- أخيرًا، أضِف
Pin
وAdvancedMarker
إلى عمليات الاستيراد.
import {
APIProvider,
Map,
AdvancedMarker,
MapCameraChangedEvent,
Pin
} from '@vis.gl/react-google-maps';
من المفترض أن تظهر لك "علامات متقدمة" مخصّصة على الخريطة:
7. تفعيل تجميع العلامات
عند استخدام الكثير من العلامات أو العلامات التي تقع بالقرب من بعضها البعض، قد تواجه مشكلة تتداخل فيها العلامات أو تظهر بشكل مزدحم جدًا، ما يؤدي إلى تجربة مستخدم سيئة. على سبيل المثال، بعد إنشاء العلامات في الخطوة الأخيرة، ربما لاحظت ما يلي:
وهنا يأتي دور تجميع العلامات. تجميع العلامات هو ميزة أخرى يتم تنفيذها بشكل شائع، وهي تعمل على تجميع العلامات القريبة في رمز واحد يتغيّر حسب مستوى التكبير/التصغير، كما يلي:
تقسّم خوارزمية تجميع العلامات المنطقة المرئية من الخريطة إلى شبكة، ثم تجمع الرموز التي تقع في الخلية نفسها. لحسن الحظ، لا داعي للقلق بشأن أي من ذلك لأنّ فريق Google Maps Platform أنشأ مكتبة أدوات مساعدة مفيدة ومفتوحة المصدر باسم MarkerClustererPlus
تنفّذ كل ذلك تلقائيًا. يمكنك الاطّلاع على رمز المصدر لمكتبة MarkerClustererPlus
على GitHub.
لتفعيل تجميع العلامات، اتّبِع الخطوات التالية:
- في أعلى ملف
app.tsx
، لنعدّل ونضيف إلى عمليات استيراد المكتبة والأنواع المتوافقة.
import React, {useEffect, useState, useRef, useCallback} from 'react';
import {createRoot} from "react-dom/client";
import {
APIProvider,
Map,
AdvancedMarker,
MapCameraChangedEvent,
useMap,
Pin
} from '@vis.gl/react-google-maps';
import {MarkerClusterer} from '@googlemaps/markerclusterer';
import type {Marker} from '@googlemaps/markerclusterer';
بالنسبة إلى مشروع النموذج لهذا الدرس البرمجي، تم تضمين مكتبة الأداة MarkerClustererPlus
في التبعيات المحدّدة في ملف package.json
، لذا سبق لك تثبيتها عند تنفيذ npm install
في بداية هذا الدرس البرمجي.
- أنشئ متغيرات لعنصر
MarkerClusterer
والعناصر الداعمة في مكوّنPoiMarkers
.
تحتاج إلى نسخة من الخريطة لإعداد MarkerClusterer
. احصل على هذا المثال من خطاف useMap()
:
const map = useMap();
- إنشاء قائمة بالعلامات المخزّنة في متغيّر حالة:
const [markers, setMarkers] = useState<{[key: string]: Marker}>({});
- تخزين أداة التجميع كمرجع:
const clusterer = useRef<MarkerClusterer | null>(null);
- في مكوّن
PoiMarkers
أيضًا، أنشئ مثيلاً منMarkerClusterer
ومرِّر إليه مثيلMap
حيث تريد عرض مجموعات العلامات:
useEffect(() => {
if (!map) return;
if (!clusterer.current) {
clusterer.current = new MarkerClusterer({map});
}
}, [map]);
- أنشئ تأثيرًا يعدّل أداة التجميع عند تغيير قائمة العلامات:
useEffect(() => {
clusterer.current?.clearMarkers();
clusterer.current?.addMarkers(Object.values(markers));
}, [markers]);
- أنشئ دالة لإنشاء مراجع للعلامات الجديدة:
const setMarkerRef = (marker: Marker | null, key: string) => {
if (marker && markers[key]) return;
if (!marker && !markers[key]) return;
setMarkers(prev => {
if (marker) {
return {...prev, [key]: marker};
} else {
const newMarkers = {...prev};
delete newMarkers[key];
return newMarkers;
}
});
};
- استخدِم هذه الطريقة في العنصر
AdvancedMarker
لإنشاء مرجع لكل علامة.
<AdvancedMarker
key={poi.key}
position={poi.location}
ref={marker => setMarkerRef(marker, poi.key)}
>
<Pin background={'#FBBC04'} glyphColor={'#000'} borderColor={'#000'} />
</AdvancedMarker>
من المفترض أن تظهر لك الآن مجموعات من العلامات على خريطتك:
إذا كبّرت وصغّرت، ستعيد MarkerClustererPlus
تلقائيًا ترقيم المجموعات وتغيير حجمها. يمكنك أيضًا النقر على أي رمز لمجموعة من العلامات لتكبير الخريطة والاطّلاع على جميع العلامات المضمّنة في تلك المجموعة.
باختصار، في هذا القسم، استوردت مكتبة الأدوات المساعدة MarkerClustererPlus
المفتوحة المصدر واستخدمتها لإنشاء مثيل من MarkerClusterer
، والذي عمل، بمساعدة حالة React والمراجع، على تجميع العلامات التي أنشأتها في الخطوة السابقة تلقائيًا.
يجب أن يبدو مكوّن PoiMarkers
على النحو التالي:
const PoiMarkers = (props: { pois: Poi[] }) => {
const map = useMap();
const [markers, setMarkers] = useState<{[key: string]: Marker}>({});
const clusterer = useRef<MarkerClusterer | null>(null);
// Initialize MarkerClusterer, if the map has changed
useEffect(() => {
if (!map) return;
if (!clusterer.current) {
clusterer.current = new MarkerClusterer({map});
}
}, [map]);
// Update markers, if the markers array has changed
useEffect(() => {
clusterer.current?.clearMarkers();
clusterer.current?.addMarkers(Object.values(markers));
}, [markers]);
const setMarkerRef = (marker: Marker | null, key: string) => {
if (marker && markers[key]) return;
if (!marker && !markers[key]) return;
setMarkers(prev => {
if (marker) {
return {...prev, [key]: marker};
} else {
const newMarkers = {...prev};
delete newMarkers[key];
return newMarkers;
}
});
};
return (
<>
{props.pois.map( (poi: Poi) => (
<AdvancedMarker
key={poi.key}
position={poi.location}
ref={marker => setMarkerRef(marker, poi.key)}
>
<Pin background={'#FBBC04'} glyphColor={'#000'} borderColor={'#000'} />
</AdvancedMarker>
))}
</>
);
};
بعد ذلك، ستتعرّف على كيفية التعامل مع تفاعل المستخدمين.
8. إضافة تفاعل المستخدم
أصبحت لديك الآن خريطة رائعة المظهر تعرض بعض الوجهات السياحية الأكثر رواجًا في سيدني. في هذا القسم، ستضيف بعض الإجراءات الإضافية للتعامل مع تفاعلات المستخدمين مع نظام الأحداث في Maps JavaScript API من أجل تحسين تجربة المستخدم في الخريطة.
توفّر Maps JavaScript API نظام أحداث شاملاً يستخدم معالجات أحداث JavaScript للسماح لك بالتعامل مع تفاعلات المستخدمين المختلفة في الرمز. على سبيل المثال، يمكنك إنشاء أدوات معالجة الأحداث لتفعيل تنفيذ الرمز البرمجي للتفاعلات، مثل نقر المستخدم على الخريطة والعلامات، وتحريك عرض الخريطة، والتكبير والتصغير، وغير ذلك.
لإضافة أداة معالجة click
إلى العلامات، ثمّ تحريك الخريطة آليًا ليظهر العلامة التي تم النقر عليها في وسط الخريطة، اتّبِع الخطوات التالية:
- أنشِئ دالة ردّ اتصال لمعالج
click
.
في المكوّن PoiMarkers
، حدِّد معالج click
باستخدام useCallback()
في React.
يتم تشغيل الحدث click
عندما ينقر المستخدم على علامة أو يلمسها، ويعرض الحدث كعنصر JSON يتضمّن معلومات عن عنصر واجهة المستخدم الذي تم النقر عليه. لتحسين تجربة المستخدم على الخريطة، يمكنك التعامل مع الحدث click
واستخدام العنصر LatLng
الخاص به للحصول على خطوط الطول والعرض للعلامة التي تم النقر عليها.
بعد الحصول على خطوط الطول والعرض، مرِّرها إلى الدالة panTo()
المضمّنة في مثيل Map
لكي يتم تحريك الخريطة بسلاسة لإعادة توسيطها على العلامة التي تم النقر عليها من خلال إضافة ما يلي في دالة رد الاتصال لمعالج الحدث:
const PoiMarkers = (props: { pois: Poi[] }) => {
...
const handleClick = useCallback((ev: google.maps.MapMouseEvent) => {
if(!map) return;
if(!ev.latLng) return;
console.log('marker clicked:', ev.latLng.toString());
map.panTo(ev.latLng);
});
...
};
- عيِّن معالِجات
click
للعلامات.
تعرض عناصر AdvancedMarker
في مكتبة vis.gl/react-google-map
سمتَين مفيدتَين للتعامل مع النقرات:
clickable
: إذا كانت القيمة صحيحة، سيكونAdvancedMarker
قابلاً للنقر وسيؤدي إلى تشغيل الحدثgmp-click
، وسيكون تفاعليًا لأغراض تسهيل الاستخدام. على سبيل المثال، ستتيح التنقّل باستخدام لوحة المفاتيح ومفاتيح الأسهم.-
onClick
: دالّة ردّ الاتصال التي سيتم استدعاؤها عند وقوع حدثclick
.
- عدِّل عملية العرض
PoiMarkers
لتعيين معالجclick
لكل علامة:
return (
<>
{props.pois.map( (poi: Poi) => (
<AdvancedMarker
... other properties ...
clickable={true}
onClick={handleClick}
>
...
</AdvancedMarker>
))}
</>
);
- انتقِل إلى المتصفّح وانقر على العلامات. من المفترض أن يتم تحريك الخريطة تلقائيًا لإعادة توسيطها عند النقر على محدّد.
باختصار، في هذا القسم، استخدمت نظام الأحداث في React لتعيين معالج click
لجميع العلامات على الخريطة، واسترددت خطوط الطول والعرض للعلامة من حدث click
الذي تم تنشيطه، واستخدمت ذلك لإعادة توسيط الخريطة كلما تم النقر على علامة.
يتبقّى لك خطوة واحدة فقط. بعد ذلك، يمكنك تحسين تجربة المستخدم على الخريطة بشكل أكبر باستخدام ميزات الرسم في Maps JavaScript API.
9- الرسم على الخريطة
حتى الآن، أنشأت خريطة لمدينة سيدني تعرض علامات للوجهات السياحية الشهيرة وتتعامل مع تفاعل المستخدم. في الخطوة الأخيرة من هذا الدرس التطبيقي، ستستخدم ميزات الرسم في Maps JavaScript API لإضافة ميزة مفيدة أخرى إلى تجربة الخريطة.
لنفترض أنّ هذه الخريطة سيستخدمها أشخاص يريدون استكشاف مدينة سيدني. من الميزات المفيدة أن يتم عرض دائرة نصف قطر حول علامة عند النقر عليها. سيسمح ذلك للمستخدم بمعرفة الوجهات الأخرى التي يمكن الوصول إليها سيرًا على الأقدام من العلامة التي تم النقر عليها.
تتضمّن Maps JavaScript API مجموعة من الدوال لرسم الأشكال على الخريطة، مثل المربّعات والمضلّعات والخطوط والدوائر. تتيح لك مكتبة vis.gl/react-google-map
إمكانية استخدام هذه الميزات في React.
بعد ذلك، يمكنك عرض دائرة لتوضيح نطاق جغرافي يبلغ 800 متر (حوالي نصف ميل) حول علامة عند النقر عليها.
يحتوي مستودع الرموز البرمجية المبدئية على مكوّن مخصّص لعنصر circle
. يمكنك العثور عليه في ملف src/components/circle.tsx
.
للسماح للمستخدمين بالرسم على الخريطة، اتّبِع الخطوات التالية:
- عدِّل عمليات الاستيراد لتضمين مكوّن الدائرة المقدَّم.
import {Circle} from './components/circle'
- أنشئ متغيّر حالة لمركز الدائرة.
التقط حالة مركز الدائرة في مكوّن PoiMarkers
. يمكنك ضبط الحالة الأولية على القيمة null، والاستفادة من حقيقة أنّه لن يتم عرض دائرة ما لم يكن لديها موقع جغرافي صالح في المركز (ونصف قطر).
const PoiMarkers = (props: { pois: Poi[] }) => {
...
const [circleCenter, setCircleCenter] = useState(null)
...
};
- تعديل مركز الدائرة عند معالجة حدث
click
استدعِ الدالة setCircleCenter
مع الموقع الجغرافي الذي تم العثور عليه في عنصر الحدث:
const handleClick = useCallback((ev: google.maps.MapMouseEvent) => {
...
setCircleCenter(ev.latLng);
});
تمنحك دوال الرسم في Maps JavaScript API مجموعة كبيرة من الخيارات حول كيفية ظهور عنصر مرسوم على الخريطة. لعرض نصف قطر دائري، اضبط خصائص عنصر الدائرة، مثل اللون ووزن الحد، ومكان توسيط الدائرة ونصف قطرها.
- أضِف دائرة إلى عملية العرض واربط مركزها بمتغيّر الحالة. يجب أن يبدو العرض على النحو التالي:
return (
<>
<Circle
radius={800}
center={circleCenter}
strokeColor={'#0c4cb3'}
strokeOpacity={1}
strokeWeight={3}
fillColor={'#3b82f6'}
fillOpacity={0.3}
/>
{props.pois.map( (poi: Poi) => (
<AdvancedMarker
key={poi.key}
position={poi.location}
ref={marker => setMarkerRef(marker, poi.key)}
clickable={true}
onClick={handleClick}
>
<Pin background={'#FBBC04'} glyphColor={'#000'} borderColor={'#000'} />
</AdvancedMarker>
))}
</>
);
};
أكملت الخطوات بنجاح انتقِل إلى المتصفّح وانقر على أحد العلامات. من المفترض أن يظهر نصف قطر دائري حوله:
10. تهانينا
لقد أنشأت تطبيق الويب الأول باستخدام مكتبة vis.gl/react-google-map
لمنصة "خرائط Google"، بما في ذلك تحميل Maps JavaScript API، وتحميل خريطة، والعمل مع العلامات، والتحكّم في الخريطة والرسم عليها، وإضافة تفاعل المستخدم.
للاطّلاع على الرمز البرمجي المكتمل، راجِع الدليل /solutions
.