পরিবহন নিয়ন্ত্রণ ব্যবহার করুন

রচনার সাথে আরও ভাল তৈরি করুন৷
Android TV OS এর জন্য Jetpack Compose ব্যবহার করে ন্যূনতম কোড সহ সুন্দর UI তৈরি করুন।

Leanback UI টুলকিটে প্লেব্যাক নিয়ন্ত্রণ রয়েছে যা একটি উন্নত ব্যবহারকারীর অভিজ্ঞতা প্রদান করে। ভিডিও অ্যাপ্লিকেশানগুলির জন্য, ট্রান্সপোর্ট কন্ট্রোলগুলি সামনে এবং পিছনের নিয়ন্ত্রণগুলির সাথে ভিডিও স্ক্রাবিং সমর্থন করে৷ স্ক্রাব করার সময় ডিসপ্লে থাম্বনেইল দেখায় যা ভিডিওতে নেভিগেট করতে সাহায্য করে।

লাইব্রেরিতে বিমূর্ত ক্লাসের পাশাপাশি প্রি-বিল্ট, বাক্সের বাইরের বাস্তবায়ন অন্তর্ভুক্ত রয়েছে যা বিকাশকারীদের জন্য আরও দানাদার নিয়ন্ত্রণ প্রদান করে। পূর্বনির্মাণ বাস্তবায়ন ব্যবহার করে, আপনি খুব বেশি কোডিং ছাড়াই দ্রুত একটি বৈশিষ্ট্য সমৃদ্ধ অ্যাপ তৈরি করতে পারেন। আপনার যদি আরও কাস্টমাইজেশনের প্রয়োজন হয়, আপনি লাইব্রেরির যে কোনো পূর্বনির্মাণ উপাদান প্রসারিত করতে পারেন।

কন্ট্রোল এবং প্লেয়ার

Leanback UI টুলকিট ট্রান্সপোর্ট কন্ট্রোল UI কে প্লেয়ার থেকে আলাদা করে যা ভিডিও ব্যাক করে। এটি দুটি উপাদান দিয়ে সম্পন্ন করা হয়: পরিবহন নিয়ন্ত্রণ (এবং ঐচ্ছিকভাবে ভিডিও) প্রদর্শনের জন্য একটি প্লেব্যাক সমর্থন খণ্ড এবং একটি মিডিয়া প্লেয়ারকে এনক্যাপসুলেট করার জন্য একটি প্লেয়ার অ্যাডাপ্টার

প্লেব্যাক খণ্ড

আপনার অ্যাপের UI অ্যাক্টিভিটি একটি PlaybackSupportFragment বা একটি VideoSupportFragment ব্যবহার করা উচিত। উভয়েই লিনব্যাক পরিবহন নিয়ন্ত্রণ রয়েছে:

  • একটি PlaybackSupportFragment এর পরিবহন নিয়ন্ত্রণগুলিকে প্রয়োজন অনুযায়ী লুকিয়ে/দেখাতে অ্যানিমেট করে।
  • একটি VideoSupportFragment PlaybackSupportFragment প্রসারিত করে এবং ভিডিও রেন্ডার করার জন্য একটি SurfaceView আছে।

আপনি UI উন্নত করতে একটি খণ্ডের ObjectAdapter কাস্টমাইজ করতে পারেন। উদাহরণস্বরূপ, একটি "সম্পর্কিত ভিডিও" সারি যোগ করতে setAdapter() ব্যবহার করুন।

প্লেয়ার অ্যাডাপ্টার

PlayerAdapter হল একটি বিমূর্ত শ্রেণী যা অন্তর্নিহিত মিডিয়া প্লেয়ারকে নিয়ন্ত্রণ করে। বিকাশকারীরা পূর্ব-নির্মিত MediaPlayerAdapter বাস্তবায়ন বেছে নিতে পারেন, অথবা এই শ্রেণীর নিজস্ব বাস্তবায়ন লিখতে পারেন।

একসাথে টুকরা glueing

