Google Assistant और मीडिया ऐप्लिकेशन

Google Assistant की मदद से, बोलकर दिए गए निर्देशों का इस्तेमाल करके कई डिवाइसों को कंट्रोल किया जा सकता है. जैसे, Google Home, आपका फ़ोन वगैरह. इसमें मीडिया के निर्देश ("बेयॉन्से का कोई गाना चलाओ") समझने की सुविधा पहले से मौजूद होती है. साथ ही, यह मीडिया कंट्रोल (जैसे, रोकना, छोड़ना, तेज़ी से आगे बढ़ाना, पसंद करना) के साथ काम करता है.

Assistant, Android मीडिया ऐप्लिकेशन के साथ मीडिया सेशन का इस्तेमाल करके कम्यूनिकेट करती है. यह आपके ऐप्लिकेशन को लॉन्च करने और वीडियो चलाने के लिए, इंटेंट या सेवाओं का इस्तेमाल कर सकता है. बेहतर नतीजों के लिए, आपके ऐप्लिकेशन में इस पेज पर बताई गई सभी सुविधाएं लागू होनी चाहिए.

लेख पढ़ें.

मीडिया सेशन का इस्तेमाल करना

हर ऑडियो और वीडियो ऐप्लिकेशन को मीडिया सेशन लागू करना होगा, ताकि कॉन्टेंट चलने के बाद Assistant, ट्रांसपोर्ट कंट्रोल को ऑपरेट कर सके.

ध्यान दें कि Assistant सिर्फ़ इस सेक्शन में दी गई कार्रवाइयों का इस्तेमाल करती है. हालांकि, हमारा सुझाव है कि तैयारी और प्लेबैक से जुड़े सभी एपीआई लागू करें, ताकि यह पक्का किया जा सके कि वे अन्य ऐप्लिकेशन के साथ काम करते हों. जिन कार्रवाइयों के लिए सहायता उपलब्ध नहीं है उनके लिए, मीडिया सेशन कॉलबैक ERROR_CODE_NOT_SUPPORTED का इस्तेमाल करके, गड़बड़ी की जानकारी दे सकते हैं.

अपने ऐप्लिकेशन के MediaSession ऑब्जेक्ट में ये फ़्लैग सेट करके, मीडिया और ट्रांसपोर्ट कंट्रोल चालू करें:

Kotlin

session.setFlags(
        MediaSessionCompat.FLAG_HANDLES_MEDIA_BUTTONS or
        MediaSessionCompat.FLAG_HANDLES_TRANSPORT_CONTROLS
)

Java

session.setFlags(MediaSessionCompat.FLAG_HANDLES_MEDIA_BUTTONS |
    MediaSessionCompat.FLAG_HANDLES_TRANSPORT_CONTROLS);

आपके ऐप्लिकेशन के मीडिया सेशन को यह एलान करना होगा कि वह किन कार्रवाइयों के साथ काम करता है. साथ ही, उसे मीडिया सेशन के कॉलबैक लागू करने होंगे. setActions() में, उन कार्रवाइयों के बारे में बताएं जिन्हें आपका ऐप्लिकेशन सपोर्ट करता है.

Universal Android Music Player सैंपल प्रोजेक्ट, मीडिया सेशन सेट अप करने का एक अच्छा उदाहरण है.

वीडियो चलाने से जुड़ी कार्रवाइयां

किसी सेवा से मीडिया चलाना शुरू करने के लिए, मीडिया सेशन में ये PLAY कार्रवाइयां और उनके कॉलबैक होने चाहिए:

कार्रवाई कॉलबैक
ACTION_PLAY onPlay()
ACTION_PLAY_FROM_SEARCH onPlayFromSearch()
ACTION_PLAY_FROM_URI (*) onPlayFromUri()

आपके सेशन में, इन PREPARE कार्रवाइयों और उनके कॉलबैक को भी लागू किया जाना चाहिए:

कार्रवाई कॉलबैक
ACTION_PREPARE onPrepare()
ACTION_PREPARE_FROM_SEARCH onPrepareFromSearch()
ACTION_PREPARE_FROM_URI (*) onPrepareFromUri()

(*) Google Assistant में यूआरआई पर आधारित कार्रवाइयाँ सिर्फ़ उन कंपनियों के लिए काम करती हैं जो Google को यूआरआई उपलब्ध कराती हैं. Google को अपने मीडिया कॉन्टेंट के बारे में बताने के बारे में ज़्यादा जानने के लिए, मीडिया के लिए कार्रवाइयाँ देखें.

