如何在fragment中保存recyclerview的滚动位置

2024-02-03

我从这里遵循了很多答案..但没有一个解决我的问题..这就是我问的原因。

我想在片段中保存滚动位置。 在他们建议遵循的许多文章中

@Override
    protected void onSaveInstanceState(Bundle outState) {
        super.onSaveInstanceState(outState);
    }

and

@Override
    protected void onRestoreInstanceState(Bundle savedInstanceState) {
        super.onRestoreInstanceState(savedInstanceState);
    }

但这两种方法在fragment中不可用。

My code:

private int mPositionIng = RecyclerView.NO_POSITION;

private String KEY_POSITION_ING = "KeyPositionIng";

在 OnCreateView() 中

if (savedInstanceState != null) {

            if (savedInstanceState.containsKey(KEY_POSITION_ING)) {
                mPositionIng = savedInstanceState.getInt(KEY_POSITION_ING);
            }
}

覆盖片段中的方法它们与上面的方法不同。我不知道我哪里做错了。

@Override
    public void onSaveInstanceState(Bundle outState) {

        int scrollPositionIng = mRecyclerViewIngredients.computeVerticalScrollOffset();

        mPositionIng = scrollPositionIng;

        outState.putInt(KEY_POSITION_ING, mPositionIng);
        super.onSaveInstanceState(outState);
    }

@Override
    public void onViewStateRestored(@Nullable Bundle savedInstanceState) {

        if (mPositionIng != RecyclerView.NO_POSITION) {

            mRecyclerViewIngredients.getLayoutManager().scrollToPosition(mPositionIng);
        }


        super.onViewStateRestored(savedInstanceState);
    }

我只需要在方向改变时保存滚动位置..请帮忙。 任何建议都会有帮助。谢谢......


Update

我在下面写的所有内容都是正确的,但它对你不起作用的原因是我没有意识到你的Activity的布局是结构化的。这是你的Activity的布局(稍微清理一下):

    <?xml version="1.0" encoding="utf-8"?>
    <android.support.constraint.ConstraintLayout
        xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        tools:context="com.tapan.recipemaster.activity.RecipeDetailActivity">
    
        <ScrollView
            android:layout_width="match_parent"
            android:layout_height="match_parent">
    
            <RelativeLayout
                android:layout_width="match_parent"
                android:layout_height="wrap_content">
    
                <FrameLayout
                    android:id="@+id/fl_fragment_detail"
                    android:layout_width="match_parent"
                    android:layout_height="match_parent"
                    android:padding="@dimen/padding_10dp"/>
    
            </RelativeLayout>
    
        </ScrollView>
    
    </android.support.constraint.ConstraintLayout>

同时,这是你的Fragment的布局(再次稍微清理一下):

<FrameLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context="com.tapan.recipemaster.fragment.RecipeDetailFragment">

    <ScrollView
        android:layout_width="match_parent"
        android:layout_height="match_parent">

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:padding="@dimen/padding_10dp"
            android:orientation="vertical">

            <LinearLayout
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:background="@color/colorAccent"
                android:orientation="vertical">

                <TextView
                    android:id="@+id/tv_ingredient"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:textColor="#FFF"
                    android:textSize="@dimen/text_23sp"
                    android:text="Ingredients"/>

                <android.support.v7.widget.RecyclerView
                    android:id="@+id/rv_ingredients"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:layout_marginTop="@dimen/dimen_8dp"/>

            </LinearLayout>

            <LinearLayout
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:orientation="vertical">

                <TextView
                    android:id="@+id/tv_step"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:layout_marginTop="@dimen/dimen_8dp"
                    android:textColor="@color/colorPrimaryDark"
                    android:textSize="@dimen/text_23sp"
                    android:text="Steps"/>

                <android.support.v7.widget.RecyclerView
                    android:id="@+id/rv_steps"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:layout_marginTop="@dimen/dimen_8dp"/>

            </LinearLayout>

        </LinearLayout>

    </ScrollView>

</FrameLayout>

Both RecyclerViews have android:layout_height="wrap_content",这意味着它们不滚动。相反,ScrollView在你的Activity是提供滚动行为的视图,所以它是this必须保存其滚动位置的视图。

您可以通过提供此信息让系统为您执行此操作ScrollView一个 ID。任何你想要的 id,只要它是唯一的。您根本不必编写任何 Java。

<ScrollView
    android:id="@+id/thisfixestheproblem"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

确保您正在修改ScrollView在您的活动的布局中,而不是在您的片段的布局中。

Original

您发布的任何代码都不需要保存您的RecyclerView方向改变时的滚动位置。只要RecyclerView在你的布局中有一个唯一的ID,它会自动为你保存滚动位置。

这是一个非常小的示例应用程序,它显示了滚动位置的自动保存,即使动态添加Fragment。正如您所看到的,我自己保存的唯一实例状态是启动片段的按钮是否应该可见。

