是否有任何窗口小部件替换已弃用的Gallery窗口小部件

时间:2015-01-19 00:55:45

标签: android android-viewpager android-ui android-gallery android-recyclerview

我需要在我的应用程序中实现某种水平ListView,以便在用户从第一个ListView(类别)中选择项目后,第二个ListView将显示与所选项目相关的所有项目(类别中的产品)。

我打算使用Gallery小部件,但由于它已被弃用,我试图找到一个好的替代品,但没有运气。

这是我发现的:

  1. 使用ViewPager的解决方案(参见 CommonsWare &#39;答案):有点复杂,没有如何处理简单click事件的示例。< / LI>
  2. 使用实现Horizontal ListView的第三方库的解决方案:声音好,但不是正式的小部件让我想知道它是否是正确的方法。
  3. 使用第三方库的解决方案,该库实现了一个非常漂亮的库cover flow effect:与第二个解决方案相同的问题。
  4. 你知道,主要的问题是我已经开发了几个应用程序,而不需要使用任何第三方库,除非真的有必要,否则我不想使用它。

    出于这个原因,我想问你们,如果你知道任何结合的解决方案/方法:

    • 原生组件。
    • 易于使用。
    • 回收。

    enter image description here

    编辑:

    按照@Ewoks和@ CommonsWare的建议,我试试了RecyclerView,结果证明这是我需要的,而不是像我想象的那样复杂。

    以下是我使用的链接,以防有人发现它们有用:

    我对第二个链接的例子进行了一些更改,我设法得到了我需要的两个画廊,其中第二个画廊列出了第一个画廊中所选类别中的所有菜肴。

    结果如下:

    enter image description here

    正如我所说,得到这个结果并不困难,我只需要在LinearLayoutManager

    的构造函数中指出 HORIZONTAL 方向
    mCategoryHorizontalManager=new LinearLayoutManager(this,LinearLayoutManager.HORIZONTAL,false);
    

    我也没有使用Picasso,我使用了Ion因为在我的项目中我还需要处理HTTP请求而Picasso只适用于图像。

    现在我的问题,正如你所知,不是如何显示图像,而是如何使点击的项目具有特殊的样式(框架,边框,背景颜色),这使得非常清楚哪个项目被选中

    到目前为止,我认为我设法以某种方式改变了所选项目的风格,但我对此并不满意。您可以在上图中看到结果,其中所选项目具有不同的背景颜色(CYAN):

    这是我的RecyclerView的每个项目的布局:

    <?xml version="1.0" encoding="utf-8"?>
    <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_margin="10dp"
        android:gravity="center"
        android:orientation="vertical">
    
        <ImageView
            android:id="@+id/picture_image_view"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_marginBottom="10dp" />
    
        <TextView
            android:id="@+id/desc_text_view"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content" />
    
    </LinearLayout>
    

    这是我的适配器:

    public class GalleryItemAdapter extends RecyclerView.Adapter<GalleryItemAdapter.ItemHolder>{
    
        /**
         * Click handler interface. RecyclerView does not have
         * its own built in like AdapterView do.
         */
        public interface OnItemClickListener{
            public void onItemClick(ItemHolder item, int position);
        }
    
        private List<GalleryObject> mItems;
    
        private OnItemClickListener mOnItemClickListener;
        private LayoutInflater mLayoutInflater;
    
        private View mSelectedView; 
    
        public GalleryItemAdapter(Context context,List<GalleryObject> picsList,int level){
            //...
            mSelectedView=null; //There's no selected item at first
        }
    
        @Override
        public ItemHolder onCreateViewHolder(ViewGroup parent, int viewType) {
            View itemView=mLayoutInflater.inflate(R.layout.recycler_row, parent,false);
    
            return new ItemHolder(itemView,this);
    
        }
    
        @Override
        public void onBindViewHolder(ItemHolder holder, int position) {
            holder.setTituloTextView(mItems.get(position).getImageTitle());
            Ion.with(holder.getPicImageView())
                    .placeholder(R.mipmap.owner_placeholder)
                    .resize(mSize,mSize)
                    .centerCrop()
                    .error(R.mipmap.owner_error)
                    .load(mItems.get(position).getImageUrl());
    
        }
    
        @Override
        public int getItemCount() {
            return mItems.size();
        }
    
        public OnItemClickListener getOnItemClickListener() {
            return this.mOnItemClickListener;
        }
    
        public void setOnItemClickListener(OnItemClickListener listener) {
            this.mOnItemClickListener = listener;
        }
    
        /* To highlight selected item*/
    
        public View getSelectedView() {
            return mSelectedView;
        }
    
        public void setSelectedView(View selectedView) {
            this.mSelectedView = selectedView;
        }
    
        /* Required implementation of ViewHolder to wrap item view */
        public static class ItemHolder extends RecyclerView.ViewHolder implements
            View.OnClickListener{
            private GalleryItemAdapter mParent;
            private TextView mTituloTextView;
            private ImageView mPicImageView;
            public ItemHolder(View itemView, GalleryItemAdapter parent) {
                super(itemView);
                itemView.setOnClickListener(this);
    
                mParent=parent;
    
                mTituloTextView= (TextView) itemView.findViewById(R.id.desc_text_view);
                mPicImageView= (ImageView) itemView.findViewById(R.id.picture_image_view);
            }
    
            public void setTituloTextView(CharSequence titulo) {
                this.mTituloTextView.setText(titulo);
            }
    
            public ImageView getPicImageView() {
                return mPicImageView;
            }
            public CharSequence getImageText(){
                return mTituloTextView.getText();
            }
            public int getGalleryLevel(){
                return mParent.mLevel;
            }
    
            @Override
            public void onClick(View v) {
                final OnItemClickListener listener=mParent.getOnItemClickListener();
                if(listener!=null){
                    listener.onItemClick(this,getPosition());
                }
                setItemActivated(v);
            }
            public void setItemActivated(View v){
                if(mParent.getSelectedView()!=null){
                   mParent.getSelectedView().setBackgroundColor(Color.TRANSPARENT);
                }
                v.setBackgroundColor(Color.CYAN);
                mParent.setSelectedView(v);
            }
        }
    }
    

    正如您所看到的,每当用户点击我调用setItemActivated的项目时,我使用getter {{1}检查mSelectedView是否为空(之前已选择项目)在这种情况下,我将背景颜色更改回TRANSPARENT。

    无论getSelectedView()的值如何,我都会将当前视图的背景颜色更改为CYAN:

    mSelectedView

    最后使用当前所选项目更新v.setBackgroundColor(Color.CYAN);

    mSelectedView

    这样可行,但结果很糟糕,因为它改变了整个视图的背景,当我认为只有图像应该以某种方式突出显示时。

    你知道如何以更好的方式改变图像的风格吗?或许有一个开箱即用的解决方案,用于突出显示我不知道的所选项目。

    非常感谢。

1 个答案:

答案 0 :(得分:2)

RecyclerView使用他的内置LayoutManagers,我建议你GridLayout最适合画廊目的。如果你不喜欢它,你可以通过扩展RecyclerView.LayoutManager

来实现自己的LayoutManager

我希望这可以作为一些初步指导......;)

P.S。我肯定不会推荐CoverFlow,因为所有其他提到的类都提供更丰富的API。此外,它的实现在性能问题上缺乏很多。