तैयारी वाले एपीआई लागू करके, बोले गए निर्देश के बाद वीडियो चलने में लगने वाले समय को कम किया जा सकता है. जिन मीडिया ऐप्लिकेशन को प्लेबैक में लगने वाले समय को कम करना है वे कॉन्टेंट को कैश मेमोरी में सेव करने और मीडिया प्लेबैक तैयार करने के लिए, अतिरिक्त समय का इस्तेमाल कर सकते हैं.

खोज क्वेरी पार्स करना

जब कोई उपयोगकर्ता किसी मीडिया आइटम को खोजता है, जैसे कि “[your app name] पर जैज़ चलाओ” या “[song title] सुनो”, तो onPrepareFromSearch() या onPlayFromSearch() कॉलबैक तरीके को क्वेरी पैरामीटर और एक्स्ट्रा बंडल मिलता है.

आपका ऐप्लिकेशन, वॉइस सर्च क्वेरी को पार्स करे और इन चरणों का पालन करके, कॉन्टेंट चलाना शुरू करे:

  1. नतीजों को फ़िल्टर करने के लिए, वॉइस सर्च से मिले एक्सट्रा बंडल और खोज क्वेरी स्ट्रिंग का इस्तेमाल करें.
  2. इन नतीजों के आधार पर, वीडियो चलाने के लिए एक सूची बनाओ.
  3. नतीजों में मौजूद सबसे काम का मीडिया आइटम चलाओ.

onPlayFromSearch() मेथड, एक अतिरिक्त पैरामीटर लेता है. इसमें आवाज़ से की गई खोज के बारे में ज़्यादा जानकारी होती है. इन अतिरिक्त सुविधाओं की मदद से, ऐप्लिकेशन में ऑडियो कॉन्टेंट को सुना जा सकता है. अगर खोज के नतीजे यह डेटा नहीं दे पाते हैं, तो लॉजिक लागू किया जा सकता है. इससे, खोज क्वेरी को पार्स किया जा सकेगा और क्वेरी के आधार पर सही ट्रैक चलाए जा सकेंगे.

Android Automotive OS और Android Auto में ये सुविधाएं काम करती हैं:

यहां दिए गए कोड स्निपेट में बताया गया है कि वॉइस सर्च क्वेरी को पार्स करने और वीडियो चलाने के लिए, MediaSession.Callback को लागू करने के दौरान onPlayFromSearch() तरीके को कैसे बदला जा सकता है:

Kotlin

override fun onPlayFromSearch(query: String?, extras: Bundle?) {
    if (query.isNullOrEmpty()) {
        // The user provided generic string e.g. 'Play music'
        // Build appropriate playlist queue
    } else {
        // Build a queue based on songs that match "query" or "extras" param
        val mediaFocus: String? = extras?.getString(MediaStore.EXTRA_MEDIA_FOCUS)
        if (mediaFocus == MediaStore.Audio.Artists.ENTRY_CONTENT_TYPE) {
            isArtistFocus = true
            artist = extras.getString(MediaStore.EXTRA_MEDIA_ARTIST)
        } else if (mediaFocus == MediaStore.Audio.Albums.ENTRY_CONTENT_TYPE) {
            isAlbumFocus = true
            album = extras.getString(MediaStore.EXTRA_MEDIA_ALBUM)
        }

        // Implement additional "extras" param filtering
    }

    // Implement your logic to retrieve the queue
    var result: String? = when {
        isArtistFocus -> artist?.also {
            searchMusicByArtist(it)
        }
        isAlbumFocus -> album?.also {
            searchMusicByAlbum(it)
        }
        else -> null
    }
    result = result ?: run {
        // No focus found, search by query for song title
        query?.also {
            searchMusicBySongTitle(it)
        }
    }

    if (result?.isNotEmpty() == true) {
        // Immediately start playing from the beginning of the search results
        // Implement your logic to start playing music
        playMusic(result)
    } else {
        // Handle no queue found. Stop playing if the app
        // is currently playing a song
    }
}

Java

