GridLayout(不是GridView)如何均匀地拉伸所有子元素

我想有一个2x2网格内的按钮。这只是ICS,所以我试图使用新的GridLayout给定。

这是我的布局的XML:

 <?xml version="1.0" encoding="utf-8"?>
<GridLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/favorites_grid"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#00ff00"
android:rowCount="2"
android:columnCount="2">
<Button
android:text="Cell 0"
android:layout_row="0"
android:layout_column="0"
android:textSize="14dip" />
<Button
android:text="Cell 1"
android:layout_row="0"
android:layout_column="1"
android:textSize="14dip" />


<Button
android:text="Cell 2"
android:layout_row="1"
android:layout_column="0"
android:textSize="14dip" />
<Button
android:text="Cell 3"
android:layout_row="1"
android:layout_column="1"
android:textSize="14dip" />
</GridLayout>

问题是我的视图没有为每一行均匀地拉伸。这导致GridLayout的右侧有很多额外的空间。

我尝试设置layout_gravity="fill_horizontal",但这只适用于行上的最后的视图。这意味着单元格1会一直延伸,为单元格0提供足够的空间。

如何解决这个问题?

388368 次浏览

UPDATE: API 21支持权重。详见PaulT的回答

在使用GridLayout时有一些限制,下面的引用来自文档

"GridLayout不提供权重原则的支持,因为 以权重定义。一般来说,因此不可能 配置GridLayout将多余的空间分布在非平凡中 多行或多列之间的比例…为了完全控制 超过多余的空间分布在行或列;使用线性布局 子视图来保存关联单元格组中的组件。"

下面是一个使用LinearLayout子视图的小例子。(我使用空间视图占用未使用的区域,并将按钮推到所需的位置。)

<GridLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:columnCount="1"
>
<TextView
android:text="2x2 button grid"
android:textSize="32dip"
android:layout_gravity="center_horizontal" />


<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content" android:orientation="horizontal">
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Button 1" />
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="start"
android:text="Button 2" />
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
</LinearLayout>


<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
>
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Button 3" />
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="start"
android:text="Button 4" />
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
</LinearLayout>
</GridLayout>

你可以动态设置每个子节点的宽度:

GridLayout.LayoutParams params = (GridLayout.LayoutParams) child.getLayoutParams();
params.width = (parent.getWidth()/parent.getColumnCount()) -params.rightMargin - params.leftMargin;
child.setLayoutParams(params);

尝试将以下内容添加到GridLayout规范中。这应该可以工作。

android:useDefaultMargins="true"

我终于找到了解决办法。就像Rotemmiz说的,你必须在之后动态地做。这段代码拉伸按钮以水平填充视图,但同样可以用于垂直填充视图。

public void fillview(android.support.v7.widget.GridLayout gl)
{
Button buttontemp;


//Stretch buttons
int idealChildWidth = (int) ((gl.getWidth()-20*gl.getColumnCount())/gl.getColumnCount());
for( int i=0; i< gl.getChildCount();i++)
{
buttontemp = (Button) gl.getChildAt(i);
buttontemp.setWidth(idealChildWidth);
}
}

(20是内部和外部的填充和空白。这可以更普遍地做,但这个要干净得多)

然后可以这样调用:

    android.support.v7.widget.GridLayout gl = (android.support.v7.widget.GridLayout)findViewById(R.id.buttongrid);
ViewTreeObserver vto = gl.getViewTreeObserver();
vto.addOnGlobalLayoutListener(new OnGlobalLayoutListener() {@Override public void onGlobalLayout()
{


android.support.v7.widget.GridLayout gl = (android.support.v7.widget.GridLayout) findViewById(R.id.buttongrid);
fillview(gl);


ViewTreeObserver obs = gl.getViewTreeObserver();
obs.removeGlobalOnLayoutListener(this);
}});

它必须用一个观察者来完成,因为我们需要在调用视图之前等待视图被绘制。

我想有一个居中表,标签右对齐,值左对齐。多余的空间应该在桌子周围。经过多次试验,并没有按照文档的要求去做,我想出了一些可行的方法。以下是我所做的:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:orientation="vertical" >


<GridLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:columnCount="2"
android:orientation="horizontal"
android:useDefaultMargins="true" >


<TextView
android:layout_gravity="right"
android:text="Short label:" />


<TextView
android:id="@+id/start_time"
android:layout_gravity="left"
android:text="Long extended value" />


<TextView
android:layout_gravity="right"
android:text="A very long extended label:" />


<TextView
android:id="@+id/elapsed_time"
android:layout_gravity="left"
android:text="Short value" />
</GridLayout>

