【问题标题】:How to make grid-view horizontally scrollable in android如何在android中使grid-view水平滚动
【发布时间】:2012-11-05 16:22:32
【问题描述】:

我已经为 gridview 编写了代码,我可以在其中显示图像和文本,但我想在单个可滚动行中显示所有图像,例如 Pulse 新闻应用程序。 我已经在 xml 中为 gridview 实现了水平滚动视图,但它根本不起作用。 我正在将 pageviwer 用于选项卡,并且我正在使用片段。

这是我的 xml 代码

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent" >
   <HorizontalScrollView 
   android:id="@+id/horizontalScrollView1" 
   android:layout_width="fill_parent" 
   android:layout_height="wrap_content"
   android:fillViewport="true"
   android:scrollbars="horizontal" >
<GridView
    android:layout_width="500dp"
    android:layout_height="400dp"
    android:id="@+id/gridview"
    android:columnWidth="300dp"
    android:numColumns="3"
    android:horizontalSpacing="10dp"
    android:scrollbars="horizontal">
</GridView>
 </HorizontalScrollView>
</RelativeLayout>

这是我的图片适配代码

public class ImageAdapter extends BaseAdapter {
private Context context;
private final String[] mobileValues;
private TextView t;
public ImageAdapter(Context context, String[] mobileValues) {
    this.context = context;
    this.mobileValues = mobileValues;
}
public View getView(int position, View convertView, ViewGroup parent) {
    LayoutInflater inflater = (LayoutInflater) context
            .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
    View gridView;
    if (convertView == null) {
        gridView = new View(context);
        // get layout from mobile.xml
        gridView = inflater.inflate(R.layout.showlist_item, null);
       // set value into textview
        TextView textView = (TextView) gridView
                .findViewById(R.id.grid_item_label);
        textView.setText(mobileValues[position]);
        // set image based on selected text
        ImageView imageView = (ImageView) gridView
                .findViewById(R.id.grid_item_image);
        String mobile = mobileValues[position];
        if (mobile.equals("Windows")) {
            imageView.setImageResource(R.drawable.test_play_image);
        } else if (mobile.equals("iOS")) {
            imageView.setImageResource(R.drawable.test_play_image);
        } else if (mobile.equals("Blackberry")) {
            imageView.setImageResource(R.drawable.test_play_image);
        } else {
            imageView.setImageResource(R.drawable.test_play_image);
        }
    } else {
        gridView = (View) convertView;
    }
    return gridView;
}
private void clickedButton(TextView tv){
    int num = Integer.parseInt(tv.getText().toString());
    ++num;
    tv.setText(Integer.toString(num));
}
private void clickedButtonm(TextView tv){
    int num = Integer.parseInt(tv.getText().toString());
    if(num>0){
        --num;
        tv.setText(Integer.toString(num));
    }
}
public int getCount() {
    return mobileValues.length;
}
public Object getItem(int position) {
    return null;
}
public long getItemId(int position) {
    return 0;
}
class MyOnClickListener implements OnClickListener{
    public final TextView tv;
    public MyOnClickListener(TextView tv){
        this.tv=tv;
    }
    public void onClick(View v) {
        // TODO Auto-generated method stub
        clickedButton(tv);
    }
}
class MyOnClickListenerm implements OnClickListener{
    public final TextView tv;
    public MyOnClickListenerm(TextView tv){
        this.tv=tv;
    }
    public void onClick(View v) {
        // TODO Auto-generated method stub
        clickedButtonm(tv);
    }
}

我想像这样向右滚动显示。

【问题讨论】:

标签: android android-layout


【解决方案1】:

从现在开始,Android 中有一个不错的解决方案(正如 Zainodis 在 its comment 中所说的那样):HorizontalGridView

1. Gradle 依赖

dependencies {
    compile 'com.android.support:leanback-v17:23.1.0'
}

2. 将其添加到您的布局中

your_activity.xml

<!-- your stuff before... -->
        <android.support.v17.leanback.widget.HorizontalGridView
            android:layout_width="wrap_content"
            android:layout_height="80dp"
            android:id="@+id/gridView"
            />
<!-- your stuff after... -->

3. 布局网格元素

为您的网格元素 ( grid_element.xml ) 创建一个布局。我创建了一个简单的按钮,其中只有一个按钮。

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical" android:layout_width="match_parent"
    android:layout_height="match_parent">

    <Button
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="New Button"
        android:id="@+id/button" />
</LinearLayout>

4. 创建适配器

深受此链接启发:https://gist.github.com/gabrielemariotti/4c189fb1124df4556058

public class GridElementAdapter extends RecyclerView.Adapter<GridElementAdapter.SimpleViewHolder>{