@Override
public void onPlayFromSearch(String query, Bundle extras) {
    if (TextUtils.isEmpty(query)) {
        // The user provided generic string e.g. 'Play music'
        // Build appropriate playlist queue
    } else {
        // Build a queue based on songs that match "query" or "extras" param
        String mediaFocus = extras.getString(MediaStore.EXTRA_MEDIA_FOCUS);
        if (TextUtils.equals(mediaFocus,
                MediaStore.Audio.Artists.ENTRY_CONTENT_TYPE)) {
            isArtistFocus = true;
            artist = extras.getString(MediaStore.EXTRA_MEDIA_ARTIST);
        } else if (TextUtils.equals(mediaFocus,
                MediaStore.Audio.Albums.ENTRY_CONTENT_TYPE)) {
            isAlbumFocus = true;
            album = extras.getString(MediaStore.EXTRA_MEDIA_ALBUM);
        }

        // Implement additional "extras" param filtering
    }

    // Implement your logic to retrieve the queue
    if (isArtistFocus) {
        result = searchMusicByArtist(artist);
    } else if (isAlbumFocus) {
        result = searchMusicByAlbum(album);
    }

    if (result == null) {
        // No focus found, search by query for song title
        result = searchMusicBySongTitle(query);
    }

    if (result != null && !result.isEmpty()) {
        // Immediately start playing from the beginning of the search results
        // Implement your logic to start playing music
        playMusic(result);
    } else {
        // Handle no queue found. Stop playing if the app
        // is currently playing a song
    }
}

अपने ऐप्लिकेशन में ऑडियो कॉन्टेंट चलाने के लिए, वॉइस सर्च को लागू करने के तरीके के बारे में ज़्यादा जानकारी देने वाला उदाहरण देखने के लिए, यूनिवर्सल Android म्यूज़िक प्लेयर का सैंपल देखें.

खाली क्वेरी को हैंडल करना

अगर onPrepare(), onPlay(), onPrepareFromSearch() या onPlayFromSearch() को खोज क्वेरी के बिना कॉल किया जाता है, तो आपके मीडिया ऐप्लिकेशन को "मौजूदा" मीडिया चलाना चाहिए. अगर कोई मीडिया नहीं चल रहा है, तो ऐप्लिकेशन को कुछ चलाने की कोशिश करनी चाहिए. जैसे, हाल ही की प्लेलिस्ट का कोई गाना या कोई रैंडम क्यू. जब कोई उपयोगकर्ता अतिरिक्त जानकारी दिए बिना, “[आपके ऐप्लिकेशन का नाम] पर संगीत चलाओ” कहता है, तब Assistant इन एपीआई का इस्तेमाल करती है.

जब कोई उपयोगकर्ता “[आपके ऐप्लिकेशन का नाम] पर संगीत चलाओ” कहता है, तो Android Automotive OS या Android Auto, आपके ऐप्लिकेशन को लॉन्च करने और ऑडियो चलाने की कोशिश करता है. इसके लिए, वह आपके ऐप्लिकेशन के onPlayFromSearch() तरीके को कॉल करता है. हालांकि, उपयोगकर्ता ने मीडिया आइटम का नाम नहीं बताया. इसलिए, onPlayFromSearch() मेथड को खाली क्वेरी पैरामीटर मिलता है. ऐसे मामलों में, आपके ऐप्लिकेशन को तुरंत ऑडियो चलाना चाहिए. जैसे, हाल ही की प्लेलिस्ट का कोई गाना या कोई रैंडम गाना.

बोलकर स्मार्टवॉच का इस्तेमाल करने की सुविधा के लिए, लेगसी सपोर्ट का एलान करना

ज़्यादातर मामलों में, ऊपर बताई गई मीडिया चलाने की कार्रवाइयों को मैनेज करने से, आपके ऐप्लिकेशन को मीडिया चलाने की सभी ज़रूरी सुविधाएं मिल जाती हैं. हालांकि, कुछ सिस्टम के लिए ज़रूरी है कि आपके ऐप्लिकेशन में खोज के लिए इंटेंट फ़िल्टर मौजूद हो. आपको अपने ऐप्लिकेशन की मेनिफ़ेस्ट फ़ाइलों में, इस इंटेंट फ़िल्टर के साथ काम करने की जानकारी देनी होगी.

फ़ोन ऐप्लिकेशन की मेनिफ़ेस्ट फ़ाइल में यह कोड शामिल करें:

<activity>
    <intent-filter>
        <action android:name=
             "android.media.action.MEDIA_PLAY_FROM_SEARCH" />
        <category android:name=
             "android.intent.category.DEFAULT" />
    </intent-filter>
</activity>

वीडियो चलाने के कंट्रोल