这似乎工作,但GridLayout显示的消息:

这个GridLayout布局或者它的LinearLayout父布局是无用的

当它对我有效时,不知道为什么它是“无用的”。

我不知道为什么这是一个好主意,但如果你尝试一下,可以提供一个更好的想法,小的改进或解释为什么它是(或不工作),我很感激反馈。

谢谢。

以下是我所做的,我很高兴地说,这对我很有效。我也想要一个2x2, 3x3等网格的项目来覆盖整个屏幕。网格布局不遵循屏幕的宽度。线性布局的工作,但你不能使用嵌套权重。

对我来说最好的选择是使用片段我使用教程开始我想做的事情。

下面是一些代码:

主要活动:

public class GridHolderActivity extends Activity {


@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);


setContentView(R.layout.activity_main_6);
}
}

activity_main_6 XML(填充3个片段)

<?xml version="1.0" encoding="utf-8"?>


<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">


<fragment
android:id="@+id/frag1"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:name=".TwoHorizontalGridFragment"
tools:layout="@layout/two_horiz" />
<fragment
android:id="@+id/frag2"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:name=".TwoHorizontalGridFragment"
tools:layout="@layout/two_horiz" />
<fragment
android:id="@+id/frag3"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
android:name=".Grid.TwoHorizontalGridFragment"
tools:layout="@layout/two_horiz" />

基本片段布局

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="wrap_content"
android:layout_gravity="center"
android:layout_height="match_parent">


<ImageQueue
android:layout_width="0dp"
android:layout_height="wrap_content"
android:id="@+id/img1"
android:layout_weight="1"/>




<ImageQueue
android:layout_width="0dp"
android:layout_height="wrap_content"
android:id="@+id/img2"
android:layout_weight="1"/>
</LinearLayout>

片段类(只处理自定义视图的初始化)每个片段膨胀2个瓦片

public class TwoHorizontalGridFragment extends Fragment {
private View rootView;


private ImageQueue imageQueue1;
private ImageQueue imageQueue2;


@Override
public View onCreateView(LayoutInflater inflater,
ViewGroup container, Bundle savedInstanceState) {
/**
* Inflate the layout for this fragment
*/
rootView = inflater.inflate(
R.layout.two_horiz, container, false);
return rootView;
}


@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);


imageQueue1 = (ImageQueue)rootView.findViewById(R.id.img1);
imageQueue2 = (ImageQueue)rootView.findViewById(R.id.img2);
imageQueue1.updateFiles();
imageQueue2.updateFiles();
}

这就是它!

本质上,这是一种使用嵌套权重的奇怪工作。它给了我一个完美的2x3网格,填满了我的10英寸平板电脑和我的HTC机器人DNA的整个屏幕。让我知道你的进展如何!

我能找到的最好的解决方案是使用线性布局(水平)为每一行,你想在其中分配按钮(单元格)宽度为0dp和权重为1。对于每个线性布局(行),将高度分配为0dp,权重分配为1。 找到下面的代码-也是android:layout_gravity="center_vertical"用于在一行中对齐按钮,以防它们包含可变长度的文本。 使用0dp和权重是一个非常整洁但不太为人所知的技巧
<LinearLayout
android:id="@+id/parent_layout"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@drawable/button_bue_3d"
android:orientation="vertical" >


<LinearLayout
android:id="@+id/layout_row1"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"


android:orientation="horizontal" >


<Button
android:id="@+id/button1"
style="?android:attr/buttonStyleSmall"
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1"
android:clickable="false"
android:layout_gravity="center_vertical"
android:text="ssssssssssssssssssssssssss" />


<Button
android:id="@+id/button2"
style="?android:attr/buttonStyleSmall"
android:clickable="false"
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1"
android:layout_gravity="center_vertical"
android:text="sggggggg" />




</LinearLayout>


<LinearLayout
android:id="@+id/layout_row2"
android:layout_weight="1"
android:layout_width="match_parent"
android:layout_height="0dp"


android:orientation="horizontal" >


<Button
android:id="@+id/button3"
style="?android:attr/buttonStyleSmall"
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1"
android:layout_gravity="center_vertical"
android:text="s" />


<Button
android:id="@+id/button4"
style="?android:attr/buttonStyleSmall"
android:layout_height="wrap_content"
android:layout_width="0dp"
android:layout_weight="1"
android:clickable="false"
android:layout_gravity="center_vertical"
android:text="s" />




</LinearLayout>




</LinearLayout>

这是一个相当老的问题,但显然很多人都感兴趣。对于像这样的4个按钮的简单布局,似乎tableelayout是实现预期结果的最简单方法。

