מעקב אחרי מצב המכשיר ב-iOS

בממשקי ה-API של Home ל-iOS, אפשר לעקוב אחרי שינויים במצב בבית באמצעות מסגרת Combine ב-Swift. אפשר לעקוב אחרי שינויים במבנים, בחדרים, במטא-נתונים של המכשירים ובמצב המכשיר באמצעות כל API שמשתמש ב-HomeDevice. הפעולה הזו מתבצעת על ידי הרשמה לבעלי אתרים שחושפים ערכים מאירועים אסינכרוניים.

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

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

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

כשמדובר באובייקט אופציונלי, משתמשים ב-if let או ב-guard כדי לבטל את העטיפה של האובייקט בצורה בטוחה. אל תשתמשו ב-! כי אסור להשתמש ב-! אלא אם המפתח יודע בוודאות שהאובייקט לא יכול להיות nil.

פרמטר הקלט structureID בדוגמה מוגדר כ-String?, כלומר מחרוזת שהיא אופציונלית ויכולה להיות nil. הפונקציה הזו מוצאת את האובייקט Structure על סמך הקלט ב-structureID.

כך מומלץ לטפל באובייקטים אופציונליים:

func structure(structureID: String?) -> Structure? {
    guard let structureID else { return nil }
    return structures.first { $0.id == structureID }
  }

איך משתמשים בפרסומים

בהמשך מופיעות כמה דוגמאות בסיסיות לעבודה עם בעלי תוכן דיגיטלי בממשקי ה-API של Home. בדוגמאות הבאות, צריך ליצור מופע של Home.

var home: Home?

לפני שאתם ניגשים לאוספים, חשוב לוודא שאתם פורסים אותם כי הם אופציונליים:

guard let home else { return nil }

מעקב אחרי שינויים במבנה

השינויים הבאים במבנה מפעילים את האוסף הזה:

home.structures().batched()
  .compactMap { $0.first(where: { $0.id = myStructureID} }
  .removeDuplicates()
  .sink { structure in
    if let structure = structure {
      print("Structure \(structure.id) updated to \(structure.name)")
    }
  }

מעקב אחר שינויים במכשיר ספציפי

השינויים הבאים במכשיר מפעילים את האיסוף הזה:

home.devices().batched()
  .compactMap { deviceList -> HomeDevice? in
    deviceList.filter { $0.name == "Bedroom Lamp"}.first
  }
  .removeDuplicates()
  .sink { lampDevice in
    if lampDevice != nil {
      print("The bedroom lamp has changed!")
    }
  }

מעקב אחר שינויים במאפיין ספציפי במכשיר

אפשר להשתמש בכל מאפיין שנתמך על ידי המכשיר וממשקי ה-API של Home. הרשימה המלאה זמינה כאןTrait.

device.types.subscribe(OnOffLightDeviceType.self)
  .compactMap { $0.matterTraits.onOffTrait }
  .removeDuplicates()
  .sink { onOffState in
    if let onOffState = onOffState {
      print("Got new state update: \(onOffState.onOff)")
    }
  }

מעקב אחר שינויים מסוג מסוים במכשיר

השינויים הבאים במכשיר יפעילו את האוסף הזה:

אפשר להשתמש בכל סוג מכשיר Matter שנתמך על ידי Home APIs. רשימה מלאה זמינה DeviceType.

device.types.subscribe(DimmableLightDeviceType.self)
  .compactMap { $0.matterTraits.levelControlTrait }
  .removeDuplicates()
  .sink { dimmableLightDevice in
    if let dimmableLightDevice = dimmableLightDevice
      print("Got new state update! \(levelControlTrait.currentLevel)")
    }
  }

מעקב אחר שינויים בחדר במבנה

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

כדי לעקוב אחרי מועד ההוספה או ההסרה של מכשירים מחדר, משתמשים בdevices() שאילתה.

home.rooms().batched()
  .sink { rooms in
    print("Got a new updated set of rooms!")
    for room in rooms {
      print("Got room #\(room.name)")
    }
  }

הרשמה לקבלת עדכונים על אירועים

בממשקי ה-API של Home, נעשה שימוש באירועים כדי לזהות שינויים במצב של מכשיר.

self.cancellable = self.device.types.subscribe(FanDeviceType.self)
  .receive(on: DispatchQueue.main)
  .catch { error in
    Logger.error("Error getting FanDeviceType: \(error)")
    return Empty<FanDeviceType, Never>().eraseToAnyPublisher()
  }
  .sink { [weak self] fanDeviceType in
    self?.fanDeviceType = fanDeviceType
    self?.updateTileInfo()
  }
}