चैनल के डेटा का इस्तेमाल करना

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

आज़माएं टीवी इनपुट सेवा का नमूना.

अनुमति लें

टीवी इनपुट को ईपीजी डेटा के साथ काम करने के लिए, इसकी Android मेनिफ़ेस्ट फ़ाइल में इस तरह अनुमति लिखने की अनुमति दें:

<uses-permission android:name="com.android.providers.tv.permission.WRITE_EPG_DATA" />

डेटाबेस में चैनलों को रजिस्टर करना

Android TV का सिस्टम डेटाबेस, टीवी इनपुट के लिए चैनल के डेटा का रिकॉर्ड रखता है. आपके सेटअप में गतिविधि है, तो आपको अपने चैनल डेटा को TvContract.Channels क्लास:

हालांकि टीवी इनपुट फ़्रेमवर्क, पारंपरिक ब्रॉडकास्ट और ओवर–द–टॉप (OTT) कॉन्टेंट भी बिना किसी परेशानी के सबमिट किया जा सकता है. इसलिए, नीचे दिए गए कॉलम इसके अलावा, परंपरागत ब्रॉडकास्ट चैनलों की पहचान बेहतर तरीके से करने के लिए:

अगर आपको अपने चैनलों के लिए ऐप्लिकेशन के लिंक की जानकारी देनी है, तो कुछ अतिरिक्त फ़ील्ड अपडेट करें. ऐप्लिकेशन लिंक फ़ील्ड के बारे में ज़्यादा जानकारी के लिए, देखें ऐप्लिकेशन के लिंक की जानकारी जोड़ें.

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

अपने बैकएंड सर्वर और सेटअप में, चैनल का मेटाडेटा (एक्सएमएल, JSON या किसी भी अन्य फ़ॉर्मैट में) हासिल करें गतिविधि, सिस्टम डेटाबेस की वैल्यू को इस तरह मैप करती है:

Kotlin

val values = ContentValues().apply {
    put(TvContract.Channels.COLUMN_DISPLAY_NUMBER, channel.number)
    put(TvContract.Channels.COLUMN_DISPLAY_NAME, channel.name)
    put(TvContract.Channels.COLUMN_ORIGINAL_NETWORK_ID, channel.originalNetworkId)
    put(TvContract.Channels.COLUMN_TRANSPORT_STREAM_ID, channel.transportStreamId)
    put(TvContract.Channels.COLUMN_SERVICE_ID, channel.serviceId)
    put(TvContract.Channels.COLUMN_VIDEO_FORMAT, channel.videoFormat)
}
val uri = context.contentResolver.insert(TvContract.Channels.CONTENT_URI, values)

Java

ContentValues values = new ContentValues();

values.put(Channels.COLUMN_DISPLAY_NUMBER, channel.number);
values.put(Channels.COLUMN_DISPLAY_NAME, channel.name);
values.put(Channels.COLUMN_ORIGINAL_NETWORK_ID, channel.originalNetworkId);
values.put(Channels.COLUMN_TRANSPORT_STREAM_ID, channel.transportStreamId);
values.put(Channels.COLUMN_SERVICE_ID, channel.serviceId);
values.put(Channels.COLUMN_VIDEO_FORMAT, channel.videoFormat);

Uri uri = context.getContentResolver().insert(TvContract.Channels.CONTENT_URI, values);

ऊपर दिए गए उदाहरण में, channel एक ऑब्जेक्ट है जिसमें चैनल का मेटाडेटा बैकएंड सर्वर.

चैनल और कार्यक्रम की जानकारी देना

सिस्टम टीवी ऐप्लिकेशन, उपयोगकर्ताओं को चैनल और प्रोग्राम की जानकारी तब दिखाता है, जब वे चैनल देखते हैं, जैसा कि पहली इमेज में दिखाया गया है. यह पक्का करने के लिए कि चैनल और प्रोग्राम की जानकारी, सिस्टम टीवी ऐप्लिकेशन के चैनल और प्रोग्राम की जानकारी देने वाले व्यक्ति को, नीचे दिए गए दिशा-निर्देशों का पालन करना होगा.

  1. चैनल नंबर (COLUMN_DISPLAY_NUMBER)
  2. आइकॉन (android:icon टीवी इनपुट का मेनिफ़ेस्ट)
  3. कार्यक्रम की जानकारी (COLUMN_SHORT_DESCRIPTION)
  4. कार्यक्रम का शीर्षक (COLUMN_TITLE)
  5. चैनल का लोगो (TvContract.Channels.Logo)
    • आस-पास के टेक्स्ट से मेल खाने के लिए #EEEEEE रंग का इस्तेमाल करें
    • पैडिंग (जगह) शामिल न करें
  6. पोस्टर आर्ट (COLUMN_POSTER_ART_URI)
    • आसपेक्ट रेशियो (चौड़ाई-ऊंचाई का अनुपात) 16:9 और 4:3 के बीच होना चाहिए

