この記事では、アプリを注意散漫防止の最適化済み(DO)ユーザー インターフェースに適切に移行する方法を説明します。また、自動車の運転状態と、それに対応するユーザー エクスペリエンスの制限を利用する方法も説明します。自動車ユーザーエクスペリエンス(UX)制限ルールについて詳しくは、自動車ユーザー エクスペリエンス制限をご覧ください。これには、駐車、アイドリング、移動の 3 つの運転状態について詳しく記載されています。
対象読者
このコンテンツは、自動車の運転状態の変化とそれに対応する UX 制限に合わせてアプリを設計するディベロッパーを対象としています。
技術的な詳細
CardrivingStateManager
自動車の運転状態(駐車、アイドリング、移動)は、Vehicle Hardware Abstraction Layer(VHAL)によって提供されるセンサー値から生成されます。システムは、基本的なセンサー情報(車速や現在のギア選択など)を使用して、現在の運転状態を導出します。
この情報は、@SystemApis を提供する CarDrivingStateManager
を通じて特権クライアントに公開されます。つまり、プラットフォーム内部構造、バンドルされた APK(SysUI や設定など)、特権 APK(GMSCore など)のみがこれらの API にアクセスできます。これらの API は、運転状態(android.car.permission.CAR_DRIVING_STATE
)に固有の権限によって保護されています。クライアントは、運転状態情報へのアクセスが必要な場合、この権限をリクエストする必要があります。
CarUxRestrictionsManager
運転状態に応じてユーザー インターフェースを表示するアプリは CarUxRestrictionsManager
をリッスンする必要があります。そうすれば運転状態から UX 制限へのマッピングが抽象化されるので、さまざまな市場の安全要件に合わせてアプリを調整する必要がありません。
注: これらのアクティビティは、ドライバーの注意散漫ガイドラインで説明されているように、DistractionOptimized としてマークする必要があります。適切にマークされていないアクティビティはブロックされます。
代わりに、アプリは、CarUxRestrictionsManager によって公開される絶対的な運転状態ではなく、CarUxRestrictionsManager によって公開される制限を監視して、ユーザー インターフェースやユーザー エクスペリエンスのあらゆる側面を理解します。
コードサンプル
次のサンプルコードは、アプリが UX の制限を監視する方法を示しています。
- Car ライブラリ パッケージをインポートします。
import android.car.Car; /* For CarUxRestrictions */ import android.car.drivingstate.CarUxRestrictions; import android.car.drivingstate.CarUxRestrictionsManager;
CarUxRestrictionManager.OnUxRestrictionsChangedListener
(mUxRChangeListener
)を実装します。このリスナーは、CarUxRestrictionsManager に登録されると、UX 制限に変更が生じたときに呼び出されます。必要に応じて、注意散漫防止の最適化済みになるように制限の変更を処理します。@Nullable private CarUxRestrictionsManager mCarUxRestrictionsManager; private CarUxRestrictions mCurrentUxRestrictions; /* Implement the onUxRestrictionsChangedListener interface */ private CarUxRestrictionsManager.OnUxRestrictionsChangedListener mUxrChangeListener = new CarUxRestrictionsManager.OnUxRestrictionsChangedListener() { @Override public void onUxRestrictionsChanged(CarUxRestrictions carUxRestrictions) { mCurrentUxRestrictions = carUxRestrictions; /* Handle the new restrictions */ handleUxRestrictionsChanged(carUxRestrictions); } };
- 自動車 API を呼び出して、mCar という名前の自動車インスタンスを作成し、自動車サービスに接続します。
mCar = Car.createCar(context); if (mCar == null) { // handle car connection error }
mCar.getCarManager() - mCarUxRestrictionsManager
を呼び出してCarUxRestrictionsManager
を取得します:CarUxRestrictionsManager carUxRestrictionsManager = (CarUxRestrictionsManager) mCar.getCarManager(Car.CAR_UX_RESTRICTION_SERVICE);
- 上記のステップ 2 で実装した
mUxRChangeListener
をCarUxRestrictionsManager
に登録するにはmCarUxRestrictionsManager.registerListener()
を呼び出します。mCarUxRestrictionsManager.registerListener(mUxrChangeListener); mUxrChangeListener.onUxRestrictionsChanged( mCarUxRestrictionsManager.getCurrentCarUxRestrictions());
サンプルコード ブロック(ステップ 3 からステップ 5 で作成)が完了すると、運転状態が変化したときにリスナーの受信制限が変更されます。
mCar = Car.createCar(context); if (mCar == null) { // handle car connection error } CarUxRestrictionsManager carUxRestrictionsManager = (CarUxRestrictionsManager) mCar.getCarManager(Car.CAR_UX_RESTRICTION_SERVICE); mCarUxRestrictionsManager.registerListener(mUxrChangeListener); mUxrChangeListener.onUxRestrictionsChanged( mCarUxRestrictionsManager.getCurrentCarUxRestrictions());
CarUxRestrictions
CarUxRestrictions オブジェクトから次の 2 種類の情報が提供されます。
- 注意散漫に対する最適化に必要な最新の要件はありますか?
- 要件がある場合、現在どのような制限が設定されていますか?
getCurrentUxRestrictions()
またはリスナー コールバックから CarUxRestrictions を取得したら、アプリは isRequiresDistractionOptimization()
API を使用して注意散漫防止の最適化が必要かどうかを判断できるようになります。この API が false を返した場合、注意散漫防止の最適化の要件はありません。アプリは任意のアクティビティを安全に実行できます。
最適化が必要な場合は、getActiveRestrictions() API を使用して既存の制限のセットを取得します。この API は現在有効なすべての制限のビットマスクである int を返します。現在通知されている一連の制限は CarUxRestrictions
の下にリストされています。
注: 制限セットのマイナーな変更は、近いうちに実施される予定です。
たとえば、アプリに動画再生制限があるかどうかを判断したい場合は、CarUxRestrictions オブジェクトを取得するときに、アプリでこの制限を確認する必要があります。
int activeUxR = mCurrentCarUxRestrictions.getActiveRestrictions(); if ((activeUxR & CarUxRestrictions.UX_RESTRICTIONS_NO_VIDEO) != 0) { handleStopPlayingVideo(); }
DrivingState
CarDrivingStateManager は、車両の実際の運転状態(駐車、アイドリング、移動)を示します。CarUxRestrictionsManager の呼び出しと同様に、CarDrivingStateManager API を呼び出すことができます。アプリで、リスナーの登録や、現在の運転状態の取得を行えます。運転状態は CarDrivingStateEvent として返されます。
CarUxRestrictionsManager API と同様に、クライアントは registerListener() を使用して運転状態にリスナーを登録し、CarDrivingStateEventListener
の実装を渡すことができます。運転状態が変わったとき、新しい CarDrivingStateEvent
によって onDrivingStateChanged() メソッドが呼び出されます。
import android.car.Car; /* For CarDrivingState */ import android.car.drivingstate.CarDrivingStateEvent; import android.car.drivingstate.CarDrivingStateManager; mDrivingStateManager = (CarDrivingStateManager) mCar.getCarManager( Car.CAR_DRIVING_STATE_SERVICE); /* Register the listener (implemented below) */ mDrivingStateManager.registerListener(mDrivingStateEventListener); /* While we wait for a change to be notified, query the current state */ mDrivingStateEvent = mDrivingStateManager.getCurrentCarDrivingState(); private final CarDrivingStateManager.CarDrivingStateEventListener mDrivingStateEventListener = new CarDrivingStateManager.CarDrivingStateEventListener() { @Override public void onDrivingStateChanged(CarDrivingStateEvent event) { mDrivingStateEvent = event; /* handle the state change accordingly */ handleDrivingStateChange(); } };
テスト
ギアと速度の変化をシミュレートすることで、運転状態を変えることができます。車両イベントを挿入するには、adbshell コマンドを使用します。このコマンドは開発とテストに役立ちます。
運転イベントをシミュレートするには、次のようにします。
- 速度を 0 に設定するには、次のようにします。
adb shell dumpsys activity service com.android.car inject-vhal-event 0x11600207 0
- ギアを「Parked」に設定するには(「PARKED」を指す CarDrivingStateEvent をシミュレートする)、次のようにします。
adb shell dumpsys activity service com.android.car inject-vhal-event 0x11400400 4
- 速度が 0 のままでギアを「Drive」に設定するには(「IDLING」を指す CarDrivingStateEvent をシミュレートする)、次のようにします。
adb shell dumpsys activity service com.android.car inject-vhal-event 0x11400400 8
- 速度を毎秒 30 メートルに設定するには(「MOVING」を指す CarDrivingStateEvent をシミュレートする)、次のようにします。
adb shell dumpsys activity service com.android.car inject-vhal-event 0x11600207 30