在Android中定义RelativeLayout的Z顺序视图


226

我想在Android中定义RelativeLayout的视图的z顺序。

我知道做到这一点的一种方法是打电话bringToFront

有更好的方法吗?如果可以在布局xml中定义z顺序,那就太好了。


4
View.bringToFront(); 是
疯子

Answers:


314

最简单的方法就是简单地注意将视图添加到XML文件的顺序。文件中的较低位置表示Z轴较高。

编辑:在Android开发人员站点的此处此处都有记录。(感谢@flightplanner)


16
不幸的是,这并不总是可能改变。例如,在相对布局中,每个元素只能根据文件中先前定义的元素进行布局
Casebash 2010年

67
Casebash,我认为不必不必只使用“ @ + id / your_element_before_its_defined”,然后在以后定义的元素中使用相同的id。我对此可能是错的,这些布局对我来说非常棘手,但是我肯定会觉得它可行。
2011年

7
tjb是正确的(我很高兴他是正确的)。将@ + id与ID的首次提及一起使用,例如layout_above =“ @ + id / some_id”
Michiel

3
您也可以将<item type =“ id” name =“ <your_id>” />放入值xml文件中,然后可以在任何地方引用它。
卡尔

8
我知道我晚了3年,但在回复@hpique的同时,这里记录了此内容
HexAndBugs 2013年


68

请注意,API 21及更高版本中的按钮和其他元素具有较高的高度,因此忽略元素的xml顺序,无论其父级布局如何。花了我一段时间找出那个。


16
对我来说,此错误的解决方案是在要通过按钮呈现的视图上调用setElevation(1000)。
在洞中射击

setElevation()需要API级别21
dp2050

21

在Android中,从API级别21开始,布局文件中的项目从其在文件中的排序方式(如正确答案所述)获得其Z顺序,并且从其标高中获得更高的标高值,这意味着其标高获得更高的Z顺序。

有时这可能会引起问题,尤其是按钮经常出现在项目顶部时,根据XML的顺序,这些按钮应按Z顺序位于其下方。要解决此问题,只需将android:elevation布局XML中的项目设置为与要实现的Z顺序匹配即可。

我在布局中设置了一个元素的高程,它将开始投射阴影。如果您不想要这种效果,可以使用如下代码删除阴影:

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
   myView.setOutlineProvider(null);
}

我还没有找到通过布局xml删除高架视图阴影的任何方法。


1
如评论中所述,您可以使用android:elevation="1000dp"。这样就不会渲染阴影。
瓦迪姆·科托夫

15

我遇到了相同的问题:在相对布局parentView中,我有2个孩子childView1和childView2。首先,我将childView1放在childView2上方,并希望childView1位于childView2的顶部。更改儿童视图的顺序并不能解决我的问题。对我有用的是在parentView和我设置的代码中设置android:clipChildren =“ false”

childView1.bringToFront();

parentView.invalidate();

2
这是可行的,而Android让我很伤心。child.bringToFront()parent.invalidate()作品,但parent.bringChildToFront(child)没有。我们都期望操作系统的逻辑在哪里?
奥利弗·豪斯勒

为了动画化某些视图(X和Y的平移),我尝试了LinearLayout,FrameLayout和RelativeLayout的几种组合,但始终存在问题(与重叠或不成比例的尺寸有关)。终于android:clipChildren="false"做到了。谢谢!
JCarlosR


13

自从引入

android:translationZ

XML字段改变了一点点。建议运行的其他答案

childView1.bringToFront();

parentView.invalidate();

完全可以看到,因为此代码不会将childView1带到XML文件中带有硬编码的android:translationZ的任何视图的前面。我对此有疑问,一旦从其他视图中删除了该字段,BringToFront()就可以正常工作。


Android 5的情况也是如此elevation
-Shelll

5

API 21 view.setElevation(float)内置

使用ViewCompat.setElevation(view, float);的向后兼容性

更多方法ViewCompat.setZ(v, pixels)ViewCompat.setTranslationZ(v, pixels)

另一种收集按钮或视图数组并用于addView添加到RelativeLayout的方法




0

检查在XML的视图之一上是否有任何高程。如果是这样,请将高程添加到其他项目或删除高程以解决问题。从那里开始,是视图的顺序决定了另一个之上的观点。


0

或将重叠的按钮或视图放在FrameLayout中。然后,xml文件中的RelativeLayout将遵循添加子布局的顺序。


0

您也可以使用下面的代码示例来实现相同的功能

ViewCompat.setElevation(sourceView, ViewCompat.getElevation(mCardView)+1);

这是向后兼容的。这mCardView是下面的视图sourceView

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.