MainActivity.java

public class MainActivity extends AppCompatActivity {

    private Button button;

    @Override
    protected void onSaveInstanceState(Bundle outState) {
        super.onSaveInstanceState(outState);
        outState.putBoolean("buttonVisible", button.getVisibility() == View.VISIBLE);
    }

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

        button = (Button) findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener() {

            @Override
            public void onClick(View v) {
                getSupportFragmentManager()
                        .beginTransaction()
                        .replace(R.id.content, new MyFragment())
                        .commit();

                button.setVisibility(View.GONE);
            }
        });

        if (savedInstanceState != null) {
            boolean buttonVisible = savedInstanceState.getBoolean("buttonVisible");
            button.setVisibility(buttonVisible ? View.VISIBLE : View.GONE);
        }
    }
}

MyFragment.java

public class MyFragment extends Fragment {

    @Nullable
    @Override
    public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
        View root = inflater.inflate(R.layout.myfragment, container, false);

        RecyclerView recycler = (RecyclerView) root.findViewById(R.id.recycler);
        recycler.setAdapter(new MyAdapter());

        return root;
    }

    private static class MyAdapter extends RecyclerView.Adapter<MyViewHolder> {

        @Override
        public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
            LayoutInflater inflater = LayoutInflater.from(parent.getContext());
            View itemView = inflater.inflate(R.layout.itemview, parent, false);
            return new MyViewHolder(itemView);
        }

        @Override
        public void onBindViewHolder(MyViewHolder holder, int position) {
            Drawable d = new ColorDrawable(Color.argb(0xff, 0, 0, position));
            ViewCompat.setBackground(holder.image, d);
            holder.text.setText("" + position);
        }

        @Override
        public int getItemCount() {
            return 256;
        }
    }

    private static class MyViewHolder extends RecyclerView.ViewHolder {

        final View image;
        final TextView text;

        MyViewHolder(View itemView) {
            super(itemView);

            this.image = itemView.findViewById(R.id.image);
            this.text = (TextView) itemView.findViewById(R.id.text);
        }
    }
}

活动主文件

<?xml version="1.0" encoding="utf-8"?>
<FrameLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/content"
    android:layout_width="match_parent"
    android:layout_height="match_parent">

    <Button
        android:id="@+id/button"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_gravity="center"
        android:text="create fragment"/>

</FrameLayout>

myfragment.xml

<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.RecyclerView
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    android:id="@+id/recycler"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    app:layoutManager="android.support.v7.widget.LinearLayoutManager"
    tools:listitem="@layout/itemview"/>

项目视图.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:gravity="center_vertical"
    android:orientation="horizontal">

    <View
        android:id="@+id/image"
        android:layout_width="48dp"
        android:layout_height="48dp"
        android:layout_margin="12dp"
        tools:background="#333"/>

    <TextView
        android:id="@+id/text"
        android:layout_width="0dp"
        android:layout_height="wrap_content"
        android:layout_weight="1"
        tools:text="text"/>