下面的一些示例代码显示了一个表的前两行,该表有6列,横跨其父字段的宽度。每个单元格中的LinearLayout和ImageView用于允许在单元格中“打开和关闭”图像,同时保持单元格的颜色。

<TableLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:stretchColumns="1,2,3,4,5,6"
android:background="@drawable/vertical_radio_button_background"
android:padding="2dp">


<TableRow
android:layout_width="match_parent"
android:layout_height="match_parent">


<LinearLayout
android:id="@+id/brown"
android:tag="13"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="1"
android:background="@color/brown">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/maraschino"
android:tag="9"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="2"
android:background="@color/maraschino">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/cayenne"
android:tag="22"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="3"
android:background="@color/cayenne">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/maroon"
android:tag="18"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="4"
android:background="@color/maroon">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/plum"
android:tag="3"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="5"
android:background="@color/plum">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/eggplant"
android:tag="15"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="6"
android:background="@color/eggplant">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>
</TableRow>


<TableRow
android:layout_width="match_parent"
android:layout_height="match_parent">


<LinearLayout
android:id="@+id/plum2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="1"
android:background="@color/plum">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/lavender"
android:tag="14"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="2"
android:background="@color/lavender">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/carnation"
android:tag="16"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="3"
android:background="@color/carnation">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/light_pink"
android:tag="23"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="4"
android:background="@color/light_pink">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/strawberry"
android:tag="10"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="5"
android:background="@color/strawberry">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>


<LinearLayout
android:id="@+id/magenta"
android:tag="20"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
android:layout_margin="1dp"
android:layout_column="6"
android:background="@color/magenta">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="5dp"
android:src="@drawable/selected_check"
android:visibility="invisible"/>
</LinearLayout>
</TableRow>
</TableLayout>
你可以通过重写ViewGroup的onLayout方法来加快这个速度。 这是我的通用解:

package your.app.package;


import android.content.Context;
import android.view.ViewGroup;


public class GridLayout extends ViewGroup {


public GridLayout(Context context) {
super(context);
}


@Override
protected void onLayout(boolean changed, int l, int t, int r, int b) {
final int columns = 2;//edit this if you need different grid
final int rows = 2;


int children = getChildCount();
if (children != columns * rows)
throw new IllegalStateException("GridLayout must have " + columns * rows + " children");


int width = getWidth();
int height = getHeight();




int viewWidth = width / columns;
int viewHeight = height / rows;


int rowIndex = 0;
int columnIndex = 0;


for (int i = 0; i < children; i++) {
getChildAt(i).layout(viewWidth * columnIndex, viewHeight * rowIndex, viewWidth * columnIndex + viewWidth, viewHeight * rowIndex + viewHeight);
columnIndex++;
if (columnIndex == columns) {
columnIndex = 0;
rowIndex++;
}
}
}


}

<强>编辑: 不要忘记match_parent for children!< / p >

android:layout_width="match_parent"
android:layout_height="match_parent"

从API 21开始,权重的概念被添加到GridLayout中。为了支持旧的android设备,你可以使用v7支持库中的GridLayout。

下面的XML给出了如何使用权重填充屏幕宽度的示例。

<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.GridLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:grid="http://schemas.android.com/apk/res-auto"


android:id="@+id/choice_grid"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:padding="4dp"


grid:alignmentMode="alignBounds"
grid:columnCount="2"
grid:rowOrderPreserved="false"
grid:useDefaultMargins="true">


<TextView
android:layout_width="0dp"
android:layout_height="100dp"
grid:layout_columnWeight="1"
grid:layout_gravity="fill_horizontal"
android:gravity="center"
android:background="#FF33B5E5"
android:text="Tile1" />


<TextView
android:layout_width="0dp"
android:layout_height="100dp"
grid:layout_columnWeight="1"
grid:layout_gravity="fill_horizontal"
android:gravity="center"
android:background="#FF33B5E5"
android:text="Tile2" />


<TextView
android:layout_width="0dp"
android:layout_height="100dp"
grid:layout_columnWeight="1"
grid:layout_gravity="fill_horizontal"
android:gravity="center"
android:background="#FF33B5E5"
android:text="Tile3" />


<TextView
android:layout_width="0dp"
android:layout_height="100dp"
grid:layout_columnWeight="1"
grid:layout_gravity="fill_horizontal"
android:gravity="center"
android:background="#FF33B5E5"
android:text="Tile4" />


</android.support.v7.widget.GridLayout>

enter image description here

Appcompat21 GridLayout有列和行权重,可以像下面这样使用,像上图一样在网格布局中均匀地创建每个网格项。

