我有一个NestedScrollView与CoordinatorLayout + AppBarLayout + CollapsingToolbarLayout一起使用,其视差效果类似于this tutorial
我需要以编程方式滚动内容(最好是平滑滚动,即动画化),但是调用滚动方法(scrollBy(),scrollTo(),smoothScrollTo(),smoothScrollBy())无济于事。
请注意,我正在使用app:layout_behavior="@string/appbar_scrolling_view_behavior"
<-不确定问题是否与此有关。
当用户单击按钮时,我正在Kotlin中呼叫nsv_form.smoothScrollBy(0, 300)
,但没有任何反应:(
(还尝试了scrollTo()
,scrollBy()
,+-300,各种不同的变体)
更新:我研究了源代码,似乎*scroll*()
方法期望布局的内容大于父视图(有意义)。就我而言,内容较小,因此我怀疑这就是滚动方法不起作用的原因。也许我需要其他东西代替scroll
?
NestedScrollView的位置从屏幕上方开始部分显示,上方是CollapsingToolbarLayout like this中的图像,因此看来我需要以编程方式移动NestedScrollView的位置并触发CoordinatorLayout的滚动行为。 -我该怎么做?
这是我的布局:
<?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">
<com.google.android.material.appbar.AppBarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@android:color/transparent">
<com.google.android.material.appbar.CollapsingToolbarLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows="true"
app:expandedTitleMarginEnd="64dp"
app:expandedTitleMarginStart="48dp"
app:layout_scrollFlags="scroll|exitUntilCollapsed">
<ImageView
android:id="@+id/iv_image"
android:layout_width="match_parent"
android:layout_height="@dimen/image_height"
android:scaleType="centerCrop"
app:layout_collapseMode="parallax"
tools:src="@drawable/some_image" />
</com.google.android.material.appbar.CollapsingToolbarLayout>
</com.google.android.material.appbar.AppBarLayout>
<androidx.core.widget.NestedScrollView
android:id="@+id/nsv_form"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/white"
app:layout_behavior="@string/appbar_scrolling_view_behavior">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:animateLayoutChanges="true"
android:orientation="vertical">
[... child views...]
</LinearLayout>
</androidx.core.widget.NestedScrollView>
</androidx.coordinatorlayout.widget.CoordinatorLayout>
TLDR :如何以编程方式滚动like this?
答案 0 :(得分:3)
我如何以编程方式像这样滚动?
对于这种滚动行为,您需要折叠或展开CollapsingToolbarLayout
,而无需滚动NestedScrollView
这是该示例代码
尝试此操作在布局中进行以下更改
<?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:id="@+id/rootView"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows="true">
<com.google.android.material.appbar.AppBarLayout
android:id="@+id/app_bar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@android:color/transparent"
android:fitsSystemWindows="true">
<com.google.android.material.appbar.CollapsingToolbarLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:fitsSystemWindows="true"
app:expandedTitleMarginEnd="64dp"
app:expandedTitleMarginStart="48dp"
app:layout_scrollFlags="scroll|exitUntilCollapsed">
<ImageView
android:id="@+id/iv_image"
android:layout_width="match_parent"
android:layout_height="250dp"
android:adjustViewBounds="true"
android:scaleType="fitXY"
android:src="@drawable/goku"
app:layout_collapseMode="parallax"
app:layout_collapseParallaxMultiplier="0.7" />
<androidx.appcompat.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="?attr/actionBarSize"
app:layout_collapseMode="pin"
app:contentInsetLeft="0dp"
app:contentInsetStart="0dp"
app:contentInsetStartWithNavigation="0dp"
app:titleTextAppearance="@style/AppTheme.Toolbar.Title"
app:popupTheme="@style/AppTheme.PopupOverlay" />
</com.google.android.material.appbar.CollapsingToolbarLayout>
</com.google.android.material.appbar.AppBarLayout>
<com.google.android.material.floatingactionbutton.FloatingActionButton
android:id="@+id/fab"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="10dp"
android:background="@color/Boxcolordiabled"
app:layout_anchor="@id/app_bar"
app:layout_anchorGravity="bottom|end"
app:srcCompat="@drawable/ic_favorite" />
<androidx.core.widget.NestedScrollView
android:id="@+id/nsv_form"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@android:color/holo_blue_light"
app:layout_behavior="@string/appbar_scrolling_view_behavior">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:animateLayoutChanges="true"
android:orientation="vertical">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="@string/demo" />
<Button
android:id="@+id/btnColl"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="Expand " />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="@string/demo" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="@string/demo" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="@string/demo" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="@string/demo" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="@string/demo" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="@string/demo" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:text="@string/demo" />
</LinearLayout>
</androidx.core.widget.NestedScrollView>
</androidx.coordinatorlayout.widget.CoordinatorLayout>
活动代码
import android.animation.ValueAnimator;
import android.os.Bundle;
import android.view.View;
import android.view.animation.DecelerateInterpolator;
import android.widget.Button;
import android.widget.Toast;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.floatingactionbutton.FloatingActionButton;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.widget.Toolbar;
import androidx.coordinatorlayout.widget.CoordinatorLayout;
import neel.com.bottomappbar.R;
public class MainActivity extends AppCompatActivity {
Toolbar toolbar;
AppBarLayout app_bar;
Button btnColl;
FloatingActionButton fab;
CoordinatorLayout rootView;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
getSupportActionBar().setTitle("Stack Demo");
app_bar = findViewById(R.id.app_bar);
btnColl = findViewById(R.id.btnColl);
fab = findViewById(R.id.fab);
rootView = findViewById(R.id.rootView);
fab.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Toast.makeText(MainActivity.this, "Collapse FAB Clicked", Toast.LENGTH_SHORT).show();
CoordinatorLayout.LayoutParams params = (CoordinatorLayout.LayoutParams) app_bar.getLayoutParams();
final AppBarLayout.Behavior behavior = (AppBarLayout.Behavior) params.getBehavior();
if (behavior != null) {
ValueAnimator valueAnimator = ValueAnimator.ofInt();
valueAnimator.setInterpolator(new DecelerateInterpolator());
valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
behavior.setTopAndBottomOffset((Integer) animation.getAnimatedValue());
app_bar.requestLayout();
}
});
valueAnimator.setIntValues(0, -900);
valueAnimator.setDuration(1000);
valueAnimator.start();
}
}
});
btnColl.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
Toast.makeText(MainActivity.this, "Expand btnColl Clicked", Toast.LENGTH_SHORT).show();
CoordinatorLayout.LayoutParams params = (CoordinatorLayout.LayoutParams) app_bar.getLayoutParams();
final AppBarLayout.Behavior behavior = (AppBarLayout.Behavior) params.getBehavior();
if (behavior != null) {
ValueAnimator valueAnimator = ValueAnimator.ofInt();
valueAnimator.setInterpolator(new DecelerateInterpolator());
valueAnimator.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
@Override
public void onAnimationUpdate(ValueAnimator animation) {
behavior.setTopAndBottomOffset((Integer) animation.getAnimatedValue());
app_bar.requestLayout();
}
});
valueAnimator.setIntValues(-900, 0);
valueAnimator.setDuration(400);
valueAnimator.start();
}
}
});
}
}
输出
答案 1 :(得分:0)
需要从 UI线程调用滚动(scrollBy()
/ scrollTo()
/ smoothScrollTo()
/ smoothScrollBy()
。
在Kotlin中,您可以使用
Handler().post {
nsv_form.scrollBy(0, 300)
}