Android- 如何根据 NestedScrollView 的滚动方向进行图像缩放?

Android- How to perform image scaling based on the scroll direction of the NestedScrollView?

提问人:Smit Patel 提问时间:10/2/2023 更新时间:10/2/2023 访问量:18

问:

我是 android 应用程序开发的新手,并试图根据滚动方向获得图像调用动画/效果,就像这个视频中一样。如果需要,请提供 kotlin 代码。提前🙂致谢[这是我想要的效果:](https://i.stack.imgur.com/XFEhv.gif)

这是我的xml:

<?xml version="1.0" encoding="utf-8"?>
<androidx.coordinatorlayout.widget.CoordinatorLayout 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"
    android:fitsSystemWindows="true">

    <com.google.android.material.appbar.AppBarLayout
        android:id="@+id/appBarLayout"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:background="@color/black">

        <com.google.android.material.appbar.CollapsingToolbarLayout
            android:id="@+id/collapsingToolbarLayout"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            app:contentScrim="@color/transparent"
            app:layout_scrollFlags="scroll|enterAlwaysCollapsed">

            <ImageView
                android:id="@+id/scrollingImageView"
                android:layout_width="match_parent"
                android:layout_height="360dp"
                android:alpha="0.7"
                android:src="@drawable/live_events_category_img"
                app:layout_constraintStart_toStartOf="parent"
                app:layout_constraintTop_toTopOf="parent" />

            <androidx.appcompat.widget.Toolbar
                android:layout_width="match_parent"
                android:layout_height="70dp"
                android:background="@color/transparent"
                app:layout_collapseMode="parallax"
                app:layout_collapseParallaxMultiplier="1"
                app:layout_scrollFlags="exitUntilCollapsed">

            </androidx.appcompat.widget.Toolbar>
        </com.google.android.material.appbar.CollapsingToolbarLayout>
    </com.google.android.material.appbar.AppBarLayout>

    <androidx.core.widget.NestedScrollView
        android:id="@+id/nestedScrollView"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:animateLayoutChanges="true"
        android:background="@color/black"
        android:isScrollContainer="true"
        android:paddingStart="10dp"
        android:paddingEnd="10dp"
        android:scrollbars="none"
        app:layout_behavior="@string/appbar_scrolling_view_behavior">
    </androidx.core.widget.NestedScrollView>

</androidx.coordinatorlayout.widget.CoordinatorLayout>
Android XML Kotlin 滚动 效果

评论


答:

0赞 Smit Patel 10/2/2023 #1

经过长时间的研究,我发现我们可以通过在 appBarLayout 上调用 addOnOffsetChangedListener 来实现这种效果,这将为我们提供每个滚动位置的偏移值,我们可以根据需要对 imageview 的缩放参数进行计算。这是我在 kotlin 文件中添加的内容,而 xml 保持不变:

var isCollapsed = false
var scaleFactor = 1.0f // Initialize the scale factor
var lastVerticalOffset = 0
binding.appBarLayout.addOnOffsetChangedListener { appBarLayout, verticalOffset ->
// Calculate the total scroll range of the CollapsingToolbarLayout
val totalScrollRange = appBarLayout.totalScrollRange

// Calculate the percentage of collapse (0 to 1)
val collapseRatio = -verticalOffset.toFloat() / totalScrollRange.toFloat()

// Calculate the target scale factor based on the collapse ratio
// Adjust the scaleFactor range as needed
val targetScaleFactor = 1.0f - collapseRatio * 0.5f

// Use ValueAnimator to smoothly interpolate the scale factor
val animator = ValueAnimator.ofFloat(scaleFactor, targetScaleFactor)
animator.duration = 100 // Adjust the duration as needed
animator.addUpdateListener { animation ->
    val animatedValue = animation.animatedValue as Float

    // Apply the interpolated scale factor to the ImageView
    binding.scrollingImageView.scaleX = animatedValue
    binding.scrollingImageView.scaleY = animatedValue
}
animator.start()

// Update the scale factor
scaleFactor = targetScaleFactor

// Check if the CollapsingToolbarLayout is fully collapsed
if (verticalOffset == -totalScrollRange) {
    if (!isCollapsed) {
        // The CollapsingToolbarLayout is now fully collapsed
        // Perform actions or call methods here
        isCollapsed = true
    }
} else {
    // The CollapsingToolbarLayout is not fully collapsed
    isCollapsed = false
}

// Update the last vertical offset
lastVerticalOffset = verticalOffset
}