clipChildren无法正常工作

Vam*_*shi 23 animation android

在我的应用程序中,我试图使用动画移动图像.当我尝试将图像(imageView2imageView4)设置为动画时,图像imageView1在移出布局时会切割.这里的源图像是imageView2imageView4目标图像imageView1

下面是我的XML:

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/animRL"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:clipChildren="false"
    android:clipToPadding="false"
    android:orientation="vertical" >

    <ImageView
        android:id="@+id/imageView1"
        android:layout_width="40dp"
        android:layout_height="60dp"
        android:layout_centerHorizontal="true"
        android:layout_centerVertical="true"
        android:src="@drawable/deskcard" />

    <RelativeLayout
        android:id="@+id/baselayout"
        android:layout_width="match_parent"
        android:layout_height="120dp"
        android:layout_alignParentRight="true"
        android:layout_below="@+id/imageView1"
        android:clipChildren="false"
        android:clipToPadding="false" >

        <RelativeLayout
            android:id="@+id/layout"
            android:layout_width="match_parent"
            android:layout_height="100dp"
            android:layout_alignParentBottom="true"
            android:layout_centerHorizontal="true"
            android:layout_marginBottom="5dp"
            android:clipChildren="false"
            android:clipToPadding="false"
            android:gravity="bottom|center" >

            <ImageView
                android:id="@+id/imageView2"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_alignParentLeft="true"
                android:layout_alignTop="@+id/imageView4"
                android:layout_marginLeft="118dp"
                android:clipChildren="false"
                android:clipToPadding="false"
                android:src="@drawable/test" />

            <ImageView
                android:id="@+id/imageView4"
                android:layout_width="40dp"
                android:layout_height="60dp"
                android:layout_alignParentBottom="true"
                android:layout_alignParentRight="true"
                android:layout_marginBottom="16dp"
                android:layout_marginRight="104dp"
                android:clipChildren="false"
                android:clipToPadding="false"
                android:src="@drawable/test1" />
        </RelativeLayout>
    </RelativeLayout>


</RelativeLayout>
Run Code Online (Sandbox Code Playgroud)

动画代码如下:

imageView4.setOnClickListener(new View.OnClickListener() {

                @Override
                public void onClick(View v) {
                    // TODO Auto-generated method stub
                     int sourceCoords[] = new int[2];
                        int targetCoords[] = new int[2];
                        int xDelta;
                        int yDelta;
                        imageView4.getLocationOnScreen(sourceCoords);
                        image.getLocationOnScreen(targetCoords);
                        xDelta = targetCoords[0] - sourceCoords[0];
                        yDelta = targetCoords[1] - sourceCoords[1];

                    TranslateAnimation animation = new TranslateAnimation(0, xDelta, 0, yDelta);
                    animation.setDuration(400);
                    animation.setFillAfter(false);
                    animation.setAnimationListener(new MyAnimationListener());

                    imageView4.startAnimation(animation);
                }
            });
Run Code Online (Sandbox Code Playgroud)

rof*_*son 32

RelativeLayout的父亲之一可能是剪辑子项(有时兼容性库会添加一个神秘的ViewGroup,例如NoSaveStateFrameLayout).我过去曾经使用过类似的东西来成功禁用视图的所有父级的剪辑:

public void disableClipOnParents(View v) {
    if (v.getParent() == null) {
        return;
    }

    if (v instanceof ViewGroup) {
        ((ViewGroup) v).setClipChildren(false);
    }

    if (v.getParent() instanceof View) {
        disableClipOnParents((View) v.getParent());
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 更新:我正在使用支持库21.0.3.更新到22.0.0为我解决了这个问题! (2认同)
  • 系统将您的视图包装到帮助程序ViewGroup中并不明显。如果您想在运行中看到它,请打开Layout Inspector,以防止遇到`clipChildren =“ false”`无法正常工作的情况,并且您可能会在层次结构中找到一个神秘的ViewGroup。 (2认同)

Xav*_*r.S 10

最后一个原因是"RelativeLayout".因此,要解决此问题,请不要将RelativeLayout用作比父控件更大的父控件.相反,FrameLayout,如:

<!-- it's ok as grand parent -->
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:clipChildren="false">

    <!-- parent must not be a RelativeLayout -->
    <FrameLayout
        android:layout_width="match_parent"
        android:layout_height="38dp"
        android:layout_alignParentBottom="true"
        android:layout_marginBottom="9dp">

        <!-- Your Larger-than-parent View -->
        <View
            android:layout_width="56dp"
            android:layout_height="138dp"
            android:layout_gravity="center"
            android:background="@android:color/black" />

    </FrameLayout>

</RelativeLayout>
Run Code Online (Sandbox Code Playgroud)


mhd*_*ati 7

我知道已经晚了,但这是最简单的完整答案:

只需放在每个布局上:

    android:clipChildren="false"
    android:clipToPadding="false"
Run Code Online (Sandbox Code Playgroud)

  • 正如我在回答中所解释的那样,在操作系统将您的视图包装/注入视图组中不在您的布局中的视图的情况下,这将不起作用。 (2认同)

Keh*_* Li 6

@roflharrison的想法很好,但是代码有一些问题:这里我们递归地禁用clipChildren,但是当我们到达根视图时,它会v.getParents()为null,该方法立即返回,并且它的ClipChildren属性不会被禁用。

更重要的是,对于以下行:

if (v.getParent() instanceof View)
Run Code Online (Sandbox Code Playgroud)

?? 视图的父级不应该是 ViewGroup 吗?难道我们不应该禁用 ViewGroup 的剪辑属性,而不是 View 的剪辑属性吗?所以我将代码更改为以下内容,并且效果很好:

public void disableClipOnParents(View v) {
    if (v == null) {
        return;
    }
    if (v instanceof ViewGroup) {
        ((ViewGroup) v).setClipChildren(false);
    }
    disableClipOnParents((View) v.getParent());
}
Run Code Online (Sandbox Code Playgroud)