Android TV Leanback (五)(使用leanback创建UI)

来源:互联网 发布:国家域名后缀 编辑:程序博客网 时间:2024/05/17 15:22

创建浏览目录

创建浏览布局

leanback库的BrowseFragment允许您创建一个主要布局,以最少的代码浏览媒体项的类别和行。
代码示例如下:

<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:id="@+id/main_frame"    android:layout_width="match_parent"    android:layout_height="match_parent">    <fragment        android:name="com.example.android.tvleanback.ui.MainFragment"        android:id="@+id/main_browse_fragment"        android:layout_width="match_parent"        android:layout_height="match_parent" /></FrameLayout>

在activity中设置布局:

public class MainActivity extends Activity {    @Override    public void onCreate(Bundle savedInstanceState) {        super.onCreate(savedInstanceState);        setContentView(R.layout.main);    }...

BrowseFragment 用视频数据和UI元素填充视图,并设置布局参数,如图标、标题以及是否启用了类别标题。
setUIElements 用于设置UI元素
setHeadersState 设置类别标题状态

应用程序的子类实现BrowseFragment 的方法,为UI元素设置事件监听,准备背景管理器等,代码示例如下:

public class MainFragment extends BrowseFragment implements        LoaderManager.LoaderCallbacks<HashMap<String, List<Movie>>> {    ...    @Override    public void onActivityCreated(Bundle savedInstanceState) {        super.onActivityCreated(savedInstanceState);        loadVideoData();        prepareBackgroundManager();        setupUIElements();        setupEventListeners();    }...    private void prepareBackgroundManager() {        mBackgroundManager = BackgroundManager.getInstance(getActivity());        mBackgroundManager.attach(getActivity().getWindow());        mDefaultBackground = getResources()            .getDrawable(R.drawable.default_background);        mMetrics = new DisplayMetrics();        getActivity().getWindowManager().getDefaultDisplay().getMetrics(mMetrics);    }    private void setupUIElements() {        setBadgeDrawable(getActivity().getResources()            .getDrawable(R.drawable.videos_by_google_banner));        // Badge, when set, takes precedent over title        setTitle(getString(R.string.browse_title));        setHeadersState(HEADERS_ENABLED);        setHeadersTransitionOnBackEnabled(true);        // set headers background color        setBrandColor(getResources().getColor(R.color.fastlane_background));        // set search icon color        setSearchAffordanceColor(getResources().getColor(R.color.search_opaque));    }    private void loadVideoData() {        VideoProvider.setContext(getActivity());        mVideosUrl = getActivity().getResources().getString(R.string.catalog_url);        getLoaderManager().initLoader(0, null, this);    }    private void setupEventListeners() {        setOnSearchClickedListener(new View.OnClickListener() {            @Override            public void onClick(View view) {                Intent intent = new Intent(getActivity(), SearchActivity.class);                startActivity(intent);           }        });        setOnItemViewClickedListener(new ItemViewClickedListener());        setOnItemViewSelectedListener(new ItemViewSelectedListener());    }...

设置UI元素

browse.png

  • setBadgeDrawable() 将指定的图片放置到browse fragment的右上角,如图UI_Element.png。当调用setTitle()时,字符串将替换图片。
  • setTitle() 设置标题并显示在fragment的右上角,除非调用了setBadgeDrawable()。
  • setHeadersState()和setHeadersTransitionOnBackEnabled() 隐藏或不使用分类标题。
  • setBrandColor() 设置分类标题区块的背景颜色。
  • setSearchAffordanceColor() 设置搜索图标的背景颜色。

自定义分类标题的视图


你可以自定义包括更多视图的复杂布局。
自定义布局如下:

<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"    android:orientation="horizontal"    android:layout_width="match_parent"    android:layout_height="match_parent">    <ImageView        android:id="@+id/header_icon"        android:layout_width="32dp"        android:layout_height="32dp" />    <TextView        android:id="@+id/header_label"        android:layout_marginTop="6dp"        android:layout_width="wrap_content"        android:layout_height="wrap_content" /></LinearLayout>