<android.support.v7.widget.GridLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:grid="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_centerHorizontal="true"
grid:alignmentMode="alignBounds"
grid:columnCount="4" >


<Button android:layout_width="0dp"
style="?buttonStyle"
android:layout_height="0dp"
android:text="-1"
grid:layout_columnWeight="1"
grid:layout_rowWeight="1"
grid:layout_gravity="fill" />
...
</<android.support.v7.widget.GridLayout>

从没有v7支持库的API 21开始使用ScrollView:

enter image description here

XML:

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


<GridLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:columnCount="2"
>


<TextView
android:layout_width="0dp"
android:layout_height="100dp"
android:layout_columnWeight="1"
android:gravity="center"
android:layout_gravity="fill_horizontal"
android:background="@color/colorAccent"
android:text="Tile1" />


<TextView
android:layout_width="0dp"
android:layout_height="100dp"
android:layout_columnWeight="1"
android:gravity="center"
android:layout_gravity="fill_horizontal"
android:background="@color/colorPrimaryDark"
android:text="Tile2" />


<TextView
android:layout_width="0dp"
android:layout_height="100dp"
android:layout_columnWeight="1"
android:gravity="center"
android:layout_gravity="fill_horizontal"
android:background="@color/colorPrimary"
android:text="Tile3" />


<TextView
android:layout_width="0dp"
android:layout_height="100dp"
android:layout_columnWeight="1"
android:gravity="center"
android:layout_gravity="fill_horizontal"
android:background="@color/colorAccent"
android:text="Tile4" />


</GridLayout>
</ScrollView>

在我的例子中,我是动态添加按钮,所以我的解决方案需要一些XML部分和一些Java部分。我必须从几个不同的地方找到并混合解决方案,我想我将在这里分享,以便其他人寻找类似的解决方案可能会发现它有帮助。

我的布局文件XML的第一部分…

<android.support.v7.widget.GridLayout
xmlns:grid="http://schemas.android.com/apk/res-auto"
android:id="@+id/gl_Options"
android:layout_width="match_parent"
android:layout_height="wrap_content"
grid:useDefaultMargins="true">
</android.support.v7.widget.GridLayout>

grid:useDefaultMargins="true"不是必需的,但我补充说,因为对我来说看起来更好,你可以应用其他视觉影响(例如填充),如在这里的一些答案中提到的。现在对于按钮,因为我必须动态添加它们。这是我的代码的Java部分,使这些按钮,我只包括那些与此上下文相关的行。假设我必须使按钮从许多myOptions可用到我的代码,我没有复制OnClickListener代码以及。

import android.support.v7.widget.GridLayout;   //Reference to Library


public class myFragment extends Fragment{
GridLayout gl_Options;


@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
gl_AmountOptions = (GridLayout)view.findViewById( R.id.gl_AmountOptions );
...
gl_Options.removeAllViews();     // Remove all existing views
gl_AmountOptions.setColumnCount( myOptions.length <= 9 ? 3: 4 );  // Set appropriate number of columns


for( String opt : myOptions ) {
GridLayout.LayoutParams lParams   = new GridLayout.LayoutParams( GridLayout.spec( GridLayout.UNDEFINED, 1f), GridLayout.spec( GridLayout.UNDEFINED, 1f));
// The above defines LayoutParameters as not specified Column and Row with grid:layout_columnWeight="1" and grid:layout_rowWeight="1"
lParams.width = 0;    // Setting width to "0dp" so weight is applied instead


Button b = new Button(this.getContext());
b.setText( opt );
b.setLayoutParams(lParams);
b.setOnClickListener( myClickListener );
gl_Options.addView( b );
}
}
}

因为我们使用的是支持库中的GridLayout,而不是标准的GridLayout,所以我们必须在YourProject.grade文件中告诉grade。

dependencies {
compile 'com.android.support:appcompat-v7:23.4.0'
...
compile 'com.android.support:gridlayout-v7:23.4.0'
}

这是正确答案

<?xml version="1.0" encoding="utf-8"?>
<GridLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/favorites_grid"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#00ff00"
android:rowCount="2"
android:columnCount="2">
<Button
android:text="Cell 0"
android:layout_row="0"
android:layout_column="0"
android:layout_columnWeight="1"
android:layout_rowWeight="1"
android:textSize="14dip"
/>
<Button
android:text="Cell 1"
android:layout_row="0"
android:layout_column="1"
android:textSize="14dip"
android:layout_columnWeight="1"
android:layout_rowWeight="1"/>