पहला डायग्राम. सिस्टम टीवी ऐप्लिकेशन का चैनल और प्रोग्राम की जानकारी देने वाला.

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

दूसरा डायग्राम. सिस्टम टीवी ऐप्लिकेशन कार्यक्रम की गाइड.

चैनल का डेटा अपडेट करना

मौजूदा चैनल का डेटा अपडेट करते समय, update() अभी तक किसी भी व्यक्ति ने चेक इन नहीं किया है शामिल करने का सुझाव दिया जाता है. आपको डेटा के मौजूदा वर्शन की पहचान करने में मदद मिलेगी Channels.COLUMN_VERSION_NUMBER का इस्तेमाल करके और Programs.COLUMN_VERSION_NUMBER अपडेट करने के लिए रिकॉर्ड चुनते समय.

ध्यान दें: ContentProvider में चैनल का डेटा जोड़ा जा रहा है समय लग सकता है. मौजूदा प्रोग्राम जोड़ें (जो मौजूदा समय से दो घंटों के अंदर हों) सिर्फ़ तब, जब आप अपने EpgSyncJobService को बाकी डेटा अपडेट करने के लिए कॉन्फ़िगर करें में रखा जाता है. यहां जाएं: Android TV Live TV का सैंपल ऐप्लिकेशन देखें.

चैनल डेटा बैच में लोड हो रहा है

चैनल के ज़्यादा डेटा के साथ सिस्टम डेटाबेस को अपडेट करते समय, ContentResolver का इस्तेमाल करें applyBatch() या bulkInsert() तरीका. यहां एक उदाहरण दिया गया है, जिसमें applyBatch() का इस्तेमाल किया गया है:

Kotlin

val ops = ArrayList<ContentProviderOperation>()
val programsCount = channelInfo.mPrograms.size
channelInfo.mPrograms.forEachIndexed { index, program ->
    ops += ContentProviderOperation.newInsert(
            TvContract.Programs.CONTENT_URI).run {
        withValues(programs[index])
        withValue(TvContract.Programs.COLUMN_START_TIME_UTC_MILLIS, programStartSec * 1000)
        withValue(
                TvContract.Programs.COLUMN_END_TIME_UTC_MILLIS,
                (programStartSec + program.durationSec) * 1000
        )
        build()
    }
    programStartSec += program.durationSec
    if (index % 100 == 99 || index == programsCount - 1) {
        try {
            contentResolver.applyBatch(TvContract.AUTHORITY, ops)
        } catch (e: RemoteException) {
            Log.e(TAG, "Failed to insert programs.", e)
            return
        } catch (e: OperationApplicationException) {
            Log.e(TAG, "Failed to insert programs.", e)
            return
        }
        ops.clear()
    }
}

Java

ArrayList<ContentProviderOperation> ops = new ArrayList<>();
int programsCount = channelInfo.mPrograms.size();
for (int j = 0; j < programsCount; ++j) {
    ProgramInfo program = channelInfo.mPrograms.get(j);
    ops.add(ContentProviderOperation.newInsert(
            TvContract.Programs.CONTENT_URI)
            .withValues(programs.get(j))
            .withValue(Programs.COLUMN_START_TIME_UTC_MILLIS,
                    programStartSec * 1000)
            .withValue(Programs.COLUMN_END_TIME_UTC_MILLIS,
                    (programStartSec + program.durationSec) * 1000)
            .build());
    programStartSec = programStartSec + program.durationSec;
    if (j % 100 == 99 || j == programsCount - 1) {
        try {
            getContentResolver().applyBatch(TvContract.AUTHORITY, ops);
        } catch (RemoteException | OperationApplicationException e) {
            Log.e(TAG, "Failed to insert programs.", e);
            return;
        }
        ops.clear();
    }
}

चैनल के डेटा को एसिंक्रोनस तरीके से प्रोसेस करें