आपके ऐप्लिकेशन का मीडिया सेशन चालू होने के बाद, Assistant आवाज़ से दिए जाने वाले निर्देशों का इस्तेमाल करके, प्लेबैक को कंट्रोल कर सकती है और मीडिया मेटाडेटा को अपडेट कर सकती है. इसके लिए, आपके कोड में ये कार्रवाइयां चालू होनी चाहिए और इनसे जुड़े कॉलबैक लागू होने चाहिए:

कार्रवाई कॉलबैक Description
ACTION_SKIP_TO_NEXT onSkipToNext() अगला वीडियो
ACTION_SKIP_TO_PREVIOUS onSkipToPrevious() पिछला गाना चलाएं
ACTION_PAUSE, ACTION_PLAY_PAUSE onPause() रोकें
ACTION_STOP onStop() रोकें
ACTION_PLAY onPlay() फिर से शुरू करें
ACTION_SEEK_TO onSeekTo() 30 सेकंड पीछे ले जाओ
ACTION_SET_RATING onSetRating(android.support.v4.media.RatingCompat) 'पसंद करें' या 'नापसंद करें' बटन.
ACTION_SET_CAPTIONING_ENABLED onSetCaptioningEnabled(boolean) कैप्शन की सुविधा चालू/बंद करें.

कृपया ध्यान दें:

  • सीख कमांड के काम करने के लिए, PlaybackState को state, position, playback speed, and update time के साथ अप-टू-डेट होना चाहिए. स्टेटस में बदलाव होने पर, ऐप्लिकेशन को setPlaybackState() को कॉल करना होगा.
  • मीडिया ऐप्लिकेशन को मीडिया सेशन का मेटाडेटा भी अप-टू-डेट रखना होगा. इससे "कौनसा गाना चल रहा है?" जैसे सवालों के जवाब दिए जा सकते हैं जब लागू होने वाले फ़ील्ड (जैसे, ट्रैक का टाइटल, कलाकार, और नाम) में बदलाव होता है, तब ऐप्लिकेशन को setMetadata() को कॉल करना होगा.
  • MediaSession.setRatingType() को सेट करना ज़रूरी है, ताकि यह पता चल सके कि ऐप्लिकेशन किस तरह की रेटिंग के साथ काम करता है. साथ ही, ऐप्लिकेशन में onSetRating() को लागू करना ज़रूरी है. अगर ऐप्लिकेशन रेटिंग की सुविधा के साथ काम नहीं करता है, तो उसे रेटिंग टाइप को RATING_NONE पर सेट करना चाहिए.

ऐसा हो सकता है कि कॉन्टेंट के टाइप के हिसाब से, बोलकर की जाने वाली कार्रवाइयां अलग-अलग हों.

कॉन्टेंट का टाइप ज़रूरी कार्रवाइयां
संगीत

इनके लिए सपोर्ट होना ज़रूरी है: चलाएं, रोकें, बंद करें, अगले पर जाएं, और पिछले पर जाएं

इनके लिए सहायता पाने का सुझाव दिया जाता है: Seek To

पॉडकास्ट

इनके लिए ज़रूरी है: चलाएं, रोकें, बंद करें, और इस समय पर जाएं

इनके लिए सहायता का सुझाव दें: अगले और पिछले पर जाएं

ऑडियो बुक इनके लिए ज़रूरी है: चलाएं, रोकें, बंद करें, और इस समय पर जाएं
रेडियो इनके लिए सहायता उपलब्ध होनी चाहिए: चलाएं, रोकें, और बंद करें
समाचार इनके लिए सपोर्ट होना ज़रूरी है: चलाएं, रोकें, बंद करें, अगले पर जाएं, और पिछले पर जाएं
वीडियो

इन सुविधाओं का होना ज़रूरी है: चलाएं, रोकें, बंद करें, इस समय पर जाएं, पीछे ले जाएं, और तेज़ी से आगे बढ़ाएं

इनके लिए सहायता उपलब्ध कराने का सुझाव दिया जाता है: अगले और पिछले गाने पर जाएं

आपको ऊपर दी गई कार्रवाइयों में से ज़्यादा से ज़्यादा कार्रवाइयों के लिए सहायता देनी होगी. हालांकि, आपको अन्य कार्रवाइयों के लिए भी सही तरीके से जवाब देना होगा. उदाहरण के लिए, अगर सिर्फ़ Premium उपयोगकर्ताओं के पास पिछले आइटम पर वापस जाने की सुविधा है, तो मुफ़्त टियर का कोई उपयोगकर्ता Assistant से पिछले आइटम पर वापस जाने के लिए कहता है, तो आपको गड़बड़ी का मैसेज दिख सकता है. ज़्यादा जानकारी के लिए, गड़बड़ी ठीक करने से जुड़ा सेक्शन देखें.