<Button
android:text="Cell 2"
android:layout_row="1"
android:layout_column="0"
android:textSize="14dip"
android:layout_columnWeight="1"
android:layout_rowWeight="1"/>
<Button
android:text="Cell 3"
android:layout_row="1"
android:layout_column="1"
android:textSize="14dip"
android:layout_columnWeight="1"
android:layout_rowWeight="1"/>
</GridLayout>

给你:

Button button = new Button(this);
// weight = 1f , gravity = GridLayout.FILL
GridLayout.LayoutParams param= new GridLayout.LayoutParams(GridLayout.spec(
GridLayout.UNDEFINED,GridLayout.FILL,1f),
GridLayout.spec(GridLayout.UNDEFINED,GridLayout.FILL,1f));
// Layout_height = 0 ,Layout_weight = 0
params.height =0;
params.width = 0;
button.setLayoutParams(param);

它可以通过layout_columnWeight &layout_rowWeight

布局:

<?xml version="1.0" encoding="utf-8"?>
<GridLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:grid="http://schemas.android.com/apk/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:columnCount="3">


<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 0x0"
grid:layout_column="0"
grid:layout_gravity="center"
grid:layout_row="0" />


<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 0x1"
grid:layout_column="1"
grid:layout_gravity="center"
grid:layout_row="0" />


<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 0x2"
grid:layout_column="2"
grid:layout_gravity="center"
grid:layout_row="0" />




<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 1x0"
grid:layout_column="0"
grid:layout_gravity="center"
grid:layout_row="1" />


<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 1x1"
grid:layout_column="1"
grid:layout_gravity="center"
grid:layout_row="1" />


<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 1x2"
grid:layout_column="2"
grid:layout_gravity="center"
grid:layout_row="1" />




<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 2x0"
grid:layout_column="0"
grid:layout_gravity="center"
grid:layout_row="2" />


<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 2x1"
grid:layout_column="1"
grid:layout_gravity="center"
grid:layout_row="2" />


<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 2x2"
grid:layout_column="2"
grid:layout_gravity="center"
grid:layout_row="2" />




<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 3x0"
grid:layout_column="0"
grid:layout_gravity="center"
grid:layout_row="3" />


<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 3x1"
grid:layout_column="1"
grid:layout_gravity="center"
grid:layout_row="3" />


<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_rowWeight="1"
android:layout_columnWeight="1"
android:gravity="center"
android:text="item 3x2"
grid:layout_column="2"
grid:layout_gravity="center"
grid:layout_row="3" />


</GridLayout>

结果

enter image description here

enter image description here

结果:

enter image description here

试试这样做:

    final int MAX_COLUMN = gridView.getColumnCount(); //5
final int MAX_ROW = gridView.getRowCount(); //7
final int itemsCount = MAX_ROW * MAX_COLUMN; //35


int row = 0, column = 0;


for (int i = 0; i < itemsCount; i++) {
ImageView view = new ImageView(this);


//Just to provide alternate colors
if (i % 2 == 0) {
view.setBackgroundColor(Color.RED);
} else {
view.setBackgroundColor(Color.GREEN);
}


GridLayout.LayoutParams params = new GridLayout.LayoutParams(GridLayout.spec(row, 1F), GridLayout.spec(column, 1F));
view.setLayoutParams(params);
gridView.addView(view);


column++;


if (column >= MAX_COLUMN) {
column = 0;
row++;
}
}

如果你想要单元格的特定宽度和高度,那么使用:

     params.width = 100; // Your width
params.height = 100; //your height

这是更多的默认应用程序没有按钮的代码,这对我来说非常方便

<GridLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:columnCount="1"
>
<TextView
android:text="2x2 button grid"
android:textSize="32dip"
android:layout_gravity="center_horizontal" />


<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Naam" />
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="start"
android:text="@{viewModel.selectedItem.test2}" />
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
</LinearLayout>


<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal"
>
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Nummer" />
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="start"
android:text="@{viewModel.selectedItem.test}" />
<Space
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1" />
</LinearLayout>
</GridLayout>

我也有同样的问题,我想用编程的方式设置宽度和高度:

设置宽度的按钮的指标。widthPixels / 2 metrics是DisplayMetrics的对象。

 GridLayout gridLayout=findViewById(R.id.grid);
for (int i = 0; i <gridLayout.getChildCount() ; i++) {
View view= gridLayout.getChildAt(i);
if(view instanceof Button){
Button btn = (Button) view;
btn.setWidth(200);//metrics.widthPixels / 2
btn.setHeight(200);//metrics.heightPixels / 7
}
}

GridLayout

       <GridLayout
android:layout_width="match_parent"
android:layout_weight="3"
android:columnCount="2"
android:padding="10dp"
android:rowCount="3"
android:background="@drawable/background_down"
android:layout_height="0dp">




