מפות צפיפות

בחירת פלטפורמה: Android iOS JavaScript

בדף הזה מתואר כלי המפה התרמית שזמין בספריית כלי השירות של Maps SDK ל-iOS. מפות חום שימושיות להצגת ההתפלגות והצפיפות של נקודות נתונים במפה.

בסרטון הזה מוסבר איך להשתמש במפות חום כחלופה לסמנים, כשצריך להציג במפה מספר גדול של נקודות נתונים.

מפות צפיפות מאפשרות לצופים להבין בקלות את ההתפלגות והעוצמה היחסית של נקודות הנתונים במפה. במקום להציב סמן בכל מיקום, במפות חום משתמשים בצבע כדי לייצג את התפלגות הנתונים.

בדוגמה שלמטה, הצבע האדום מייצג אזורים עם ריכוז גבוה של תחנות משטרה בוויקטוריה, אוסטרליה.

מפה עם מפת חום שמציגה את המיקום של תחנות משטרה
מפת חום במפה

אם עדיין לא הגדרתם את הספרייה, כדאי לעיין במדריך ההגדרה לפני שתמשיכו לקרוא את שאר המאמר.

הוספת מפת חום פשוטה

כדי להוסיף מפת חום למפה, צריך להשתמש במערך נתונים שכולל את הקואורדינטות של כל מיקום שמעניין אתכם. קודם כול יוצרים מופע GMUHeatmapTileLayer ומגדירים את המאפיין map לערך GMSMapView. כדי לוודא שמפת הבסיס נטענת לפני שמשתמשים במפת החום, צריך לעשות את זה בפונקציה viewDidLoad() של האפליקציה. לאחר מכן מעבירים אוסף של אובייקטים GMUWeightedLatLng למופע GMUHeatmapTileLayer.

כלי השירות מספק את המחלקה GMUHeatmapTileLayer, שמקבלת אוסף של אובייקטים מסוג GMUWeightedLatLng. הוא יוצר את תמונות המשבצות לרמות שונות של זום, על סמך אפשרויות הרדיוס, הגרדיאנט והאטימות שצוינו.

הסבר מפורט יותר על השלבים:

  1. יוצרים מופע GMUHeatmapTileLayer ומגדירים את המאפיין map לערך GMSMapView (צריך לעשות את זה בפונקציה viewDidLoad() של האפליקציה).
  2. מעבירים אוסף של אובייקטים מסוג GMUWeightedLatLng למופע GMUHeatmapTileLayer.
  3. קוראים לפונקציה GMUHeatmapTileLayer.map ומעבירים את תצוגת המפה.

    Swift

    class Heatmap: UIViewController {
    
      private var mapView: GMSMapView!
      private var heatmapLayer: GMUHeatmapTileLayer!
    
      override func viewDidLoad() {
        super.viewDidLoad()
        heatmapLayer = GMUHeatmapTileLayer()
        heatmapLayer.map = mapView
      }
    
      // ...
    
      func addHeatmap() {
    
        // Get the data: latitude/longitude positions of police stations.
        guard let path = Bundle.main.url(forResource: "police_stations", withExtension: "json") else {
          return
        }
        guard let data = try? Data(contentsOf: path) else {
          return
        }
        guard let json = try? JSONSerialization.jsonObject(with: data, options: []) else {
          return
        }
        guard let object = json as? [[String: Any]] else {
          print("Could not read the JSON.")
          return
        }
    
        var list = [GMUWeightedLatLng]()
        for item in object {
          let lat = item["lat"] as! CLLocationDegrees
          let lng = item["lng"] as! CLLocationDegrees
          let coords = GMUWeightedLatLng(
            coordinate: CLLocationCoordinate2DMake(lat, lng),
            intensity: 1.0
          )
          list.append(coords)
        }
    
        // Add the latlngs to the heatmap layer.
        heatmapLayer.weightedData = list
      }
    }
          

    Objective-C

    @implementation Heatmap {
      GMSMapView *_mapView;
      GMUHeatmapTileLayer *_heatmapLayer;
    }
    
    - (void)viewDidLoad {
      [super viewDidLoad];
      _heatmapLayer = [[GMUHeatmapTileLayer alloc] init];
      _heatmapLayer.map = _mapView;
    }
    
    // ...
    
    - (void) addHeatmap {
    
      // Get the data: latitude/longitude positions of police stations.
      NSURL *path = [NSBundle.mainBundle URLForResource:@"police_stations" withExtension:@"json"];
      NSData *data = [NSData dataWithContentsOfURL:path];
      NSArray *json = [NSJSONSerialization JSONObjectWithData:data options:0 error:nil];
    
      NSMutableArray<GMUWeightedLatLng *> *list = [[NSMutableArray alloc] init];
      [json enumerateObjectsUsingBlock:^(id  _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) {
        NSDictionary *item = (NSDictionary *)obj;
        CLLocationDegrees lat = [(NSNumber *) [item valueForKey:@"lat"] doubleValue];
        CLLocationDegrees lng = [(NSNumber *) [item valueForKey:@"lng"] doubleValue];
        GMUWeightedLatLng *coords = [[GMUWeightedLatLng alloc] initWithCoordinate:CLLocationCoordinate2DMake(lat, lng)
                                                                        intensity:1.0];
        [list addObject:coords];
      }];
    
    
      // Add the latlngs to the heatmap layer.
      _heatmapLayer.weightedData = list;
    }
    @end
          