आवाज़ से की जाने वाली क्वेरी के सैंपल

यहां कुछ सैंपल क्वेरी दी गई हैं. आपको इन्हें लागू करने के बाद टेस्ट करना चाहिए:

MediaSession कॉलबैक “Ok Google” वाक्यांश का इस्तेमाल करना
onPlay()

“चलाओ.”

“फिर से शुरू करो.”

onPlayFromSearch()
onPlayFromUri()
संगीत

(ऐप्लिकेशन का नाम) पर संगीत या गाने चलाओ.” यह एक खाली क्वेरी है.

(ऐप्लिकेशन का नाम) पर (गाना | कलाकार | एल्बम | शैली | प्लेलिस्ट) चलाओ.”

रेडियो (ऐप्लिकेशन का नाम) पर (फ़्रीक्वेंसी | स्टेशन) चलाओ.”
ऑडियो बुक

(ऐप्लिकेशन का नाम) पर मेरी ऑडियो बुक पढ़ो.”

(ऐप्लिकेशन का नाम) पर (ऑडियो बुक) पढ़ो.”

पॉडकास्ट (ऐप्लिकेशन का नाम) पर (पॉडकास्ट) चलाओ.”
onPause() “रोकें.”
onStop() “बंद करो.”
onSkipToNext() “अगला (गाना | एपिसोड | ट्रैक) चलाओ.”
onSkipToPrevious() “पिछला (गाना | एपिसोड | ट्रैक) चलाओ.”
onSeekTo()

“रीस्टार्ट करो.”

## सेकंड आगे बढ़ाओ.”

## मिनट पहले पर वापस जाओ.”

लागू नहीं (अपनी MediaMetadata अप-टू-डेट रखें) “क्या चल रहा है?”

गड़बड़ियां

मीडिया सेशन के दौरान गड़बड़ियां होने पर, Assistant उन्हें ठीक करती है और उपयोगकर्ताओं को इसकी सूचना देती है. पक्का करें कि आपका मीडिया सेशन, मीडिया सेशन के साथ काम करना में बताए गए तरीके के मुताबिक, अपने PlaybackState में ट्रांसपोर्ट स्टेट और गड़बड़ी के कोड को सही तरीके से अपडेट करता हो. Assistant, getErrorCode() से मिले सभी गड़बड़ी कोड को पहचानता है.

आम तौर पर गलत तरीके से हैंडल किए जाने वाले मामले

यहां गड़बड़ी के कुछ उदाहरण दिए गए हैं. आपको यह पक्का करना चाहिए कि इन्हें सही तरीके से हैंडल किया जा रहा हो:

  • उपयोगकर्ता को साइन इन करना होगा
    • PlaybackState गड़बड़ी के कोड को ERROR_CODE_AUTHENTICATION_EXPIRED पर सेट करें.
    • PlaybackState गड़बड़ी का मैसेज सेट करें.
    • अगर ऑडियो चलाने के लिए ज़रूरी हो, तो PlaybackState की स्थिति को STATE_ERROR पर सेट करें. ऐसा न होने पर, PlaybackState की स्थिति को पहले जैसा ही रहने दें.
  • उपयोगकर्ता ऐसी कार्रवाई का अनुरोध करता है जो उपलब्ध नहीं है
    • PlaybackState गड़बड़ी का कोड सही तरीके से सेट करें. उदाहरण के लिए, अगर कार्रवाई काम नहीं करती है, तो PlaybackState को ERROR_CODE_NOT_SUPPORTED पर सेट करें. इसके अलावा, अगर कार्रवाई साइन-इन से सुरक्षित है, तो PlaybackState को ERROR_CODE_PREMIUM_ACCOUNT_REQUIRED पर सेट करें.
    • PlaybackState गड़बड़ी का मैसेज सेट करें.
    • PlaybackState के बाकी हिस्से को पहले जैसा ही रखें.
  • उपयोगकर्ता ने ऐसे कॉन्टेंट का अनुरोध किया है जो ऐप्लिकेशन में उपलब्ध नहीं है
    • PlaybackState गड़बड़ी का कोड सही तरीके से सेट करें. उदाहरण के लिए, ERROR_CODE_NOT_AVAILABLE_IN_REGION का इस्तेमाल करें.
    • PlaybackState गड़बड़ी का मैसेज सेट करें.
    • प्लेबैक को रोकने के लिए, PlaybackSate की स्थिति को STATE_ERROR पर सेट करें. ऐसा न करने पर, PlaybackState के बाकी हिस्से को पहले जैसा ही रखें.
  • उपयोगकर्ता ने ऐसे कॉन्टेंट का अनुरोध किया है जो पूरी तरह से मेल नहीं खाता. उदाहरण के लिए, फ़्री टियर का इस्तेमाल करने वाला कोई व्यक्ति, ऐसे कॉन्टेंट का अनुरोध करता है जो सिर्फ़ प्रीमियम टियर के उपयोगकर्ताओं के लिए उपलब्ध है.
    • हमारा सुझाव है कि आप कोई गड़बड़ी न दिखाएं. इसके बजाय, आपको खेलने के लिए मिलती-जुलती कोई चीज़ ढूंढने को प्राथमिकता देनी चाहिए. प्लेबैक शुरू होने से पहले, Assistant सबसे सही जवाब देगी.