<androidx.cardview.widget.CardView
android:layout_height="0dp"
android:layout_width="0dp"
android:layout_columnWeight="1"
android:layout_rowWeight="1"
android:layout_margin="10dp"
android:elevation="10dp"
app:cardCornerRadius="15dp"
>
<LinearLayout
android:weightSum="3"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
>


<ImageView
android:layout_weight="2"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_margin="15dp"
android:src="@drawable/user" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Users"
android:textSize="16sp"
android:layout_marginStart="15dp"
android:layout_marginLeft="15dp" />
</LinearLayout>


</androidx.cardview.widget.CardView>
<androidx.cardview.widget.CardView
android:layout_height="0dp"
android:layout_width="0dp"
android:layout_columnWeight="1"
android:layout_rowWeight="1"
android:layout_margin="10dp"
android:elevation="10dp"
app:cardCornerRadius="15dp"
>
<LinearLayout
android:weightSum="3"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
>


<ImageView
android:layout_weight="2"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_margin="15dp"
android:src="@drawable/addusers" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Add Users"
android:textSize="16sp"
android:layout_marginStart="15dp"
android:layout_marginLeft="15dp" />
</LinearLayout>




</androidx.cardview.widget.CardView>


<androidx.cardview.widget.CardView
android:layout_height="0dp"
android:layout_width="0dp"
android:layout_columnWeight="1"
android:layout_rowWeight="1"
android:layout_margin="10dp"
android:elevation="10dp"
app:cardCornerRadius="15dp"
>
<LinearLayout
android:weightSum="3"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
>


<ImageView
android:layout_weight="2"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_margin="15dp"
android:src="@drawable/newspaper" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Report"
android:textSize="16sp"
android:layout_marginStart="15dp"
android:layout_marginLeft="15dp" />
</LinearLayout>






</androidx.cardview.widget.CardView>
<androidx.cardview.widget.CardView
android:layout_height="0dp"
android:layout_width="0dp"
android:layout_columnWeight="1"
android:layout_rowWeight="1"
android:layout_margin="10dp"
android:elevation="10dp"
app:cardCornerRadius="5dp"
>
<LinearLayout
android:weightSum="3"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
>


<ImageView
android:layout_weight="2"
android:layout_width="50dp"
android:layout_height="50dp"
android:layout_margin="15dp"
android:src="@drawable/settings" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Settings"
android:textSize="16sp"
android:layout_marginStart="15dp"
android:layout_marginLeft="15dp" />
</LinearLayout>




</androidx.cardview.widget.CardView>


</GridLayout>

你可以在这里找到整个教程, Android Grid Layout With CardView和OnItemClickListener < / p >

这里有一个例子

enter image description here

<androidx.constraintlayout.widget.ConstraintLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".GridMenuActivity">


<ScrollView
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent">




<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="#FFFFFF"
android:orientation="vertical"
android:weightSum="10">


<RelativeLayout
android:layout_width="match_parent"
android:layout_height="200dp"
android:layout_weight="2"
android:background="@drawable/oval_background">


<ImageView
android:id="@+id/imageView6"
android:layout_width="75dp"
android:layout_height="75dp"
android:layout_centerInParent="true"
android:layout_margin="5dp"
app:srcCompat="@mipmap/dmm_logo" />


</RelativeLayout>


<GridLayout
android:id="@+id/mainGrid"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="8"
android:alignmentMode="alignBounds"
android:columnCount="2"
android:columnOrderPreserved="true"
android:padding="5dp"
android:rowCount="5">


<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="0"
android:layout_rowWeight="1"
android:layout_column="0"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginTop="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_dashboard" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Dashboard"
android:textAlignment="center"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:gravity="center"
android:text="Add Entry"
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>


<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="0"
android:layout_rowWeight="1"
android:layout_column="1"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginTop="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_sell" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Sale Forecast"
android:textAlignment="center"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:gravity="center"
android:text="Upcoming Milk Requirement"
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>


<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="1"
android:layout_rowWeight="1"
android:layout_column="0"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_seller" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Sellers"
android:textAlignment="center"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:gravity="center"
android:text="Milk Providers"
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>


<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="1"
android:layout_rowWeight="1"
android:layout_column="1"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_shopping" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Purchasers"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Milk Consumers"
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>




<!-- Row 2 -->


<!-- Column 1 -->
<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="2"
android:layout_rowWeight="1"
android:layout_column="0"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_advance" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Advance"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Advance Payments"
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>


<!-- Column 2 -->
<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="2"
android:layout_rowWeight="1"
android:layout_column="1"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_reciever" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Due"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Pending Payments"
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>