डेटा में बदलाव करना, जैसे कि सर्वर से स्ट्रीम फ़ेच करना या डेटाबेस को ऐक्सेस करना यूज़र इंटरफ़ेस (यूआई) थ्रेड को ब्लॉक न करें. AsyncTask का इस्तेमाल करना एक एसिंक्रोनस रूप से अपडेट करने का तरीका है. उदाहरण के लिए, किसी बैकएंड सर्वर से चैनल की जानकारी लोड करते समय, AsyncTask का इस्तेमाल इस तरह किया जा सकता है:

Kotlin

private class LoadTvInputTask(val context: Context) : AsyncTask<Uri, Unit, Unit>() {

    override fun doInBackground(vararg uris: Uri) {
        try {
            fetchUri(uris[0])
        } catch (e: IOException) {
            Log.d("LoadTvInputTask", "fetchUri error")
        }
    }

    @Throws(IOException::class)
    private fun fetchUri(videoUri: Uri) {
        context.contentResolver.openInputStream(videoUri).use { inputStream ->
            Xml.newPullParser().also { parser ->
                try {
                    parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, false)
                    parser.setInput(inputStream, null)
                    sTvInput = ChannelXMLParser.parseTvInput(parser)
                    sSampleChannels = ChannelXMLParser.parseChannelXML(parser)
                } catch (e: XmlPullParserException) {
                    e.printStackTrace()
                }
            }
        }
    }
}

Java

private static class LoadTvInputTask extends AsyncTask<Uri, Void, Void> {

    private Context mContext;

    public LoadTvInputTask(Context context) {
        mContext = context;
    }

    @Override
    protected Void doInBackground(Uri... uris) {
        try {
            fetchUri(uris[0]);
        } catch (IOException e) {
          Log.d("LoadTvInputTask", "fetchUri error");
        }
        return null;
    }

    private void fetchUri(Uri videoUri) throws IOException {
        InputStream inputStream = null;
        try {
            inputStream = mContext.getContentResolver().openInputStream(videoUri);
            XmlPullParser parser = Xml.newPullParser();
            try {
                parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, false);
                parser.setInput(inputStream, null);
                sTvInput = ChannelXMLParser.parseTvInput(parser);
                sSampleChannels = ChannelXMLParser.parseChannelXML(parser);
            } catch (XmlPullParserException e) {
                e.printStackTrace();
            }
        } finally {
            if (inputStream != null) {
                inputStream.close();
            }
        }
    }
}

अगर आपको ईपीजी डेटा को नियमित तौर पर अपडेट करना है, तो WorkManager इस्तेमाल में न होने के दौरान अपडेट प्रक्रिया को चलाने के लिए, जैसे कि हर दिन सुबह 3:00 बजे.

डेटा अपडेट टास्क को यूज़र इंटरफ़ेस (यूआई) थ्रेड से अलग करने की अन्य तकनीकों में, HandlerThread क्लास या Looper का इस्तेमाल करके खुद क्लास लागू की जा सकती है और Handler क्लास. देखें ज़्यादा जानकारी के लिए प्रोसेस और थ्रेड देखें.

चैनल, ऐप्लिकेशन के लिंक का इस्तेमाल कर सकते हैं, ताकि उपयोगकर्ता आसानी से मिलते-जुलते ऐप्लिकेशन को लॉन्च कर सकें चैनल का कॉन्टेंट देखने के दौरान गतिविधि. चैनल ऐप्लिकेशन इस्तेमाल करें ऐप्लिकेशन लिंक करने पर, लोगों की दिलचस्पी बढ़ाने के लिए, गतिविधियों को लॉन्च किया जा सकेगा या अतिरिक्त कॉन्टेंट शामिल है. उदाहरण के लिए, ऐप्लिकेशन लिंक का इस्तेमाल किया जा सकता है इसके लिए, आपको ये काम करने होंगे:

  • मिलता-जुलता कॉन्टेंट खोजने और खरीदने के लिए, उपयोगकर्ता की मदद करें.
  • मौजूदा समय में चल रहे कॉन्टेंट के बारे में ज़्यादा जानकारी दें.
  • एपिसोड में दिखाया जाने वाला कॉन्टेंट देखते समय, अगला एपिसोड इस सीरीज़ शामिल है.
  • उपयोगकर्ता को कॉन्टेंट से इंटरैक्ट करने की अनुमति दें—उदाहरण के लिए, रेटिंग दें या समीक्षा करें कॉन्टेंट को चलाने की सुविधा में रुकावट डाले बिना.

जब उपयोगकर्ता चुनें दबाता है, तो ऐप्लिकेशन लिंक दिखते हैं चैनल का कॉन्टेंट देखते समय टीवी का मेन्यू.