প্লেব্যাক খণ্ডটিকে প্লেয়ারের সাথে সংযুক্ত করতে আপনাকে অবশ্যই কিছু "নিয়ন্ত্রণ আঠালো" ব্যবহার করতে হবে। লিনব্যাক লাইব্রেরি দুটি ধরণের আঠালো সরবরাহ করে:

  • PlaybackBannerControlGlue প্লেব্যাক ফ্র্যাগমেন্টে পরিবহন নিয়ন্ত্রণগুলিকে "পুরানো শৈলীতে" আঁকে, সেগুলিকে একটি অস্বচ্ছ পটভূমিতে স্থাপন করে। ( PlaybackBannerControlGlue PlaybackControlGlue প্রতিস্থাপন করে, যা অবমূল্যায়িত হয়েছে।)
  • PlaybackTransportControlGlue একটি স্বচ্ছ ব্যাকগ্রাউন্ড সহ "নতুন শৈলী" নিয়ন্ত্রণ ব্যবহার করে।

leanback পরিবহন নিয়ন্ত্রণ আঠালো

আপনি যদি চান যে আপনার অ্যাপ ভিডিও স্ক্রাবিং সমর্থন করে তাহলে আপনাকে অবশ্যই PlaybackTransportControlGlue ব্যবহার করতে হবে।

এছাড়াও আপনাকে একটি "আঠালো হোস্ট" নির্দিষ্ট করতে হবে যা প্লেব্যাক ফ্র্যাগমেন্টের সাথে আঠাকে আবদ্ধ করে, UI-তে পরিবহন নিয়ন্ত্রণগুলি আঁকে এবং তাদের অবস্থা বজায় রাখে এবং ট্রান্সপোর্ট কন্ট্রোল ইভেন্টগুলিকে আঠালোতে ফিরিয়ে দেয়। হোস্ট অবশ্যই প্লেব্যাক ফ্র্যাগমেন্ট টাইপের সাথে মেলে। PlaybackSupportFragmentGlueHost একটি PlaybackFragment এর সাথে এবং VideoSupportFragmentGlueHost একটি VideoFragment এর সাথে ব্যবহার করুন।

এখানে একটি দৃষ্টান্ত দেখানো হয়েছে যে কীভাবে একটি লিনব্যাক পরিবহন নিয়ন্ত্রণের অংশগুলি একসাথে ফিট করে:

leanback পরিবহন নিয়ন্ত্রণ আঠালো

যে কোডটি আপনার অ্যাপটিকে একসাথে আঠালো করে সেটি PlaybackSupportFragment বা VideoSupportFragment ভিতরে থাকা উচিত যা UI কে সংজ্ঞায়িত করে।

নিম্নলিখিত উদাহরণে, অ্যাপটি PlaybackTransportControlGlue এর একটি উদাহরণ তৈরি করে, এটির নাম দেয় playerGlue , এবং একটি নতুন-নির্মিত MediaPlayerAdapter এর সাথে এর VideoSupportFragment সংযোগ করে। যেহেতু এটি একটি VideoSupportFragment সেটআপ কোড একটি VideoSupportFragmentGlueHost কে playerGlue এ সংযুক্ত করতে setHost() কল করে। কোডটি ক্লাসের ভিতরে অন্তর্ভুক্ত করা হয়েছে যা VideoSupportFragment প্রসারিত করে।

কোটলিন

class MyVideoFragment : VideoSupportFragment() {

  fun onCreate(savedInstanceState: Bundle) {
      super.onCreate(savedInstanceState)
      val playerGlue = PlaybackTransportControlGlue(getActivity(),
          MediaPlayerAdapter(getActivity()))
      playerGlue.setHost(VideoSupportFragmentGlueHost(this))
      playerGlue.addPlayerCallback(object : PlaybackGlue.PlayerCallback() {
          override fun onPreparedStateChanged(glue: PlaybackGlue) {
              if (glue.isPrepared()) {
                  playerGlue.seekProvider = MySeekProvider()
                  playerGlue.play()
              }
          }
      })
      playerGlue.setSubtitle("Leanback artist")
      playerGlue.setTitle("Leanback team at work")
      val uriPath = "android.resource://com.example.android.leanback/raw/video"
      playerGlue.getPlayerAdapter().setDataSource(Uri.parse(uriPath))
  }
}

জাভা

public class MyVideoFragment extends VideoSupportFragment {