<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="3"
android:layout_rowWeight="1"
android:layout_column="0"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_transaction" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Transactions"
android:layout_gravity="center"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Payments Detalis"
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>


<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="3"
android:layout_rowWeight="1"
android:layout_column="1"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_sell" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Sell Product"
android:layout_gravity="center"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Ghee, Curd etc."
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>


<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="4"
android:layout_rowWeight="1"
android:layout_column="0"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_purchase_report" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Purchases"
android:layout_gravity="center"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Milk Purchase Entries"
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>


<androidx.cardview.widget.CardView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_row="4"
android:layout_rowWeight="1"
android:layout_column="1"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:layout_marginBottom="16dp"
android:clickable="true"
android:focusable="true"
android:foreground="?android:attr/selectableItemBackground"
app:cardCornerRadius="8dp"
app:cardElevation="3dp">


<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal|center_vertical"
android:layout_margin="16dp"
android:orientation="vertical">


<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:src="@drawable/ic_sale_report" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Sales"
android:layout_gravity="center"
android:textColor="@color/colorPrimary"
android:textSize="16sp"
android:textStyle="bold" />


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Milk Sale Entries"
android:textSize="10sp" />


</LinearLayout>


</androidx.cardview.widget.CardView>


</GridLayout>


</LinearLayout>


</ScrollView>
</androidx.constraintlayout.widget.ConstraintLayout>

非常适合我。 我希望它也能帮助你

对于我来说,我只是将layout_widthlayout_height更改为wrap_content,并将layout_gravity设置为center_horizontal:

<GridLayout
android:id="@+id/gridLayout"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:columnCount="2"
android:rowCount="4">

关于网格布局的一些技巧。

  1. 默认网格布局在最小SDK 21+上工作最好。
  2. GridLayout的高度/宽度应该是固定的或match_parent。这是因为Grid layout计算它的子节点的高度/宽度,而拥有自己的可变高度可能会导致计算精确高度时出现问题。
  3. 网格布局默认情况下忽略子节点的页边距,因此如果希望子节点控制它们的页边距,则应该使用android:useDefaultMargins="true"
  4. 要使用Grid布局创建一个动态的、自动拉伸的视图组,可以:
    1. 父元素将同时控制这两项:总组的最大高度和每行中的元素数量
    2. 父节点将控制每行中的列数,子节点将控制总高度。

第一个场景的优点是我们可以在组中添加任意数量的孩子,他们都将很好地均匀伸展。缺点是我们得到的是一个固定规模的群体。而内容较大的儿童也占据了固定的空间。

第二个场景的优点是我们可以添加更多的子节点,他们将决定组的高度。在父元素的顶部附加一个嵌套的滚动视图将使整个元素列表可滚动。 缺点是子控件控制组的高度和变量高度,可能会导致整个视图看起来很混乱

如果我们稍微调整一下,这两种情况都可以发挥它们的优点,它们的缺点可以被最小化。

第一个场景的例子:

    <GridLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:columnCount="2"
android:useDefaultMargins="true">


<View
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_rowWeight="1"
android:layout_columnSpan="1"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginHorizontal="8dp"
android:layout_marginVertical="8dp"
android:background="@color/black" />


<View
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_rowWeight="1"
android:layout_columnSpan="1"
android:layout_columnWeight="1"
android:layout_gravity="fill"


android:layout_marginHorizontal="8dp"
android:layout_marginVertical="8dp"
android:background="@color/black" />


<View
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_rowWeight="1"
android:layout_columnSpan="2"
android:layout_columnWeight="1"
android:layout_gravity="fill"


android:layout_marginHorizontal="8dp"
android:layout_marginVertical="8dp"
android:background="@color/black" />


<View
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_rowWeight="1"
android:layout_columnSpan="1"
android:layout_columnWeight="1"
android:layout_gravity="fill"
android:layout_marginHorizontal="8dp"
android:layout_marginVertical="8dp"
android:background="@color/black" />


<View
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_rowWeight="1"
android:layout_columnSpan="1"
android:layout_columnWeight="1"
android:layout_gravity="fill"


android:layout_marginHorizontal="8dp"
android:layout_marginVertical="8dp"
android:background="@color/black" />


<View
android:layout_width="0dp"
android:layout_height="0dp"
android:layout_rowWeight="1"
android:layout_columnSpan="2"
android:layout_columnWeight="1"
android:layout_gravity="fill"


android:layout_marginHorizontal="8dp"
android:layout_marginVertical="8dp"
android:background="@color/black" />


     

<!--
add more elements here with same attributes and they will fit on their own!
-->