पहला डायग्राम. ऐप्लिकेशन के लिंक का उदाहरण चैनल लाइन में तब दिखेगा, जब चैनल का कॉन्टेंट दिख रहा होगा.

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

ऐप्लिकेशन लिंक का चैनल डेटा दें

Android TV, अपने-आप हर चैनल के लिए ऐप्लिकेशन का एक लिंक बनाता है. चैनल के डेटा से ली गई जानकारी का इस्तेमाल करके. ऐप्लिकेशन के लिंक की जानकारी देने के लिए, अपने TvContract.Channels फ़ील्ड:

  • COLUMN_APP_LINK_COLOR - यह इस चैनल के ऐप्लिकेशन लिंक के एक्सेंट का रंग. ऐक्सेंट के रंग के उदाहरण के लिए, इमेज 2, कॉलआउट 3 देखें.
  • COLUMN_APP_LINK_ICON_URI से इस चैनल के ऐप्लिकेशन लिंक के ऐप्लिकेशन बैज आइकॉन का यूआरआई. किसी ऐप्लिकेशन बैज आइकॉन का उदाहरण, दूसरी इमेज, कॉलआउट 2 देखें.
  • COLUMN_APP_LINK_INTENT_URI से इस चैनल के लिए ऐप्लिकेशन लिंक का इंटेंट यूआरआई. आपके पास यूआरआई बनाने का विकल्प है इसके साथ toUri(int) का इस्तेमाल किया जा रहा है URI_INTENT_SCHEME और यूआरआई को वापस मूल इंटेंट में parseUri().
  • COLUMN_APP_LINK_POSTER_ART_URI अभी तक किसी भी व्यक्ति ने चेक इन नहीं किया है - ऐप्लिकेशन लिंक के बैकग्राउंड के तौर पर इस्तेमाल किए गए पोस्टर आर्ट का यूआरआई इस चैनल के लिए. पोस्टर इमेज के उदाहरण के लिए, दूसरी इमेज, कॉलआउट 1 देखें.
  • COLUMN_APP_LINK_TEXT से इस चैनल के लिए ऐप्लिकेशन लिंक का जानकारी देने वाला लिंक टेक्स्ट. उदाहरण के लिए ऐप्लिकेशन लिंक की जानकारी के लिए, दूसरी इमेज में टेक्स्ट देखें.

दूसरा डायग्राम. ऐप्लिकेशन लिंक की जानकारी.

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

  • इंटेंट यूआरआई के लिए (COLUMN_APP_LINK_INTENT_URI), सिस्टम ACTION_MAIN का इस्तेमाल करता है CATEGORY_LEANBACK_LAUNCHER श्रेणी के लिए गतिविधि, आमतौर पर ऐप्लिकेशन मेनिफ़ेस्ट में तय की जाती है. अगर इस गतिविधि की जानकारी नहीं है, तो एक काम न करने वाले ऐप्लिकेशन का लिंक दिखता है—अगर जब उपयोगकर्ता इस पर क्लिक करता है, तो कुछ नहीं होता.
  • जानकारी वाले टेक्स्ट के लिए (COLUMN_APP_LINK_TEXT), सिस्टम "app-name खोलें" का इस्तेमाल करता है. अगर कोई काम करने वाला ऐप्लिकेशन लिंक इंटेंट यूआरआई तय नहीं किया गया है, तो सिस्टम "कोई लिंक उपलब्ध नहीं" का इस्तेमाल करता है.
  • ऐक्सेंट के रंग के लिए (COLUMN_APP_LINK_COLOR), सिस्टम, ऐप्लिकेशन के डिफ़ॉल्ट रंग का इस्तेमाल करता है.
  • पोस्टर इमेज के लिए (COLUMN_APP_LINK_POSTER_ART_URI), सिस्टम, ऐप्लिकेशन के होम स्क्रीन बैनर का इस्तेमाल करता है. अगर ऐप्लिकेशन में बैनर दिखाया जाता है, तो सिस्टम एक डिफ़ॉल्ट टीवी ऐप्लिकेशन इमेज का इस्तेमाल करता है.
  • बैज आइकॉन के लिए (COLUMN_APP_LINK_ICON_URI), सिस्टम, ऐप्लिकेशन का नाम दिखाने वाले बैज का इस्तेमाल करता है. यदि सिस्टम पोस्टर इमेज के लिए, ऐप्लिकेशन बैनर या ऐप्लिकेशन की डिफ़ॉल्ट इमेज, ऐप्लिकेशन का बैज नहीं दिखाया गया है.

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