किसी मकसद से वीडियो चलाना

Assistant, ऑडियो या वीडियो ऐप्लिकेशन लॉन्च कर सकती है. साथ ही, डीप लिंक के साथ इंटेंट भेजकर, कॉन्टेंट चलाना शुरू कर सकती है.

इंटेंट और उसका डीप लिंक अलग-अलग सोर्स से मिल सकता है:

  • जब Assistant किसी मोबाइल ऐप्लिकेशन को शुरू करती है, तो वह Google Search का इस्तेमाल करके मार्क अप किया गया कॉन्टेंट वापस पा सकती है. यह कॉन्टेंट, लिंक के साथ देखने की कार्रवाई की जानकारी देता है.
  • जब Assistant किसी टीवी ऐप्लिकेशन को शुरू करती है, तब आपके ऐप्लिकेशन में टीवी सर्च प्रोवाइडर शामिल होना चाहिए, ताकि मीडिया कॉन्टेंट के यूआरआई दिखाए जा सकें. Assistant, कॉन्टेंट उपलब्ध कराने वाली कंपनी को क्वेरी भेजती है. इससे, डीप लिंक के यूआरआई और वैकल्पिक कार्रवाई वाला इंटेंट वापस मिलना चाहिए. अगर क्वेरी से इंटेंट में कोई कार्रवाई मिलती है, तो Assistant उस कार्रवाई और यूआरआई को आपके ऐप्लिकेशन पर वापस भेज देती है. अगर सेवा देने वाली कंपनी ने कोई कार्रवाई तय नहीं की है, तो Assistant इंटेंट में ACTION_VIEW जोड़ देगी.

Assistant, आपके ऐप्लिकेशन को भेजे गए इंटेंट में EXTRA_START_PLAYBACK और true जोड़ता है. जब आपके ऐप्लिकेशन को EXTRA_START_PLAYBACK वाला इंटेंट मिलता है, तब उसे कॉन्टेंट चलाना शुरू कर देना चाहिए.

ऐक्टिव होने पर इंटेंट मैनेज करना

उपयोगकर्ता, Assistant से कोई कॉन्टेंट चलाने के लिए कह सकते हैं. ऐसा तब भी किया जा सकता है, जब आपका ऐप्लिकेशन पिछले अनुरोध के हिसाब से कॉन्टेंट चला रहा हो. इसका मतलब है कि आपका ऐप्लिकेशन, कॉन्टेंट चलाने के लिए नए इंटेंट पा सकता है. ऐसा तब होगा, जब कॉन्टेंट चलाने की गतिविधि पहले से ही लॉन्च हो चुकी हो और चालू हो.

डीप लिंक के साथ इंटेंट का इस्तेमाल करने वाली गतिविधियों को नए अनुरोधों को हैंडल करने के लिए, onNewIntent() को ओवरराइड करना चाहिए.