    private Context context;
    private List<String> elements;

    public GridElementAdapter(Context context){
        this.context = context;
        this.elements = new ArrayList<String>();
        // Fill dummy list
        for(int i = 0; i < 40 ; i++){
            this.elements.add(i, "Position : " + i);
        }
    }

    public static class SimpleViewHolder extends RecyclerView.ViewHolder {
        public final Button button;

        public SimpleViewHolder(View view) {
            super(view);
            button = (Button) view.findViewById(R.id.button);
        }
    }

    @Override
    public SimpleViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        final View view = LayoutInflater.from(this.context).inflate(R.layout.grid_element, parent, false);
        return new SimpleViewHolder(view);
    }

    @Override
    public void onBindViewHolder(SimpleViewHolder holder, final int position) {
        holder.button.setText(elements.get(position));
        holder.button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View view) {
                Toast.makeText(context, "Position =" + position, Toast.LENGTH_SHORT).show();
            }
        });
    }

    @Override
    public long getItemId(int position) {
        return position;
    }

    @Override
    public int getItemCount() {
        return this.elements.size();
    }
}

5. 在你的活动中初始化它:

private HorizontalGridView horizontalGridView;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.your_activity);
    horizontalGridView = (HorizontalGridView) findViewById(R.id.gridView);
    GridElementAdapter adapter = new GridElementAdapter(this);

    horizontalGridView.setAdapter(adapter);
}

【讨论】:

  • 不错。这是我一直在寻找的,但有一个大错误:如果您设置horizontalGridView.setNumRows(2);,它也会使网格无限在垂直方向上滚动。设置行高没有帮助。
  • 我刚刚试过你说的。你是对的。我不知道是否有我不知道的选项来解决该问题,或者它是否是一个巨大的错误。希望对我来说,一排总是我需要的最大值。
  • 这个解决方案有问题,完成后,AndroidManifest.xml 出现错误,我必须使用&lt;uses-feature android:name="android.software.leanback" android:required="false"/&gt; 来解决这个问题。我正在使用 v17:23.2.1
  • 天啊,为什么 HORIZONTALgridView 会无限垂直滚动。哇。我花了 4 个小时在这个废话上白白浪费了时间
  • 浪费时间,需要太多依赖并强制你升级你的SDK级别,加上强制appcompat更改主题,远离这个
【解决方案2】:
        <HorizontalScrollView
            android:layout_width="match_parent"
            android:layout_height="fill_parent"
            android:layout_below="@+id/seatLegendLayout">

            <FrameLayout
                android:layout_width="fill_parent"
                android:layout_height="match_parent">

                <LinearLayout
                    android:id="@+id/linearLayout_gridtableLayout"
                    android:layout_width="900dp"
                    android:layout_height="match_parent"
                    android:orientation="horizontal">

                    <GridView
                        android:id="@+id/gridView1"
                        android:layout_width="fill_parent"
                        android:layout_height="fill_parent"
                        android:layout_margin="4dp"
                        android:columnWidth="100dp"
                        android:gravity="center"
                        android:numColumns="9"
                        android:horizontalSpacing="1dp"
                        android:scrollbarAlwaysDrawHorizontalTrack="true"
                        android:scrollbarAlwaysDrawVerticalTrack="true"
                        android:scrollbars="horizontal"
                        android:stretchMode="none"
                        android:verticalSpacing="1dp">

                    </GridView>


                </LinearLayout>
            </FrameLayout>
        </HorizontalScrollView>

【讨论】:

  • 不错,但这会在右侧的末尾留下空白区域。有什么解决办法吗? @Ashish Soni
  • @DhirajDevkar 您需要确保@+id/linearLayout_gridtableLayout 的宽度等于numColumns * columnWidth + gridView padding
【解决方案3】:

我发现 Two-way GridView 在 github 上很有帮助。

它有一些方法:

scrollDirectionPortrait (vertical | horizontal)

scrollDirectionLandscape (vertical | horizontal)

numRows()

【讨论】:

  • 你在你的应用中实现了吗?
  • @Junaid 是的,!!!!!!那是一个有趣的项目!!!! :D。附:脸书还不够好吗?? :D
  • 是的,Facebook 是一个很好的交流社交平台,但它与开发有什么关系呢? :-/ :P
【解决方案4】:

我已经测试了一个更好的更清洁的工作解决方案,没有任何额外的依赖项,只需更改您的布局 xml,如下所示。

  <HorizontalScrollView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:layout_alignParentBottom="true">

    <android.support.v7.widget.RecyclerView
        android:id="@+id/horizontal_grid_view"
        android:layout_width="wrap_content"
        android:layout_height="112dp"
        android:scrollbarAlwaysDrawVerticalTrack="true"></android.support.v7.widget.RecyclerView>
</HorizontalScrollView>

在分配网格布局管理器时,还可以根据您的要求设置跨度计数。

【讨论】:

  • 这对我有用,但你应该用更多的代码改进你的答案,那么这将是不使用外部库的最佳答案。
【解决方案5】:

我不认为 gridviews 可以水平滚动。 Android 已为此目的提供了 galleryView。你可以用那个。这是一个可以帮助您将galleryView作为水平网格视图工作的标题:- Horizontal scrolling in android gridview

【讨论】:

【解决方案6】:

图书馆Android-DraggableGridViewPagerJustin(zzhouj)

提供以下功能

  • 网格视图布局拆分为页面。
  • 在 support-v4 库中水平滑动页面,如 ViewPager。
  • 设置列和行数。
  • 设置监听器:页面更改、项目 单击,项目长按,重新排列。

帮助我创建了一个带有页面指示器的水平滚动网格,希望它可以帮助尝试实现类似功能的人。

【讨论】:

    【解决方案7】:

    如果对您有困难,您可以将 recyclerView 用作 GridView,而无需使用 GridView。往下看

    <androidx.recyclerview.widget.RecyclerView 
        android:id="@+id/rvQuickAccess"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        app:spanCount="2"
        android:gravity="center"
        android:orientation="horizontal"
        tools:listitem="@layout/layout_item"
        app:layoutManager="androidx.recyclerview.widget.GridLayoutManager"
        android:scrollbarAlwaysDrawHorizontalTrack="true"/>
    

    您可以通过 app:spanCount = " " 设置列数。不要忘记将 layoutManager 设置为 GridLayoutManager 和方向 "Horizo​​ntal"

    【讨论】:

      【解决方案8】:

      对于一小组数据,一个不错的方法是为您的容器使用如下布局:

      <HorizontalScrollView
              android_id="@+id/scroll_view"
              android_width="match_parent"
              android_height="wrap_content">
          <LinearLayout
                  android_id="@+id/my_list"
                  android_width="wrap_content"
                  android_height="wrap_content" >
          </LinearLayout>
      </HorizontalScrollView>
      

      列表项的不同布局 (list_item.xml):

      <FrameLayout
              android_id="@+id/item_container"
              android_width="100dp"
              android_height="100dp">
          <ImageView
                  android_id="@+id/item_background"
                  android_width="match_parent"
                  android_height="match_parent" />
          <TextView
                  android_id="@+id/item_title"
                  android_width="match_parent"
                  android_height="50dp"
                  android_background="#80000000"
                  android_gravity="center_vertical" />
      </FrameLayout>
      

      然后根据需要以编程方式添加视图:

      public void addItensToLayout(String... mobileValues, LayoutInflater inflater) {
          LinearLayout list = (LinearLayout) findViewById(R.id.my_list);
          for (String item : mobileValues) {
              FrameLayout item = inflater.inflate(R.layout.list_item, list, false);
              TextView textView = (TextView) gridView
                  .findViewById(R.id.item_title);
              textView.setText(item);
              ImageView imageView = (ImageView) item
                  .findViewById(R.id.item_background);
              String mobile = mobileValues[position];
              if (mobile.equals("Windows")) {
                  imageView.setImageResource(R.drawable.test_play_image);
              } else if (mobile.equals("iOS")) {
                  imageView.setImageResource(R.drawable.test_play_image);
              } else if (mobile.equals("Blackberry")) {
                  imageView.setImageResource(R.drawable.test_play_image);
              } else {
                  imageView.setImageResource(R.drawable.test_play_image);
              }
              list.addView(item);
          }
      }
      

      这样做,您不再使用适配器。如果你真的需要使用适配器,你应该使用ViewPager,在 android 文档中有很多这样做的信息,或者你可以从 StackOverflow 开始:

      Using viewpager in my application android viewPager implementation

      如果我错过了那里的任何一点,请询问更多信息。

      【讨论】:

      • 根据您的数据大小,这可能非常糟糕。 ListViews 为您提供视图回收,而不是将所有视图同时保存在内存中,使用这种方法您会失去这种能力,并且会很快耗尽内存并且性能会很糟糕。
      猜你喜欢
      • 2012-09-16
      • 1970-01-01
      • 1970-01-01
      • 2019-01-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-04-02
      • 2022-01-26
      相关资源
      最近更新 更多