  @Override
  public void onCreate(Bundle savedInstanceState) {
      super.onCreate(savedInstanceState);
      final PlaybackTransportControlGlue<MediaPlayerAdapter> playerGlue =
              new PlaybackTransportControlGlue(getActivity(),
                      new MediaPlayerAdapter(getActivity()));
      playerGlue.setHost(new VideoSupportFragmentGlueHost(this));
      playerGlue.addPlayerCallback(new PlaybackGlue.PlayerCallback() {
          @Override
          public void onPreparedStateChanged(PlaybackGlue glue) {
              if (glue.isPrepared()) {
                  playerGlue.setSeekProvider(new MySeekProvider());
                  playerGlue.play();
              }
          }
      });
      playerGlue.setSubtitle("Leanback artist");
      playerGlue.setTitle("Leanback team at work");
      String uriPath = "android.resource://com.example.android.leanback/raw/video";
      playerGlue.getPlayerAdapter().setDataSource(Uri.parse(uriPath));
  }
}

নোট করুন যে সেটআপ কোডটি মিডিয়া প্লেয়ার থেকে ইভেন্টগুলি পরিচালনা করার জন্য একটি PlayerAdapter.Callback ও সংজ্ঞায়িত করে৷

UI আঠালো কাস্টমাইজ করা

আপনি PlaybackBannerControlGlue এবং PlaybackTransportControlGlue কাস্টমাইজ করতে পারেন PlaybackControlsRow পরিবর্তন করতে।

শিরোনাম এবং বিবরণ কাস্টমাইজ করা

প্লেব্যাক নিয়ন্ত্রণের শীর্ষে শিরোনাম এবং বিবরণ কাস্টমাইজ করতে, onCreateRowPresenter() ওভাররাইড করুন :

কোটলিন

override fun onCreateRowPresenter(): PlaybackRowPresenter {
    return super.onCreateRowPresenter().apply {
        (this as? PlaybackTransportRowPresenter)
                ?.setDescriptionPresenter(MyCustomDescriptionPresenter())
    }
}

জাভা

@Override
protected PlaybackRowPresenter onCreateRowPresenter() {
  PlaybackTransportRowPresenter presenter = (PlaybackTransportRowPresenter) super.onCreateRowPresenter();
  presenter.setDescriptionPresenter(new MyCustomDescriptionPresenter());
  return presenter;
}

নিয়ন্ত্রণ যোগ করা হচ্ছে

কন্ট্রোল গ্লু PlaybackControlsRow ক্রিয়াগুলির জন্য নিয়ন্ত্রণগুলি প্রদর্শন করে।

PlaybackControlsRow এর অ্যাকশন দুটি গ্রুপে বরাদ্দ করা হয়েছে: প্রাথমিক অ্যাকশন এবং সেকেন্ডারি অ্যাকশন । প্রাইমারি গ্রুপের কন্ট্রোল সিক বারের উপরে এবং সেকেন্ডারি গ্রুপের কন্ট্রোল সিক বারের নিচে প্রদর্শিত হয়। প্রাথমিকভাবে, প্লে/পজ বোতামের জন্য শুধুমাত্র একটি একক প্রাথমিক অ্যাকশন আছে, আর কোনো সেকেন্ডারি অ্যাকশন নেই।

আপনি onCreatePrimaryActions() এবং onCreateSecondaryActions() ওভাররাইড করে প্রাথমিক এবং মাধ্যমিক গোষ্ঠীতে অ্যাকশন যোগ করতে পারেন।

কোটলিন

private lateinit var repeatAction: PlaybackControlsRow.RepeatAction
private lateinit var pipAction: PlaybackControlsRow.PictureInPictureAction
private lateinit var thumbsUpAction: PlaybackControlsRow.ThumbsUpAction
private lateinit var thumbsDownAction: PlaybackControlsRow.ThumbsDownAction
private lateinit var skipPreviousAction: PlaybackControlsRow.SkipPreviousAction
private lateinit var skipNextAction: PlaybackControlsRow.SkipNextAction
private lateinit var fastForwardAction: PlaybackControlsRow.FastForwardAction
private lateinit var rewindAction: PlaybackControlsRow.RewindAction

override fun onCreatePrimaryActions(primaryActionsAdapter: ArrayObjectAdapter) {
    // Order matters, super.onCreatePrimaryActions() will create the play / pause action.
    // Will display as follows:
    // play/pause, previous, rewind, fast forward, next
    //   > /||      |<        <<        >>         >|
    super.onCreatePrimaryActions(primaryActionsAdapter)
    primaryActionsAdapter.apply {
        add(skipPreviousAction)
        add(rewindAction)
        add(fastForwardAction)
        add(skipNextAction)
    }
}