בדוגמה הזו, הנתונים מאוחסנים בקובץ JSON, ‏ police_stations.json. הנה קטע מהקובץ:

[
{"lat" : -37.1886, "lng" : 145.708 } ,
{"lat" : -37.8361, "lng" : 144.845 } ,
{"lat" : -38.4034, "lng" : 144.192 } ,
{"lat" : -38.7597, "lng" : 143.67 } ,
{"lat" : -36.9672, "lng" : 141.083 }
]

התאמה אישית של מפת החום

למפת החום יש כמה מאפיינים שאפשר להתאים אישית. אפשר להגדיר את האפשרויות כשיוצרים את מופע GMUHeatmapTileLayer, או בכל שלב אחר על ידי הגדרת ערך חדש לאפשרות.

אלה האפשרויות הזמינות:

  1. רדיוס: הגודל של הטשטוש הגאוסיאני שמוחל על מפת החום, בפיקסלים. ברירת המחדל היא 20. הערך חייב להיות בין 10 ל-50. משתמשים בGMUHeatmapTileLayer.radius כדי להגדיר את הרדיוס.

  2. מעבר צבעים: טווח של צבעים שמשמשים במפת החום ליצירת מפת הצבעים, מדרגת העוצמה הנמוכה ביותר ועד הגבוהה ביותר. יוצרים GMUGradient באמצעות מערך של מספרים שלמים שמכיל את הצבעים, ומערך של מספרים עשרוניים שמציין את נקודת ההתחלה של כל צבע, שמוצגת כאחוז מהעוצמה המקסימלית ומבוטאת כשבר בין 0 ל-1. צריך לציין רק צבע אחד למעבר צבעים חד-צבעי, או לפחות שני צבעים למעבר צבעים רב-צבעי. מפת הצבעים נוצרת באמצעות אינטרפולציה בין הצבעים האלה. השיפוע שמוגדר כברירת מחדל כולל שני צבעים. הפרמטר colorMapSize מגדיר את מספר השלבים במעבר הצבעים. מספרים גדולים יותר יניבו מעבר חלק יותר בין הצבעים, ומספרים קטנים יותר יניבו מעברים חדים יותר, בדומה לתרשים קונטור. משתמשים ב-GMUHeatmapTileLayer.gradient כדי להגדיר את המעבר ההדרגתי.

  3. אטימות: האטימות של שכבת מפת החום כולה, בטווח שבין 0 ל-1. ערך ברירת המחדל הוא 0.7. משתמשים בערך GMUHeatmapTileLayer.opacity כדי להגדיר את ערך השקיפות.

לדוגמה, יצירת Gradient:

Swift

let gradientColors: [UIColor] = [.green, .red]
let gradientStartPoints: [NSNumber] = [0.2, 1.0]
heatmapLayer.gradient = GMUGradient(
  colors: gradientColors,
  startPoints: gradientStartPoints,
  colorMapSize: 256
)
      

Objective-C

NSArray<UIColor *> *gradientColors = @[UIColor.greenColor, UIColor.redColor];
NSArray<NSNumber *> *gradientStartPoints = @[@0.2, @1.0];
_heatmapLayer.gradient = [[GMUGradient alloc] initWithColors:gradientColors
                                                 startPoints:gradientStartPoints
                                                colorMapSize:256];
      

כדי לשנות את רמת השקיפות של מפת חום קיימת:

Swift

heatmapLayer.opacity = 0.7
      

Objective-C

_heatmapLayer.opacity = 0.7;
      

עדכון של אפשרות קיימת

כדי לעדכן אפשרות שכבר הוגדרה, פועלים לפי השלבים הבאים:

  1. מעדכנים את האפשרות לערך הרצוי.
  2. התקשרו אל GMUHeatmapTileLayer.clearTileCache().

שינוי מערך הנתונים

כדי לשנות את מערך הנתונים שעליו מבוססת מפת החום:

  1. עדכון של איסוף הנתונים. משתמשים ב-GMUHeatmapTileLayer.weightedData ומעבירים מערך של GMUWeightedLatLng.
  2. התקשרו אל GMUHeatmapTileLayer.clearTileCache().

הסרת מפת חום

כדי להסיר מפת חום, קוראים ל-GMUHeatmapTileLayer.map ומעבירים את nil.

Swift

heatmapLayer.map = nil
      

Objective-C

_heatmapLayer.map = nil;
      

לצפייה באפליקציית ההדגמה

דוגמה נוספת להטמעה של מפת חום מופיעה ב-HeatmapViewController באפליקציית ההדגמה שמגיעה עם ספריית כלי העזר. במדריך ההגדרה מוסבר איך להפעיל את אפליקציית ההדגמה.