Android Automotive, sesin sürüş güvenliği etkileşimleri için çok önemli bir bileşen olduğunu ve kullanıcıların sürüş sırasında Android Automotive işletim sistemiyle etkileşim kurmasının en güvenli yollarından biri olduğunu düşünüyor. Sonuç olarak, sesli asistanların kullanıcılar için sürüş sırasında gerçekleştirilmesi zor olabilecek görevleri yerine getirmesini sağlamak amacıyla Android sesli asistan API'lerini ( VoiceInteractionSession
dahil) genişlettik.
Dokunarak Oku, kullanıcı mesaj bildirimleriyle etkileşimde bulunduğunda sesli asistanların kullanıcı adına metin mesajlarını okumasına ve yanıtlamasına olanak tanır. Bu işlevselliği sağlamak için bir sesli asistanı CarVoiceInteractionSession
entegre edebilirsiniz.
Otomotiv'de, INBOX
veya INBOX_IN_GROUP
olarak tanımlanan Bildirim Merkezi'ne gönderilen bildirimler (örneğin, SMS mesajları) bir Oynat düğmesi içerir. Kullanıcı, seçilen sesli asistanın bildirimi yüksek sesle okuması ve isteğe bağlı olarak sesle yanıt vermesi için Oynat'a tıklayabilir.
Şekil 1. Oynat düğmesiyle Dokunarak Oku bildirimi.
CarVoiceInteractionSession ile entegrasyon
Sonraki bölümlerde sesli asistanın CarVoiceInteractionSession
ile nasıl entegre edileceği açıklanmaktadır.
Sesli etkileşimleri destekleyin
Araba sesli etkileşim hizmetleri sağlayan uygulamaların mevcut Android sesli etkileşimleriyle entegre olması gerekir . Daha fazla bilgi edinmek için Android için Google Asistan'a bakın ( VoiceInteractionSession
hariç). Tüm sesli etkileşim API öğeleri mobil cihazlarda uygulananlarla aynı kalsa da, CarVoiceInteractionSession
( CarVoiceInteractionSession'ı Uygulama bölümünde açıklanmıştır) VoiceInteractionSession
yerini almıştır. Daha fazla bilgi için şu sayfalara bakın:
CarVoiceInteractionSession'ı uygulayın
CarVoiceInteractionSession
sesli asistanların metin mesajlarını yüksek sesle okumasını ve ardından bu mesajlara kullanıcı adına yanıt vermesini sağlamak için kullanabileceğiniz API'leri kullanıma sunar.
CarVoiceInteractionSession
ve VoiceInteractionSession
sınıfları arasındaki temel fark, CarVoiceInteractionSession
eylemi onShow
geçirmesidir, böylece sesli yardımcı, CarVoiceInteractionSession
bir oturum başlatır başlatmaz kullanıcının isteğinin içeriğini algılayabilir. Her sınıf için onShow
parametreleri aşağıdaki tabloda listelenmiştir:
ArabaSesEtkileşimOturumu | Sesli Etkileşim Oturumu |
---|---|
onShow şu üç parametreyi alır:
| onShow şu iki parametreyi alır:
|
Android 10'daki değişiklikler
Android 10'dan başlayarak platform, hangi eylemlerin desteklendiğini tespit etmek için VoiceInteractionService.onGetSupportedVoiceActions
çağırır. Sesli yardımcı, aşağıdaki örnekte gösterildiği gibi VoiceInteractionService.onGetSupportedVoiceActions
geçersiz kılar ve uygular:
public class MyInteractionService extends VoiceInteractionService { private static final ListSUPPORTED_VOICE_ACTIONS = Arrays.asList( CarVoiceInteractionSession.VOICE_ACTION_READ_NOTIFICATION); @Override public Set onGetSupportedVoiceActions(@NonNull Set voiceActions) { Set result = new HashSet<>(voiceActions); result.retainAll(SUPPORTED_VOICE_ACTIONS); return result; } }
Geçerli eylemler aşağıdaki tabloda açıklanmıştır. Her eylemle ilgili ayrıntılar için bkz. Sıra diyagramları .
Aksiyon | Beklenen yük | Beklenen sesli etkileşim eylemi |
---|---|---|
VOICE_ACTION_READ_NOTIFICATION | Mesajları kullanıcıya yüksek sesle okuyun ve ardından mesajlar başarıyla okunduğunda Okundu olarak işaretle seçeneğini beklemede olarak etkinleştirin. İsteğe bağlı olarak kullanıcıdan yanıt vermesini isteyin. | |
VOICE_ACTION_REPLY_NOTIFICATION | Anahtarla parçalanabilir.StatusBarNotification ile eşleşen KEY_NOTIFICATION .android.permission.BIND_NOTIFICATION_LISTENER_SERVICE gerektirir. | Kullanıcıdan yanıt mesajını belirtmesini isteyin, yanıt mesajını bekleyen niyetin RemoteInputReply girin ve ardından bekleyen niyeti tetikleyin. |
VOICE_ACTION_HANDLE_EXCEPTION | Anahtarlı dize.ExceptionValue ile eşleşen KEY_EXCEPTION ( Exception değerleri bölümünde açıklanmıştır).Bir Boole değeriyle eşleşen KEY_FALLBACK_ASSISTANT_ENABLED . Değer true ise kullanıcının isteğini yerine getirebilecek geri dönüş yardımcısı devre dışı bırakılmıştır. | İstisna için yapılması beklenen eylem, istisnanın belgelerinde tanımlanır. |
İstisna değerleri
EXCEPTION_NOTIFICATION_LISTENER_PERMISSIONS_MISSING
, sesli asistana Manifest.permission.BIND_NOTIFICATION_LISTENER_SERVICE
izninin eksik olduğunu ve bu iznin kullanıcıdan alınması gerektiğini belirtir.
Bildirim dinleyicisi izni iste
Varsayılan sesli asistanın bildirim dinleyicisi izni yoksa platformun FallbackAssistant
(otomobil üreticisi tarafından etkinleştirildiyse), sesli asistanın izin istemesi konusunda bilgilendirilmeden önce mesajı yüksek sesle okuyabilir. FallbackAssistant
etkin olup olmadığını ve mesajı okuyup okumadığını belirlemek için sesli asistanın veri yükündeki KEY_FALLBACK_ASSISTANT_ENABLED
Boolean değerini kontrol etmesi gerekir.
Platform, sesli asistanın bu iznin istenme sayısı kadar hız sınırlama mantığı eklemesini önerir. Bunu yapmak, sesli asistana bu izni vermek istemeyen ve FallbackAssistant
metin mesajlarını yüksek sesle okumasını tercih eden kullanıcıya saygı gösterir. Kullanıcının bir mesaj bildiriminde Oynat'a her basışında kullanıcıdan izin istemek, olumsuz bir kullanıcı deneyimi olabilir. Platform, sesli asistan adına hız sınırı koymuyor.
Bildirim dinleyicisi izni istenirken sesli asistan, kullanıcının park halinde mi yoksa araba mı sürdüğünü belirlemek için CarUxRestrictionsManager
kullanmalıdır. Kullanıcı araba kullanıyorsa sesli asistan, iznin nasıl verileceğiyle ilgili talimatlar sağlayan bir bildirim görüntüler. Bunu yapmak, kullanıcının daha güvenli olduğunda izin vermesine yardımcı olur (ve hatırlatır).
StatusBarNotification'la çalışın
Oku ve Yanıtla sesli eylemleriyle iletilen StatusBarNotification
Kullanıcılara mesaj bildirme bölümünde açıklandığı gibi her zaman araçla uyumlu bir mesajlaşma bildiriminde bulunur. Bazı bildirimler Yanıt Bekleniyor amacına sahip olmasa da hepsinde Okundu Olarak İşaretleme bekleyen amaçları vardır.
Bildirimlerle etkileşimleri kolaylaştırmak için, bildirimden mesajları ayıklamak ve yanıt mesajlarını bildirimin uygun bekleyen amacına yazmak için yöntemler sağlayan NotificationPayloadHandler
kullanın. Sesli yardımcı mesajı okuduktan sonra sesli asistanın Okundu Olarak İşaretle amacını tetiklemesi gerekir .
Dokunarak Okuma ön koşullarını karşılayın
Kullanıcı mesajları okumak ve yanıtlamak için sesli eylemi tetiklediğinde yalnızca varsayılan sesli asistanın VoiceInteractionSession
bilgilendirilir. Yukarıda belirtildiği gibi, bu varsayılan sesli asistanın aynı zamanda bildirim dinleyicisi iznine de sahip olması gerekir.
Sıra diyagramları
Bu şekiller CarVoiceInteractionSession actions
mantıksal akışlarını gösterir:
Şekil 2. VOICE_ACTION_READ_NOTIFICATION için sıra diyagramı.
Şekil 3'te izin isteklerine oran sınırlarının uygulanması önerilir:
Şekil 3. VOICE_ACTION_REPLY_NOTIFICATION için sıra diyagramı.
Şekil 4. VOICE_ACTION_HANDLE_EXCEPTION için sıra diyagramı.
Uygulamanın adını oku
Sesli yardımcınızın, mesajın okunması sırasında mesajlaşma uygulamasının adını yüksek sesle okumasını istiyorsanız (örneğin, "Hangouts'tan Sam şunu söyledi..."), asistanın mesajı okuduğundan emin olmak için aşağıdaki kod örneğinde gösterilene benzer bir işlev oluşturun. doğru isim:
@Nullable String getMessageApplicationName(Context context, StatusBarNotification statusBarNotification) { ApplicationInfo info = getApplicationInfo(context, statusBarNotification.getPackageName()); if (info == null) return null; Notification notification = statusBarNotification.getNotification(); // Sometimes system packages will post on behalf of other apps, so check this // field for a system app notification. if (isSystemApp(info) && notification.extras.containsKey(Notification.EXTRA_SUBSTITUTE_APP_NAME)) { return notification.extras.getString(Notification.EXTRA_SUBSTITUTE_APP_NAME); } else { PackageManager pm = context.getPackageManager(); return String.valueOf(pm.getApplicationLabel(info)); } } @Nullable ApplicationInfo getApplicationInfo(Context context, String packageName) { final PackageManager pm = context.getPackageManager(); ApplicationInfo info; try { info = pm.getApplicationInfo(packageName, 0); } catch (PackageManager.NameNotFoundException e) { return null; } return info; } boolean isSystemApp(ApplicationInfo info) { return (info.flags & ApplicationInfo.FLAG_SYSTEM) != 0; }