वीडियो चलाने के दौरान, Assistant आपके ऐप्लिकेशन को भेजे गए इंटेंट में अतिरिक्त फ़्लैग जोड़ सकती है. खास तौर पर, यह FLAG_ACTIVITY_CLEAR_TOP या FLAG_ACTIVITY_NEW_TASK या दोनों को जोड़ सकती है. आपके कोड को इन फ़्लैग को हैंडल करने की ज़रूरत नहीं है. हालाँकि, Android सिस्टम इनका जवाब देता है. ऐसा हो सकता है कि जब पिछला यूआरआई अब भी चल रहा हो और उसी समय नए यूआरआई के साथ दूसरा प्लेबैक अनुरोध मिले, तो इससे आपके ऐप्लिकेशन के व्यवहार पर असर पड़े. यह जांच करना बेहतर होगा कि इस मामले में आपका ऐप्लिकेशन कैसा जवाब देता है. इस स्थिति को सिम्युलेट करने के लिए, adb कमांड लाइन टूल का इस्तेमाल किया जा सकता है. इसमें कॉन्स्टेंट 0x14000000, दो फ़्लैग का बूलियन बिटवाइज़ OR होता है:

adb shell 'am start -a android.intent.action.VIEW --ez android.intent.extra.START_PLAYBACK true -d "<first_uri>"' -f 0x14000000
adb shell 'am start -a android.intent.action.VIEW --ez android.intent.extra.START_PLAYBACK true -d "<second_uri>"' -f 0x14000000

किसी सेवा से वीडियो चलाना

अगर आपके ऐप्लिकेशन में media browser service है, तो Assistant से कनेक्ट किया जा सकता है. ऐसे में, Assistant, सेवा के media session से कम्यूनिकेट करके ऐप्लिकेशन को शुरू कर सकती है. मीडिया ब्राउज़र सेवा को कभी भी कोई ऐक्टिविटी लॉन्च नहीं करनी चाहिए. Assistant, आपकी गतिविधि को PendingIntent के आधार पर लॉन्च करेगी. इसे setSessionActivity() की मदद से तय किया जाता है.

मीडिया ब्राउज़र सेवा शुरू करते समय, MediaSession.Token सेट करना न भूलें. वीडियो चलाने से जुड़े काम करने वाले ऐक्शन को हर समय सेट करना न भूलें. इनमें वीडियो शुरू होने के दौरान सेट किए जाने वाले ऐक्शन भी शामिल हैं. Assistant को उम्मीद होती है कि मीडिया ऐप्लिकेशन, Assistant के पहली बार प्लेबैक कमांड भेजने से पहले ही, प्लेबैक ऐक्शन सेट कर देगा.

किसी सेवा से शुरू करने के लिए, Assistant, मीडिया ब्राउज़र क्लाइंट एपीआई लागू करती है. यह TransportControls कॉल करता है. इससे आपके ऐप्लिकेशन के मीडिया सेशन पर, PLAY ऐक्शन कॉलबैक ट्रिगर होते हैं.

नीचे दिए गए डायग्राम में, Assistant से जनरेट किए गए कॉल और उनसे जुड़े मीडिया सेशन के कॉलबैक का क्रम दिखाया गया है. (तैयार किए गए कॉलबैक सिर्फ़ तब भेजे जाते हैं, जब आपका ऐप्लिकेशन उन्हें सपोर्ट करता हो.) सभी कॉल एसिंक्रोनस होते हैं. Assistant, आपके ऐप्लिकेशन से किसी जवाब का इंतज़ार नहीं करती है.

मीडिया सेशन की मदद से वीडियो चलाना

जब कोई उपयोगकर्ता, Assistant को गाने चलाने का निर्देश देता है, तो Assistant एक छोटी सूचना देती है. सूचना पूरी होने के बाद, Assistant 'चलाएं' कार्रवाई शुरू करती है. यह किसी खास प्लेबैक स्थिति का इंतज़ार नहीं करता.

अगर आपका ऐप्लिकेशन ACTION_PREPARE_* कार्रवाइयों के साथ काम करता है, तो Assistant सूचना शुरू करने से पहले, PREPARE कार्रवाई को कॉल करता है.

MediaBrowserService से कनेक्ट करना

किसी सेवा का इस्तेमाल करके ऐप्लिकेशन शुरू करने के लिए, Assistant को ऐप्लिकेशन की MediaBrowserService से कनेक्ट होना चाहिए. साथ ही, उसे MediaSession.Token को वापस पाना चाहिए. कनेक्शन के अनुरोधों को सेवा के onGetRoot() तरीके से मैनेज किया जाता है. अनुरोधों को मैनेज करने के दो तरीके हैं:

  • कनेक्शन के सभी अनुरोध स्वीकार करना
  • सिर्फ़ Assistant ऐप्लिकेशन से मिले कनेक्शन के अनुरोध स्वीकार करें