</GridLayout>
< p >输出: img1 < / p >

第二个场景:

<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:ignore="HardcodedText"
>


<GridLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:columnCount="2"
android:orientation="horizontal"
android:useDefaultMargins="true"
>


<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_columnSpan="1"
android:text="this is a text"
android:textColor="@color/white"
android:layout_gravity="center"
android:layout_margin="8dp"
android:background="@color/black"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_columnSpan="1"
android:layout_gravity="fill_horizontal"
android:text="this is something cool. this should be taking more space but it is also controlling the total height of row"
android:textColor="@color/white"
android:gravity="center"
android:layout_margin="8dp"
android:background="@color/black"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_columnSpan="1"
android:layout_gravity="fill_horizontal"
android:text="once the width is determined by any child, the whole column shall take the same height"
android:textColor="@color/white"
android:gravity="center"
android:layout_margin="8dp"
android:background="@color/black"
/>
<TextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_columnSpan="1"
android:layout_gravity="fill"
android:text="this column can only control how they shall look by layout gravity. this should look like column 0,0 but its  taking full row height/width"
android:textColor="@color/white"
android:gravity="center"
android:layout_margin="8dp"
android:background="@color/black"
/>


<!--


-->






</GridLayout>


</FrameLayout>
< p > outpus: enter image description here < / p >

main。xml

<GridLayout
android:id="@+id/grid_related_news"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="8dp"
android:padding="3dp"
android:columnCount="2">


</GridLayout>

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout android:layout_width="0dp"
android:layout_height="wrap_content"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_columnWeight="1"
android:gravity="center"
android:padding="3dp"
android:layout_gravity="fill_horizontal"
xmlns:android="http://schemas.android.com/apk/res/android">


<androidx.cardview.widget.CardView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@color/white"
app:cardBackgroundColor="@color/white"
app:cardCornerRadius="5dp"
app:cardElevation="2dp"
android:layout_margin="4dp">


<androidx.constraintlayout.widget.ConstraintLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">


<ImageView
android:id="@+id/img_related_news"
android:layout_width="0dp"
android:layout_height="0dp"
android:layoutDirection="rtl"
android:scaleType="centerCrop"
app:layout_constraintDimensionRatio="H,1:1"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:srcCompat="@drawable/light_gray" />


<LinearLayout
android:layout_width="0dp"
android:layout_height="0dp"
android:background="#59000000"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />


<TextView
android:id="@+id/txt_related_news_title"
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_marginStart="12dp"
android:layout_marginTop="6dp"
android:layout_marginEnd="12dp"
android:layout_marginBottom="12dp"
android:elevation="2dp"
android:fontFamily="@font/yekan_bold"
android:letterSpacing="-0.1"
android:lineSpacingExtra="4dp"
android:maxLines="4"
android:textColor="@color/white"
android:textSize="13sp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
tools:text="@string/lorem_ipsum_sentence" />


</androidx.constraintlayout.widget.ConstraintLayout>


</androidx.cardview.widget.CardView>


</LinearLayout>

java

GridLayout grid_related_news = findViewById(R.id.grid_related_news);
View view = LayoutInflater.from(this).inflate(R.layout.related_item, (ViewGroup) grid_related_news, false);
ImageView img_related_news = view.findViewById(R.id.img_related_news);
...


grid_related_news.addView(view);

你可以用这个例子

我只是在网格视图中做了简单的网格布局,并在想为什么我以前没有这样做。它很容易实现。(我在示例中使用自定义包装器CSView,但只是将其更改为View)。Ops要求只适用于GridView,所以我把它贴在这里作为答案。为了使拉伸均匀,例如numColumns:auto_fit android:numColumns=2

用法:

CSGridLayout(this, R.id.sound_store_grid, SubscriptionUpgradeStoreDialogItem(this),
PresetUpgradeStoreDialogItem(this), MidiUpgradeStoreDialogItem(this))

实现:

class CSGridLayout(parent: CSActivityView<*>,
viewId: Int,
vararg items: CSView<*>) : CSView<GridView>(parent, viewId) {


private val items = list(items)
private var adapter = Adapter()


init {
view.adapter = adapter
adapter.notifyDataSetChanged()
}


inner class Adapter : BaseAdapter() {
override fun getCount() = items.size
override fun getViewTypeCount() = 1
override fun isEnabled(position: Int) = true
override fun getItem(position: Int) = items[position]
override fun getItemViewType(position: Int) = 0
override fun getItemId(position: Int) = position.toLong()
override fun getView(position: Int, toReuseView: View?, parent: ViewGroup) =
items[position].view
}
}