</LinearLayout>
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何在fragment中保存recyclerview的滚动位置 的相关文章

  • 如何从 AAR 依赖项中排除特定资源?

    有没有一种相当简单的方法来实现模块的build gradle文件来指示应排除依赖项中的某些文件 我特别感兴趣的是从 AAR 中排除某些资源 金丝雀泄密 https github com square leakcanary是一个有趣的库 可帮
  • android - EditText 打字速度很慢

    我的 EditText 在打字时响应速度很慢 这种滞后现象足以让我找到解决方案 我做了一些研究 发现了一个 SO 线程输入文本时 EditText 滞后 https stackoverflow com questions 6173591 a
  • 合并两个位图图像(并排)

    任何人都可以帮助将两个位图图像合并为单个位图 在android中 并排 谢谢 尤瓦拉吉 您可以使用Canvas 查看这篇文章 http www jondev net articles Combining 2 Images in Androi
  • 为什么 Kotlin 数据类可以在 Gson 的不可空字段中包含空值?

    在 Kotlin 中你可以创建一个data class data class CountriesResponse val count Int val countries List
  • 无法合并 Dex - Android Studio 3.0

    当我在稳定频道中将 Android Studio 更新到 3 0 并运行该项目时 我开始收到以下错误 Error Execution failed for task app transformDexArchiveWithExternalLi
  • 更改 AChartEngine 中的图例大小

    我想专门更改饼图的图例大小输出 我已经尝试了所有可以找到的 AChartEngine 方法 但没有一个只能更改图例文本大小 我必须重写 onDraw 函数吗 如果是这样 怎么办 要设置图例高度 请使用 renderer setLegendH
  • 在 Android 中将应用程序上下文保存到静态变量是否安全?

    我知道在 Android 上使用静态变量是相当危险的 特别是当您将它们引用到活动时 但是 如果我有一个扩展 Application 的类 我们称此类为 App 引用此类的实例是否安全 如果是这样 任何其他类对应用程序上下文进行任何类型的引用
  • Android 手机应用意图

    我想在手机上启动手机应用程序作为意图 我正在使用这个代码 startActivity getPackageManager getLaunchIntentForPackage com android phone 但该函数抛出一个空指针异常 因
  • 如何在 Android 上的 HttpPost 中发送 unicode 字符

    我试图在我的应用程序中允许多语言支持 这会发出 HTTP post 来上传新消息 我需要做什么才能支持日语和其他非拉丁语语言 我的代码目前看起来像这样 note the msg string is a JSON message by the
  • Facebook LoginActivity 未正确显示

    我有一个使用 Facebook 登录的应用程序 我有 FacebookSDK 并且使用 com facebook LoginActivity 问题是 在 10 英寸平板电脑上 当显示软键盘时 活动无法正确显示 我使用的是 Samsung G
  • 更改android中禁用按钮的颜色

    有没有办法通过样式或其他形式更改 android 中禁用按钮的颜色 我目前有以下内容 可绘制 button default xml
  • 点击监听器的公共类

    我的所有 6 项活动中有 7 个按钮 所有 6 个按钮在所有活动中都具有相同的功能 如何为这 6 个按钮执行通用的单击事件侦听器 您可以创建一个实现 View OnClickListener 的新类 如下所示 public class My
  • 无法在 Android 模拟器中安装 apk

    我正在尝试通过 adb shell 在 ICS 模拟器中安装 apk 从一个站点下载 但出现以下错误 失败 INSTALL FAILED UID CHANGED 可能是什么问题 只需 rm r 有问题的数据目录即可 如果您在安装时遇到此错误
  • 带有空白白屏的 WebView

    我在 DialogFragment 中有一个 webview 它使用以下方式显示文档和 PDF它可以进行几次尝试 但如果用户尝试频繁打开和关闭对话框 webview 将显示空白屏幕 我已经尝试了所有的线程link1 https stacko
  • 如何在android sdk上使用PowerMock

    我想为我的 android 项目编写一些单元测试和仪器测试 然而 我遇到了一个困扰我一段时间的问题 我需要模拟静态方法并伪造返回值来测试项目 经过一些论坛的调查 唯一的方法是使用PowerMock来模拟静态方法 这是我的 gradle 的一
  • 按名称查找视图

    是否可以通过名称而不是 id 来查找视图 findViewById R id someView 但我想做这样的事情 findViewByName someView 在处理 xml 时 您必须通过标识符查找视图 但是您可以使用以下方式查找标识
  • 如何使 tablayout 文本大小相等?

    这就是我所做的 我为文本创建了一种样式
  • Jetpack Compose 部分或开放侧边框

    我正在尝试绘制部分或一侧开放的矩形圆形边框以实现此效果 玩了一下之后我得到了这个 这是通过以下方式完成的 RoundedCornerShape topStartPercent 50 bottomStartPercent 50 start R
  • WebView 在某些设备上如果不长按则不会滚动

    我有一个 WebView 设置如下 the web view mWebView WebView findViewById R id webView push the url on to the web view mWebView loadU
  • 基于BluetoothChat示例通过蓝牙套接字发送文件

    大家好 根据我之前问的一个问题 我已经能够将文件转换为其他字节数组 以便使用以下写入方法 public void sendFile Log d TAG sending data InputStream inputStream null Ur