 使用Presenter实现抽象方法:create,bind,unbind ,如下:

public class IconHeaderItemPresenter extends Presenter {    @Override    public ViewHolder onCreateViewHolder(ViewGroup viewGroup) {        LayoutInflater inflater = (LayoutInflater) viewGroup.getContext()            .getSystemService(Context.LAYOUT_INFLATER_SERVICE);        View view = inflater.inflate(R.layout.icon_header_item, null);        return new ViewHolder(view);    }    @Override    public void onBindViewHolder(ViewHolder viewHolder, Object o) {        HeaderItem headerItem = ((ListRow) o).getHeaderItem();        View rootView = viewHolder.view;        ImageView iconView = (ImageView) rootView.findViewById(R.id.header_icon);        Drawable icon = rootView.getResources().getDrawable(R.drawable.ic_action_video, null);        iconView.setImageDrawable(icon);        TextView label = (TextView) rootView.findViewById(R.id.header_label);        label.setText(headerItem.getName());    }    @Override    public void onUnbindViewHolder(ViewHolder viewHolder) {    // no op    }}

这个例子展示了如何定义一个多视图的复杂的presenter。然而,有种更简单的方式结合TextView和图片,通过使用TextView.drawableLeft属性。这种方式就不需要Imageview。

在fragment中显示,如下:

setHeaderPresenterSelector(new PresenterSelector() {    @Override    public Presenter getPresenter(Object o) {        return new IconHeaderItemPresenter();    }});

设置标题区块的显示状态

使用BrowseFragment.setHeadersState()设置标题区块的状态。
* HEADERS_ENABLED 当Fragment被创建时,默认可用并显示;
* HEADERS_HIDDEN 当Fragment被创建时,默认隐藏;
* HEADERS_DISABLED 当Fragment被创建时,默认不可用并绝不显示。

显示媒体列表


BrowseFragment允许你使用Adapter和Presenter定义并显示可浏览的媒体内容类别和项目。Adapter可以连接到包含媒体目录信息的本地或在线数据源。Adapter使用Presenter创建视图并绑定数据以显示到屏幕上。
实现presenter,如下:

public class StringPresenter extends Presenter {    private static final String TAG = "StringPresenter";    public ViewHolder onCreateViewHolder(ViewGroup parent) {        TextView textView = new TextView(parent.getContext());        textView.setFocusable(true);        textView.setFocusableInTouchMode(true);        textView.setBackground(            parent.getContext().getResources().getDrawable(R.drawable.text_bg));        return new ViewHolder(textView);    }    public void onBindViewHolder(ViewHolder viewHolder, Object item) {        ((TextView) viewHolder.view).setText(item.toString());    }    public void onUnbindViewHolder(ViewHolder viewHolder) {        // no op    }}

构造Adapter使用Presenter来显示类别和项目:

private ArrayObjectAdapter mRowsAdapter;private static final int NUM_ROWS = 4;@Overrideprotected void onCreate(Bundle savedInstanceState) {    ...    buildRowsAdapter();}private void buildRowsAdapter() {    mRowsAdapter = new ArrayObjectAdapter(new ListRowPresenter());    for (int i = 0; i < NUM_ROWS; ++i) {        ArrayObjectAdapter listRowAdapter = new ArrayObjectAdapter(                new StringPresenter());        listRowAdapter.add("Media Item 1");        listRowAdapter.add("Media Item 2");        listRowAdapter.add("Media Item 3");        HeaderItem header = new HeaderItem(i, "Category " + i);        mRowsAdapter.add(new ListRow(header, listRowAdapter));    }    mBrowseFragment.setAdapter(mRowsAdapter);}

更新背景

使用 BackgroundManager改变activity的背景,如下:

protected void updateBackground(Drawable drawable) {    BackgroundManager.getInstance(this).setDrawable(drawable);}

根据用户的当前选择自动更新背景:

protected void clearBackground() {    BackgroundManager.getInstance(this).setDrawable(mDefaultBackground);}protected OnItemViewSelectedListener getDefaultItemViewSelectedListener() {    return new OnItemViewSelectedListener() {        @Override        public void onItemSelected(Object item, Row row) {            if (item instanceof Movie ) {                Drawable background = ((Movie)item).getBackdropDrawable();                updateBackground(background);            } else {                clearBackground();            }        }    };}
阅读全文
0 0
原创粉丝点击