override fun onCreateSecondaryActions(adapter: ArrayObjectAdapter?) {
    super.onCreateSecondaryActions(adapter)
    adapter?.apply {
        add(thumbsDownAction)
        add(thumbsUpAction)
    }
}

জাভা

private PlaybackControlsRow.RepeatAction repeatAction;
private PlaybackControlsRow.PictureInPictureAction pipAction;
private PlaybackControlsRow.ThumbsUpAction thumbsUpAction;
private PlaybackControlsRow.ThumbsDownAction thumbsDownAction;
private PlaybackControlsRow.SkipPreviousAction skipPreviousAction;
private PlaybackControlsRow.SkipNextAction skipNextAction;
private PlaybackControlsRow.FastForwardAction fastForwardAction;
private PlaybackControlsRow.RewindAction rewindAction;

@Override
protected void onCreatePrimaryActions(ArrayObjectAdapter primaryActionsAdapter) {
    // Order matters, super.onCreatePrimaryActions() will create the play / pause action.
    // Will display as follows:
    // play/pause, previous, rewind, fast forward, next
    //   > /||      |<        <<        >>         >|
    super.onCreatePrimaryActions(primaryActionsAdapter);
    primaryActionsAdapter.add(skipPreviousAction);
    primaryActionsAdapter.add(rewindAction);
    primaryActionsAdapter.add(fastForwardAction);
    primaryActionsAdapter.add(skipNextAction);
}

@Override
protected void onCreateSecondaryActions(ArrayObjectAdapter adapter) {
    super.onCreateSecondaryActions(adapter);
    adapter.add(thumbsDownAction);
    adapter.add(thumbsUpAction);
}

নতুন অ্যাকশনগুলি পরিচালনা করতে আপনাকে অবশ্যই onActionClicked() ওভাররাইড করতে হবে।

কোটলিন

override fun onActionClicked(action: Action) {
    when(action) {
        rewindAction -> {
            // Handle Rewind
        }
        fastForwardAction -> {
            // Handle FastForward
        }
        thumbsDownAction -> {
            // Handle ThumbsDown
        }
        thumbsUpAction -> {
            // Handle ThumbsUp
        }
        else ->
            // The superclass handles play/pause and delegates next/previous actions to abstract methods,
            // so those two methods should be overridden rather than handling the actions here.
            super.onActionClicked(action)
    }
}

override fun next() {
    // Skip to next item in playlist.
}

override fun previous() {
    // Skip to previous item in playlist.
}

জাভা

@Override
public void onActionClicked(Action action) {
    if (action == rewindAction) {
        // Handle Rewind
    } else if (action == fastForwardAction ) {
        // Handle FastForward
    } else if (action == thumbsDownAction) {
        // Handle ThumbsDown
    } else if (action == thumbsUpAction) {
        // Handle ThumbsUp
    } else {
        // The superclass handles play/pause and delegates next/previous actions to abstract methods,
        // so those two methods should be overridden rather than handling the actions here.
        super.onActionClicked(action);
    }
}

@Override
public void next() {
    // Skip to next item in playlist.
}

@Override
public void previous() {
    // Skip to previous item in playlist.
}

বিশেষ ক্ষেত্রে, আপনি কাস্টম নিয়ন্ত্রণ রেন্ডার করার জন্য আপনার নিজস্ব PlaybackTransportRowPresenter প্রয়োগ করতে চাইতে পারেন এবং PlaybackSeekUi ব্যবহার করে অ্যাকশন খোঁজার জন্য প্রতিক্রিয়া জানাতে পারেন।

ভিডিও স্ক্রাবিং

যদি আপনার অ্যাপটি একটি VideoSupportFragment ব্যবহার করে এবং আপনি ভিডিও স্ক্রাবিং সমর্থন করতে চান।

স্ক্রাবিং

আপনাকে PlaybackSeekDataProvider এর একটি বাস্তবায়ন প্রদান করতে হবে। এই উপাদানটি স্ক্রল করার সময় ব্যবহৃত ভিডিও থাম্বনেল প্রদান করে। PlaybackSeekDataProvider প্রসারিত করে আপনাকে অবশ্যই আপনার নিজের প্রদানকারীকে বাস্তবায়ন করতে হবে। Leanback শোকেস অ্যাপে উদাহরণটি দেখুন। .