במדריך הזה נסביר בפירוט על רכיבי האינטרנט של מפות Google בתלת-ממד, ועל השיקולים שצריך להביא בחשבון כשמשלבים אותם באפליקציה.
שיקולי ביצועים
כדי להבטיח חוויית שימוש חלקה ורספונסיבית מבחינת אינטראקטיביות ואלמנטים חזותיים, כדאי לשקול את הגישות הבאות.
טעינת המפה
ההגדרה הראשונית של הטעינה והרינדור של מפות תלת-ממדיות משלבת שיטות להגדרת הדפדפן ושיטות מומלצות לממשק המשתמש, כדי לספק חוויית משתמש אופטימלית.
- טעינת API: משתמשים בטעינה דינמית אסינכרונית של מפות תלת-ממדיות כדי לטעון את Maps JavaScript API בטעינת הדף הראשונית.
- Libraries: טעינת ספריות באופן פרוגרמטי במקומות שבהם הן נדרשות, כמו
google.maps.importLibrary("maps3d"). לחלופין, אם אתם משתמשים ברכיבי אינטרנט כמו<gmp-map-3d>ישירות בדף ה-HTML עם טעינת סקריפט ישירה, הספריות ייטענו באופן אוטומטי בזמן המתאים. - ניהול התכונות של מפת הבסיס: אפשר להשתמש במזהה מפה מותאם אישית כדי לסנן נקודות עניין במפת הבסיס (מצב HYBRID), ולשלוט בצפיפות שלהן, במיוחד אם לאפליקציה יש קבוצה משלה של רכיבים בהתאמה אישית כמו סמנים או קווים פוליגוניים. כך נמנעים עומס חזותי וחפיפה אפשרית. לחלופין, אתם יכולים להשבית תכונות של אריחים וקטוריים במפת הבסיס, כמו נקודות עניין, קווים פוליגוניים של כבישים, שמות של כבישים ושמות של רחובות (מצב SATELLITE).
- אירועים: האזנה לאירועים gmp-steadystate או gmp-error כדי ליצור את הלוגיקה הבאה, כמו טעינת סמנים או הנפשה של המצלמה.
אינטראקציה עם המשתמש: צריך להמתין לאירוע gmp-steadystate לפני שמבצעים שינויים בתוכן של המפה. אם משתמש מתחיל לבצע פעולות במפה (הזזה, שינוי מרחק התצוגה) לפני האירוע הראשוני gmp-steadystate, האירוע יופעל רק אחרי שהמשתמש יפסיק לבצע פעולות. כדי להימנע מהצגה או מעדכון של תוכן שכבת-על (כמו סמנים או פוליגונים) בזמן שהמשתמש מזיז את המפה או משנה את מרחק התצוגה, צריך להאזין לאירועים הבאים: gmp-centerchange, gmp-headingchange gmp-rangechange gmp-rollchange gmp-tiltchange.
השתמשו ב-
requestAnimationFrame()(rAF) לעדכונים רציפים, והפרידו באופן מוחלט בין חישובים אינטנסיביים לבין בקשות להזזת פריטים גרפיים.- שימוש ב-rAF: סנכרון העדכונים עם קצב התצוגה של הדפדפן כדי לקבל אנימציה חלקה של 60FPS וצריכת חשמל מופחתת.
- הימנעו מפעולות שרטוט אינטנסיביות: אל תבצעו משימות כבדות שלא קשורות לשרטוט במהלך העדכון הסופי.
- לוגיקה נפרדת: מבצעים את כל הלוגיקה האינטנסיבית לפני קריאות מינימליות לעדכון רכיבי אינטרנט בתוך הלולאה של rAF.
הגדרות הסצנה הראשוניות:
<gmp-map-3d>הגדרות המצלמה, כמו הטיה, ישפיעו על מהירות הטעינה. ככל שמגדילים את התצוגה או מטים את הסצנה, כך מוצגים יותר פוליגונים מפורטים שצריך לטעון. רמת הפירוט תלויה גם במיקום (למשל: עיר עם הרבה בניינים לעומת אזור כפרי עם מאפיינים טבעיים בלבד).רכיב חזותי לטעינה מראש: למרות ש-
<gmp-map-3d>נטען מהר מאוד, יכול להיות שייקח קצת זמן עד שהוא יוצג ברזולוציה מלאה למשתמשים עם מכשירים פשוטים (GPU נמוך) או רוחב פס נמוך (4G איטי). במקרה כזה, אפשר ליצור מסך טעינה עם תמונה, אנימציה או טקסט, בזמן שסצנת התלת-ממד נטענת ברקע. בהמשך מפורטים האירועים המרכזיים שאפשר להשתמש בהם:
// create the map in the background and wait for gmp-steadystate event async function initMap() { await google.maps.importLibrary("maps3d"); const map = document.querySelector('gmp-map-3d'); const div = document.querySelector('div'); // preloader " map.addEventListener('gmp-steadystate', ({isSteady}) => { if (isSteady) { div.style.display = 'none'; } }); } initMap();
- מפה דו-ממדית:
- אפשר להציג למשתמשים האלה מפה דו-ממדית חלופית (SATELLITE) שעדיין כוללת את הנתונים הגיאוגרפיים שלכם, כמו סמנים.
- לחלופין, אפשר להציג למשתמשים מפה סטטית דו-ממדית משלימה במצב SATELLITE כדי להמחיש מקום מסוים בזמן הטעינה.
ניהול וביצועים של רכיבים חזותיים
במפות תלת-ממדיות יש כמה דרכים להציג רכיבים חזותיים כמו סמנים, קווים פוליגוניים ומודלים תלת-ממדיים, עם ביצועים אופטימליים וזמן עיבוד מינימלי, גם כשמדובר ברכיבים חזותיים בנפח גדול יותר.
סמנים
- אפשרות אופטימלית להתאמה אישית:
- PinElement: כדי לבצע שינויים בסיסיים בסמן (צבע, קנה מידה, גבול, גליף טקסט), משתמשים ברכיב
<gmp-pin>או במחלקהPinElement. זו השיטה הכי יעילה להתאמה אישית. - שימוש בסמנים מסוג HTMLImageElement או SVGElement רק כשצריך: אפשר להשתמש בהם כדי להוסיף עוד התאמות אישיות, כמו הוספת שקיפות או הזרקת תמונה כמו סמל ל-SVGElement (נדרש קידוד base64). הם יעברו רסטריזציה בזמן הטעינה, וזה יגרום לעומס על הביצועים. צריך לעטוף את HTMLImageElement ו-SVGElement ברכיב
<template>לפני שמקצים אותם למשבצת ברירת המחדל של Marker3DElement. - בשלב הזה אי אפשר להוסיף HTML או CSS פשוטים.
- PinElement: כדי לבצע שינויים בסיסיים בסמן (צבע, קנה מידה, גבול, גליף טקסט), משתמשים ברכיב
- ניהול ההתנהגות במקרה של חפיפה: משתמשים במאפיין collisionBehavior של הסמן. אם יש סמנים קריטיים שחייבים להיות גלויים תמיד, צריך להגדיר את ההתנהגות בהתאם. סמנים פחות חשובים אפשר להסתיר כדי שהמפה תהיה נקייה ופחות עמוסה, במיוחד ברמות זום גבוהות.
- רק נקודות עניין קריטיות: השתמשו ב-drawsWhenOccluded (או הגדירו את המאפיין באופן פרוגרמטי) רק לסמנים שחייבים לראות דרך מבנים או פני שטח (למשל, יעד חילוץ, קו תשתית קבור או דמות של משתמש).
- בדיקת הסתרה: מכיוון שהמפה היא בתלת-ממד, בניינים או פני השטח יכולים להסתיר את הסמנים. כדאי לבדוק זוויות מצלמה וגבהים שונים של סמנים כדי לוודא שנקודות עניין חשובות נשארות גלויות, או להטמיע לוגיקה להתאמת החשיפה והגובה כשהן מוסתרות.
- שימוש בגובה: במפות תלת-ממדיות, הסמנים צריכים להשתמש במיקום עם ערך גובה. כדי להצמיד סמנים לשטח או למבנים, צריך להשתמש בהגדרות כמו altitudeMode: 'RELATIVE_TO_GROUND', 'RELATIVE_TO_MESH' או הגדרות דומות, כדי לוודא שהסמן מוצמד בצורה נכונה כשמטים או מסובבים את המפה.
פוליגונים וקווים פוליגוניים
- פישוט הגיאומטריה: לפני הרינדור, מפעילים אלגוריתם פישוט על נתוני הנתיב. כך אפשר להפחית את מספר הקודקודים תוך שמירה על הצורה הכללית, ולשפר באופן משמעותי את מהירות הרינדור, במיוחד כשמדובר בגבולות או במסלולים מורכבים.
- הפחתת נתונים לפי רמת זום: בקבוצות נתונים גדולות מאוד, כדאי לטעון גיאומטריה מפורטת יותר רק כשהמשתמש מגדיל את התצוגה של האזור. ברמת זום נמוכה, צריך רק גרסה פשוטה מאוד של הקו הפוליגוני או הפוליגון.
- חישוב מראש של פוליגונים מובלטים: אם הפוליגונים מובלטים (
extruded: true), נתוני הנתיב מגדירים נפח תלת-ממדי (רשת). עיבוד של פוליגונים מורכבים עם הרבה קודקודים דורש משאבי מחשוב רבים. חשוב לוודא שנתוני המקור של הפוליגונים פשוטים ככל האפשר. - בדיקת הביצועים של קווים פוליגוניים ופוליגונים: כשמוסיפים הרבה קווים פוליגוניים או פוליגונים, או קווים פוליגוניים או פוליגונים מורכבים, במיוחד כשמחלצים אותם לתלת-ממד, חשוב לוודא שהם לא גורמים לירידה בקצב הפריימים. אם צריך, הגבילו את מספר הקודקודים או השתמשו באלגוריתמים לפישוט.
- כשמעדכנים צורה, משנים את כל מערך הנתיבים בפעולה אחת, במקום ליצור לולאה ולשנות רכיבים בודדים. פעולת הקצאה אחת (למשל, polyline.path = newPathArray;) יעילה הרבה יותר מכמה עדכונים חוזרים.
- הימנעו מקווים פוליגוניים מובלטים (ככל האפשר): אפשר להשתמש בערך גובה כדי למקם קווים פוליגוניים במרחב תלת-ממדי, אבל הבלטה של קו פוליגוני (למשל, הגדרה של רוחב קו וטווח גובה גדול) יכולה להיות אינטנסיבית מבחינה גרפית. כדי לשפר את הביצועים, כדאי להשתמש בקווים פוליגוניים דו-ממדיים על הקרקע (RELATIVE_TO_GROUND) או ברוחב קו מינימלי.
- השתמשו ב-drawsOccludedSegments רק לרכיבי ניתוב קריטיים. אם אתם משתמשים בצורות רקע או בצורות הקשריות, אפשרו להן להיות מוסתרות באופן טבעי על ידי הגיאומטריה התלת-ממדית של המפה. הצגת גיאומטריה מוסתרת לא קריטית מוסיפה מורכבות מיותרת לעיבוד.
מודלים תלת-ממדיים
העיבוד והאינטראקטיביות של מודל תלת-ממדי בפורמט .glb, כמו אירוע מסוג קליק של gmp, מהירים מאוד ב-<gmp-map-3d>.
- הקטנת גודל הקובץ באמצעות דחיסה: כדי להבטיח טעינה מהירה, במיוחד ברשתות סלולריות, מומלץ שקבצי מודלים מורכבים בפורמט .glb יהיו קטנים מ-5MB (רצוי אפילו פחות). השיטה העיקרית לעשות את זה היא להחיל דחיסת Draco על נתוני הרשת בקובצי ה-.glb, מה שיכול להקטין משמעותית את גודל הקובץ (לרוב ביותר מ-50%) עם פגיעה מינימלית באיכות הוויזואלית.
- מרכז נקודת המוצא של המודל: ודאו שתוכנת המידול בתלת-ממד מייצאת את המודל כשנקודת המוצא שלו (נקודת 0, 0, 0) ממוקמת במרכז בסיס המודל. כך קל יותר למקם ולסובב את המודל במפה, ולוודא שהוא מעוגן בצורה נכונה לקואורדינטות של קו הרוחב וקו האורך.
- ניהול CORS: אם קובצי המודל מתארחים בדומיין או ב-CDN שונים מאפליקציית האינטרנט, צריך להגדיר את שרת האירוח כך שיכלול את הכותרות הנדרשות של שיתוף משאבים בין מקורות (CORS) (למשל, Access-Control-Allow-Origin: *). אחרת, המפה לא תוכל לטעון את המודל.