在滑动时移动和调整DrawerLayout的内容

问题描述 投票:8回答:2

我刚看到这个应用程序,看到这个自定义动画为DrawerLayout。我猜它必须先截取屏幕截图,然后在View中绘制一个自定义的Activity,但我不确定,也不确定细节。有谁知道如何做到这一点?

enter image description here

android drawerlayout
2个回答
18
投票

你可以通过在你的View上的onDrawerSlide()DrawerListener方法中翻译和缩放内容DrawerLayout来做到这一点。由于内容View本身正在调整大小,并且在右下角有一个单独的TextView,我们将把这两个都放在另一个持有者ViewGroup中。如果不需要该标签TextView,也可以省略持有者ViewGroup

该示例的基本DrawerLayout设置:

<android.support.v4.widget.DrawerLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/drawer_layout"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:background="#222222">

    <RelativeLayout android:id="@+id/holder"
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <LinearLayout android:id="@+id/content"
            android:layout_width="match_parent"
            android:layout_height="match_parent"
            android:orientation="vertical">

            <android.support.v7.widget.Toolbar
                android:id="@+id/toolbar"
                android:layout_width="match_parent"
                android:layout_height="?attr/actionBarSize"
                android:background="#E97411" />

            <ImageView android:id="@+id/main_content"
                android:layout_width="match_parent"
                android:layout_height="0dp"
                android:layout_weight="1"
                android:background="#EEEEEE"
                android:src="@drawable/ic_launcher" />

        </LinearLayout>

        <TextView android:id="@+id/label"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_alignParentBottom="true"
            android:layout_alignParentRight="true"
            android:visibility="gone"
            android:textSize="26dp"
            android:text="My App" />

    </RelativeLayout>

    <android.support.design.widget.NavigationView
        android:id="@+id/navigation_view"
        android:layout_width="240dp"
        android:layout_height="match_parent"
        android:layout_gravity="left"
        android:background="#555555" />

</android.support.v4.widget.DrawerLayout>

示例Activity显示标准的View初始化,以及实际正在进行工作的DrawerListener

public class MainActivity extends AppCompatActivity {

    private static final float END_SCALE = 0.7f;

    private DrawerLayout drawerLayout;
    private NavigationView navigationView;
    private Toolbar toolbar;
    private TextView labelView;
    private View contentView;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);

        drawerLayout = (DrawerLayout) findViewById(R.id.drawer_layout);
        navigationView = (NavigationView) findViewById(R.id.navigation_view);
        toolbar = (Toolbar) findViewById(R.id.toolbar);
        labelView = (TextView) findViewById(R.id.label);
        contentView = findViewById(R.id.content);

        toolbar.setNavigationIcon(new DrawerArrowDrawable(this));
        toolbar.setNavigationOnClickListener(new OnClickListener() {
                @Override
                public void onClick(View v) {
                    if (drawerLayout.isDrawerOpen(navigationView)) {
                        drawerLayout.closeDrawer(navigationView);
                    }
                    else {
                        drawerLayout.openDrawer(navigationView);
                    }
                }
            }
        );

        drawerLayout.setScrimColor(Color.TRANSPARENT);
        drawerLayout.addDrawerListener(new DrawerLayout.SimpleDrawerListener() {
                @Override
                public void onDrawerSlide(View drawerView, float slideOffset) {
                    labelView.setVisibility(slideOffset > 0 ? View.VISIBLE : View.GONE);

                    // Scale the View based on current slide offset
                    final float diffScaledOffset = slideOffset * (1 - END_SCALE);
                    final float offsetScale = 1 - diffScaledOffset;
                    contentView.setScaleX(offsetScale);
                    contentView.setScaleY(offsetScale);

                    // Translate the View, accounting for the scaled width
                    final float xOffset = drawerView.getWidth() * slideOffset;
                    final float xOffsetDiff = contentView.getWidth() * diffScaledOffset / 2;
                    final float xTranslation = xOffset - xOffsetDiff;
                    contentView.setTranslationX(xTranslation);
                }

                @Override
                public void onDrawerClosed(View drawerView) {
                    labelView.setVisibility(View.GONE);
                }
            }
        );
    }
}

该示例使用SimpleDrawerListener,但onDrawerSlide()方法可以在ActionBarDrawerToggle中被类似地覆盖,如果使用它。在这种情况下,需要调用super方法来保存汉堡箭头动画。

请注意DrawerLayoutActivity娱乐期间保留抽屉状态,因此您在处理方向更改等时可能需要考虑到这一点。


0
投票

抽屉行为是一个库使用Android DrawerLayout支持库作为父类[易于迁移],它在抽屉上提供额外的行为,例如,在幻灯片上的抽屉时移动视图或缩放视图的高度。

如果当前项目使用Android DrawerLayout支持库并且有点无聊的效果。然后,只需更改布局代码并调用动画/效果所需的方法。

Check out github code

摇篮

dependencies {
   implementation 'com.infideap.drawerbehavior:drawer-behavior:0.1.5'
}

如果gradle无法同步,您可以在项目级gradle中包含此行,

repositories {
 maven{
   url "https://dl.bintray.com/infideap2/Drawer-Behavior"
 }
}
© www.soinside.com 2019 - 2024. All rights reserved.