Sterowanie urządzeniami w iOS

Ten przewodnik jest kontynuacją artykułu Dostęp do urządzeń i metadanych urządzeń na iOS i zawiera dodatkowe przykłady kontroli nad urządzeniami i dostępu do nich.

Aby używać określonych typów lub cech urządzeń, takich jak Matter OnOffTrait użyte w wielu przykładach, musisz je zaimportować:

import GoogleHomeSDK
import GoogleHomeTypes

Sprawdzanie, czy cecha obsługuje polecenie

Użyj funkcji supports na poziomie cechy, aby sprawdzić, czy polecenie jest obsługiwane na danym urządzeniu.

Aby na przykład sprawdzić, czy urządzenie obsługuje polecenie toggle cechy Włączanie/wyłączanie:

// Check if the OnOff trait supports the toggle command.
if onOffTraitTest.supportsToggleCommand {
  print("onOffTrait supports toggle command")
} else {
  print("onOffTrait does not support stateful toggle command")
}

Wysyłanie polecenia do urządzenia

Wysłanie polecenia jest podobne do odczytania atrybutu stanu z cechy. Aby włączyć lub wyłączyć urządzenie, użyj polecenia przełączania OnOffTrait, które w modelu danych ekosystemu Google Home jest zdefiniowane jako toggle(). Ta metoda zmienia wartość onOff na false, jeśli jest ona równa true, lub na true, jeśli jest równa false:

// Calling a command on a trait.
do {
  try await onOffTraitTest.toggle()
} catch let error as HomeError {
  // Code for handling the exception
}

Polecenia mogą zwracać wyjątek, jeśli w przepływie wykonania zostanie wykryty problem. Jako deweloper powinieneś używać bloku do-catch, aby prawidłowo obsługiwać te wyjątki i wyświetlać użytkownikom szczegółowe informacje w przypadkach, w których błędy wymagają podjęcia działań. Nieobsłużone wyjątki zatrzymają działanie aplikacji i mogą spowodować jej awarię.

Możesz też użyć poleceń off() lub on(), aby jednoznacznie ustawić stan:

do {
  try await onOffTraitTest.off()
  try await onOffTraitTest.on()
} catch let error as HomeError {
  // Code for handling the exception
}

Po wysłaniu polecenia zmiany stanu i jego wykonaniu możesz odczytać stan zgodnie z opisem w sekcji Odczytywanie stanu urządzenia, aby obsłużyć go w aplikacji.

Wysyłanie polecenia z parametrami

Niektóre polecenia mogą używać parametrów, np. te na urządzeniach OnOffTrait lub LevelControlTrait:

offWithEffect

// Turn off the light using the DyingLight effect.
do {
  try await onOffTraitTest.offWithEffect(
    effectIdentifier: Matter.OnOffTrait.EffectIdentifierEnum.dyingLight,
    effectVariant: 0
  )
} catch let error as HomeError {
  // Code for handling the exception
}

moveToLevel

// Change the brightness of the light to 50%
do {
  try await levelControlTraitTest.moveToLevel(
    level: UInt8(127),
    transitionTime: 0,
    optionsMask: Matter.LevelControlTrait.OptionsBitmap(),
    optionsOverride: Matter.LevelControlTrait.OptionsBitmap()
  )
} catch let error as HomeError {
  // Code for handling the exception
}

Sprawdzanie, czy cecha obsługuje atrybut

Niektóre urządzenia mogą obsługiwać cechę Matter, ale nie konkretny atrybut. Na przykład urządzenie Cloud-to-cloud, które zostało przypisane do Matter, może nie obsługiwać wszystkich atrybutów Matter. Aby obsługiwać takie przypadki, użyj właściwości isSupported na poziomie cechy, aby sprawdzić, czy atrybut jest obsługiwany na danym urządzeniu.

Aby na przykład sprawdzić, czy urządzenie obsługuje atrybut onOff cechy Włączanie/wyłączanie:

// Check if the OnOff trait supports the onOff attribute.
if onOffTrait.attributes.$onOff.isSupported {
  print("onOffTrait supports onOff state")
} else {
  print("onOffTrait is for a command only device!")
}

Niektóre atrybuty mogą mieć wartość null w specyfikacji Matter lub w schemacie Cloud-to-cloud smart home. W przypadku tych atrybutów możesz określić, czy wartość null zwrócona przez atrybut wynika z tego, że urządzenie nie zgłasza tej wartości, czy wartość atrybutu to w rzeczywistości nil. Aby to zrobić, użyj atrybutu isNullable oprócz atrybutu isSupported:

// Check if a nullable attribute is set or is not supported.
if let deviceType = await device.types.get(OnOffLightDeviceType.self) {
  if let onOffTrait = deviceType.traits[Matter.OnOffTrait.self] {
    if onOffTrait.attributes.startUpOnOff == nil {
      if onOffTrait.attributes.$startUpOnOff.isSupported {
        print(
          "onOffTrait supports startUpOnOff and it is nil. Check the spec for the contextual meaning."
        )
      } else {
        print("onOffTrait does not support startUpOnOff!")
      }
    } else {
      print(
        "onOffTrait supports startUpOnOff and it is set to \(onOffTrait.attributes.startUpOnOff)"
      )
    }
  }
}

Aktualizowanie atrybutów cech

Jeśli chcesz zmienić wartość danego atrybutu, a żadne z poleceń cechy tego nie robi, atrybut może obsługiwać jawne ustawienie wartości.

Czy wartość atrybutu można zmienić, zależy od 2 czynników:

  • Czy atrybut można zapisywać?
  • Czy wartość atrybutu może się zmienić w wyniku wysłania polecenia dotyczącego cechy?

Informacje te znajdziesz w dokumentacji referencyjnej dotyczącej cech i ich atrybutów.

Kombinacje właściwości, które określają, jak wartość atrybutu może zostać zmieniona, to:

  • Tylko do odczytu i nie ma na niego wpływu żadne inne polecenie. Oznacza to, że wartość atrybutu nie zmienia się. Na przykład atrybut currentPosition tagu SwitchTrait.

  • Tylko do odczytu i podatne na inne polecenia. Oznacza to, że wartość atrybutu może się zmienić tylko w wyniku wysłania polecenia. Na przykład atrybut currentLevel jest dostępny tylko do odczytu, ale jego wartość można zmieniać za pomocą poleceń takich jak moveToLevel.LevelControlTrait

  • Można je zapisywać i nie mają na nie wpływu inne polecenia. Oznacza to, że możesz bezpośrednio zmienić wartość atrybutu za pomocą funkcji update cechy, ale nie ma poleceń, które wpłyną na wartość atrybutu. Na przykład atrybut WrongCodeEntryLimit tagu DoorLockTrait.

  • Można w nim zapisywać dane i jest on modyfikowany przez inne polecenia. Oznacza to, że możesz bezpośrednio zmienić wartość atrybutu za pomocą funkcji update cechy, a wartość atrybutu może się zmienić w wyniku wysłania polecenia. Na przykład atrybut occupiedCoolingSetpoint tagu ThermostatTrait można zapisać, ale też zaktualizować za pomocą setpointRaiseLower polecenia.

Przykład użycia funkcji aktualizacji do zmiany wartości atrybutu

Ten przykład pokazuje, jak jawnie ustawić wartość atrybutu DoorLockTrait.wrongCodeEntryLimit.

Aby ustawić wartość atrybutu, wywołaj funkcję update cechy i przekaż jej funkcję aktualizacji, która ustawia nową wartość. Zalecamy, aby najpierw sprawdzić, czy usługa obsługuje atrybut.

Na przykład:

if doorLockTraitTest.attributes.$wrongCodeEntryLimit.isSupported {
  let _ = try await doorLockTraitTest.update {
    $0.setWrongCodeEntryLimit(3)
  }
}