随机推荐

  • 使用未指定的索引。考虑添加 ".indexOn": "g"

    我正在使用 Geofire 在某个区域进行循环查询 设置好观察者后 我会返回位置 但是 随着位置的变化 我还会返回 使用未指定的索引 考虑添加 indexOn g 我的 geofire 数据库看起来像这样 karmadots geofire
  • 将正方形分割成小正方形

    我有一个大广场 我想把这个正方形分成小正方形 我需要所有可能的组合 我知道组合有无数种 但我有一个限制 我有最小正方形的固定尺寸 我可以使用蛮力来实现它 但它太长了 对于这个任务有更好的算法吗 Thanks 那么这个问题只有当我们做出两个假
  • 尝试理解 Ruby 中 self.method_name 与 Classname.method_name 的使用

    我试图了解何时使用 self method name 与何时使用 Classname method name 在下面的示例中 为什么 before create 需要引用 User hash password 而不是 self hash p
  • Apache:如何对用户隐藏服务器版本和操作系统?

    我在一个网站上读到我需要添加两行httpd conf file 服务器签名关闭 ServerTokens 产品 但当我添加它们后 一切都没有改变 正如之前我可以在浏览器中看到的 Apache 2 2 16 Debian 也许这很重要 当我打
  • 默认的 VB6 字符集是什么?

    我们有一个用 Java 编写的应用程序 它读取 VB6 应用程序生成的一些文本 问题是 这个 VB6 应用程序使用一些特殊字符生成此输出 例如 我们不知道这些字符采用什么字符集 那么问题来了 VB6有没有使用默认的字符集 是哪一个 如何将数
  • 如何通过新的 V2 API 使用 Google Translate TTS?

    我曾经使用以下网址调用 Google Translate TTS 下载音频文件 然而谷歌改变了工作方式 因此我无法再下载音频文件 我已注册 Google Translate API V2 免费试用版 但找不到如何获取 TTS 音频文件 任何
  • Android 4.0.3 (MIUI ROM) 下未加载本机库

    一位客户联系我 当他将 Android ROM 更新到相当于 Android 4 0 3 的 MIUI 时 我的 Android 应用程序崩溃了 LogCat 中的相关行是 04 09 10 37 09 326 17789 17789 E
  • 在 OS X Lion 10.7.4 和 Python 3.2.2 上安装 MatPlotLib 1.2.x

    几天前我问了一个关于在同一系统上安装 numpy 的问题 值得庆幸的是 我自己设法解决了这个问题 但不幸的是我现在陷入了尝试安装 matplotlib 的困境 我首先尝试了当前的分布式版本 但没有成功 所以我想我应该下载 git 存储库并尝
  • 函数模板重载解析和编译器优化

    我正在看这里发现的这个问题包含类型的类型的模板函数重载 https stackoverflow com questions 44511121 template function overload for type containing a
  • 将数据存储为 flutter 中共享首选项中的对象

    我想在共享首选项中存储一个对象 其中包含一些字段 如姓名 年龄 电话号码等 我不知道如何在颤振中的共享首选项中存储对象 您可以将对象存储在共享首选项中 如下所示 SharedPreferences shared User await Sha
  • 使用 EDITBIN 时的错误代码 -1073741515

    我正在使用 EditBin 来增加我正在编写的应用程序的堆栈大小 我在 Visual Studio 的构建后事件命令行中包含以下内容 C Program Files x86 Microsoft Visual Studio 10 0 VC b
  • 如何使我的网站符合 PCI 标准

    假设我决定使用支付网关而不是使用他们的托管页面 而是提供我自己的信用卡详细信息表单 然后通过 xml 将数据发送到他们的后端 如下所示本页有解释 http www eway com au Developer eway api hosted
  • Java内存模型:编译器重新排列代码行

    众所周知 Java 语言允许编译器重新排列已编译代码行 只要重新排序对代码语义没有影响即可 然而 编译器只需关心语义 如从当前线程 如果这种重新排序影响多线程情况下的语义 通常会导致并发问题 内存可见性 我的问题 通过允许编译器使用这个 f
  • 如何使用 matplotlib 在圆环饼图中制作子图?

    如何使用Python的matplotlib为圆环饼图制作子图 下面是我写的代码 import matplotlib pyplot as plt labels Frogs Hogs Dogs sizes 15 30 45 colors yel
  • 如何将 Dart Html 客户端 Web 套接字响应从 Blob 转换为 Uint8List?

    我已经实现了自己的二进制消息协议 用于从 Dart 客户端到 Java 服务器的简单请求 响应对象 它们在 Dart 中编码为 Uint8List 在远程服务器上以 Java 编码为 ByteBuffer 往返适用于 dart io 中的
  • 将空格分隔的文件转换为 CSV

    我有一个包含表格数据的文本文件 我需要做的是自动执行写入以逗号分隔而不是空格分隔的新文本文件的任务 从现有数据中提取几列 对列重新排序 这是原始数据前 4 行的片段 Number of rows 8542 Algorithm Date Ti
  • dplyr 掩盖 GGally 并破坏 ggparcoord

    鉴于新的会议 执行一个小ggparcoord 函数文档中提供的示例 library GGally data diamonds package ggplot2 diamonds samp lt diamonds sample 1 dim di
  • 使用 Angular Web 应用程序调用 mongo/golang db 时被 CORS 策略错误阻止

    我正在制作一个前端带有 Angular 的 Web 应用程序 后端带有 golang 和 mongo 的数据库 我已经启动并运行了数据库 并且所有路由请求都已经过测试并且正在 Postman 上运行 但是 当我尝试对 Angular 应用程
  • 如何将 char* 转换为 std::vector?

    我有一个 char 变量 char buffer fread buffer 1 lSize pFile 如何将其转换为 std vector 铸造会给我一个错误 std vector
  • 如何在fragment中保存recyclerview的滚动位置

    我从这里遵循了很多答案 但没有一个解决我的问题 这就是我问的原因 我想在片段中保存滚动位置 在他们建议遵循的许多文章中 Override protected void onSaveInstanceState Bundle outState