iOS'te cihaz durumunu izleme

iOS için Home API'lerinde, Swift'te Combine çerçevesi kullanılarak evdeki durumdaki değişiklikleri gözlemleyebilirsiniz. Home API'lerindeki yapılarda, odalarda, cihaz meta verilerinde ve cihaz durumundaki değişiklikleri gözlemlemek için HomeDevice kullanılarak herhangi bir API ile işlem yapılabilir. Bu işlem, eşzamansız etkinliklerdeki değerleri gösteren yayıncılara abone olarak yapılır.

Bir koleksiyona öğe eklendiğinde, koleksiyondan öğe silindiğinde veya koleksiyondaki bir öğe değiştirildiğinde koleksiyonun en son anlık görüntüsü döndürülür.

Bu anlık görüntüyü eski bir kopyayla karşılaştırarak belirli değişiklikleri belirlemek geliştiricinin sorumluluğundadır. Home API'lerindeki her üst nesne türü için sağlanan id alanı bu amaçla kullanılabilir.

İsteğe bağlı nesneleri sarmalama

İsteğe bağlı bir nesneyi güvenli bir şekilde açmak için if let veya guard kullanın. Geliştirici, nesnenin boş olamayacağından emin olmadığı sürece ! hiçbir zaman kullanılmamalıdır. Bu nedenle ! kullanmayın.

Örnekte structureID giriş parametresi String? olarak tanımlanmıştır. Bu, isteğe bağlı olan ve boş olma olasılığı bulunan bir dize olduğu anlamına gelir. Bu işlev, structureID'daki girişe göre Structure nesnesini bulur.

İsteğe bağlı nesneleri işleme konusunda önerimiz:

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

Yayıncıları kullanma

Aşağıda, Home API'lerinde yayıncılarla çalışmayla ilgili bazı temel örnekler verilmiştir. Aşağıdaki örnekler için Home sınıfının bir örneği oluşturulmalıdır.

var home: Home?

Koleksiyonlara erişmeden önce, isteğe bağlı oldukları için paketlerini açtığınızdan emin olun:

guard let home else { return nil }

Bir yapıdaki değişiklikleri izleme

Bir yapıda yapılan aşağıdaki değişiklikler bu koleksiyonu tetikler:

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)")
    }
  }

Belirli bir cihazdaki değişiklikleri izleme

Bir cihazda yapılan aşağıdaki değişiklikler bu koleksiyonu tetikler:

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!")
    }
  }

Cihazdaki belirli bir özellikte yapılan değişiklikleri izleme

Cihaz ve Home API'leri tarafından desteklenen tüm özellikleri kullanın. Tam liste için Trait bölümüne bakın.

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

Cihazdaki belirli bir türdeki değişiklikleri izleme

Bir cihaz türünde yapılan aşağıdaki değişiklikler bu koleksiyonu tetikler:

Home API'ler tarafından desteklenen tüm Matter cihaz türlerini kullanabilirsiniz. Tam listeyi DeviceType sayfasında bulabilirsiniz.

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

Bir yapıdaki odada yapılan değişiklikleri izleme

Bir odada yapılan aşağıdaki değişiklikler bu koleksiyonu tetikler:

Cihazların bir odaya ne zaman eklendiğini veya odadan ne zaman kaldırıldığını izlemek için devices() sorgusunu kullanın.

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

Etkinliklere abone olma

Home API'lerinde etkinlikler, cihazın durumundaki değişiklikleri algılamak için kullanılır.

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()
  }
}