कनेक्शन के सभी अनुरोध स्वीकार करना

Assistant को आपके मीडिया सेशन पर कमांड भेजने की अनुमति देने के लिए, आपको BrowserRoot वापस भेजना होगा. सबसे आसान तरीका यह है कि सभी MediaBrowser ऐप्लिकेशन को, MediaBrowserService से कनेक्ट करने की अनुमति दी जाए. आपको एक नॉन-नल BrowserRoot ऑब्जेक्ट वापस करना होगा. Universal Music Player से मिला कोड यहां दिया गया है:

Kotlin

override fun onGetRoot(
        clientPackageName: String,
        clientUid: Int,
        rootHints: Bundle?
): BrowserRoot? {

    // To ensure you are not allowing any arbitrary app to browse your app's contents, you
    // need to check the origin:
    if (!packageValidator.isCallerAllowed(this, clientPackageName, clientUid)) {
        // If the request comes from an untrusted package, return an empty browser root.
        // If you return null, then the media browser will not be able to connect and
        // no further calls will be made to other media browsing methods.
        Log.i(TAG, "OnGetRoot: Browsing NOT ALLOWED for unknown caller. Returning empty "
                + "browser root so all apps can use MediaController. $clientPackageName")
        return MediaBrowserServiceCompat.BrowserRoot(MEDIA_ID_EMPTY_ROOT, null)
    }

    // Return browser roots for browsing...
}

Java

@Override
public BrowserRoot onGetRoot(@NonNull String clientPackageName, int clientUid,
                             Bundle rootHints) {

    // To ensure you are not allowing any arbitrary app to browse your app's contents, you
    // need to check the origin:
    if (!packageValidator.isCallerAllowed(this, clientPackageName, clientUid)) {
        // If the request comes from an untrusted package, return an empty browser root.
        // If you return null, then the media browser will not be able to connect and
        // no further calls will be made to other media browsing methods.
        LogHelper.i(TAG, "OnGetRoot: Browsing NOT ALLOWED for unknown caller. "
                + "Returning empty browser root so all apps can use MediaController."
                + clientPackageName);
        return new MediaBrowserServiceCompat.BrowserRoot(MEDIA_ID_EMPTY_ROOT, null);
    }

    // Return browser roots for browsing...
}

Assistant ऐप्लिकेशन के पैकेज और हस्ताक्षर को स्वीकार करें

Assistant को मीडिया ब्राउज़र सेवा से कनेक्ट करने की अनुमति दी जा सकती है. इसके लिए, आपको उसके पैकेज का नाम और हस्ताक्षर देखना होगा. आपके ऐप्लिकेशन को MediaBrowserService के onGetRoot तरीके में पैकेज का नाम मिलेगा. Assistant को आपके मीडिया सेशन में निर्देश भेजने की अनुमति देने के लिए, आपको BrowserRoot वापस भेजना होगा. यूनिवर्सल म्यूज़िक प्लेयर सैंपल, पैकेज के जाने-पहचाने नामों और हस्ताक्षर की सूची बनाए रखता है. यहां उन पैकेज के नाम और हस्ताक्षर दिए गए हैं जिनका इस्तेमाल Google Assistant करती है.

<signature name="Google" package="com.google.android.googlequicksearchbox">
    <key release="false">19:75:b2:f1:71:77:bc:89:a5:df:f3:1f:9e:64:a6:ca:e2:81:a5:3d:c1:d1:d5:9b:1d:14:7f:e1:c8:2a:fa:00</key>
    <key release="true">f0:fd:6c:5b:41:0f:25:cb:25:c3:b5:33:46:c8:97:2f:ae:30:f8:ee:74:11:df:91:04:80:ad:6b:2d:60:db:83</key>
</signature>

<signature name="Google Assistant on Android Automotive OS" package="com.google.android.carassistant">
    <key release="false">17:E2:81:11:06:2F:97:A8:60:79:7A:83:70:5B:F8:2C:7C:C0:29:35:56:6D:46:22:BC:4E:CF:EE:1B:EB:F8:15</key>
    <key release="true">74:B6:FB:F7:10:E8:D9:0D:44:D3:40:12:58:89:B4:23:06:A6:2C:43:79:D0:E5:A6:62:20:E3:A6:8A:BF:90:E2</key>
</signature>