Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/mercurial/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
React native 使用一个对象跟踪UI元素状态,但一旦离开屏幕并返回,这些状态就不会保留_React Native_React Hooks_React Native Navigation - Fatal编程技术网

React native 使用一个对象跟踪UI元素状态,但一旦离开屏幕并返回,这些状态就不会保留

React native 使用一个对象跟踪UI元素状态,但一旦离开屏幕并返回,这些状态就不会保留,react-native,react-hooks,react-native-navigation,React Native,React Hooks,React Native Navigation,在我的react原生项目中,我有三个复选框,我需要跟踪这些复选框的状态,因此我使用一个具有键值(值为布尔值)的对象来表示所有三个复选框的状态,并使用useStatehook来管理它们。这是我的密码: import React,{useState,useffect}来自“React”; ... const MyScreen=({navigation})=>{ //最初,选中所有复选框 常量initialCheckBoxState={ 0:对, 1:对, 2:对, }; 常量[checkBoxesS

在我的react原生项目中,我有三个复选框,我需要跟踪这些复选框的状态,因此我使用一个具有键值(值为布尔值)的对象来表示所有三个复选框的状态,并使用
useState
hook来管理它们。这是我的密码:

import React,{useState,useffect}来自“React”;
...
const MyScreen=({navigation})=>{
//最初,选中所有复选框
常量initialCheckBoxState={
0:对,
1:对,
2:对,
};
常量[checkBoxesState,setCheckBoxesState]=useState(初始CheckBoxState);
useffect(()=>{
return()=>{
log(“屏幕未卸载”);
};
},[复选框状态];
返回(
...
(
{
常量checkboxessstatecompy={…checkBoxesState};
checkBoxesStateCopy[index]=!checkBoxesStateCopy[index];
设置复选框状态(复选框状态副本);
}}
/>
)}
/>
...
);
};
我省略了与我的问题无关的代码。如您所见,我为每个项目绘制一个
复选框
组件

实际上,始终有三个项目(即要显示的三个复选框)。在开始时,我声明了
initialCheckBoxState
,每个密钥对表示每个密钥的复选框的状态。在
on按下
复选框的
回调中
我切换每个复选框状态,并通过hook方法
setCheckBoxesState
整体更新
checkBoxesState

运行时一切正常,切换复选框状态时重新呈现我的屏幕,UI正确显示复选框的状态。但问题是,当我导航回上一个屏幕并导航回此屏幕时,所有复选框状态都返回到初始状态

那么,为什么复选框状态不保留


p.S.上一个屏幕和
MyScreen
在同一个堆栈导航器下。用户按下上一屏幕的按钮导航到
MyScreen
。从
MyScreen
用户可以通过按下“headerLeft”按钮转到上一个屏幕

您需要使用异步存储将数据保存到设备。组件卸载时,状态变量将被清除

异步存储文档:

从'@react native community/async storage'导入异步存储;
//只能存储字符串值,以便将对象转换为字符串:
const storeData=async(值)=>{
试一试{
const jsonValue=JSON.stringify(value)
等待AsyncStorage.setItem('@storage_Key',jsonValue)
}捕获(e){
//保存错误
}
}
const getData=async()=>{
试一试{
const jsonValue=wait AsyncStorage.getItem(“@storage\u Key”)
返回jsonValue!=null?JSON.parse(jsonValue):null;
}捕获(e){
//读取值时出错
}
}
更新-

由于React组件生命周期的性质,状态未被持久化。具体来说,当您离开屏幕时,将调用生命周期方法
componentWillUnmount

以下是一段摘录自:

componentWillUnmount()将在卸载和销毁组件之前立即调用。在此方法中执行任何必要的清理,例如使计时器无效、取消网络请求或清理在componentDidMount()中创建的任何订阅。 …组件实例一旦卸载,就再也不会被装载。

这意味着存储在状态中的任何值也将被销毁,当导航回屏幕
ComponentDidMount
时,将调用该屏幕,您可能希望在该屏幕上将持久值分配回状态


除了异步存储之外,还有两种可能的方法可以在某些用例中跨屏幕持久化数据,即使用异步存储或单例存储。

首先让我们回答这个问题:

为什么复选框状态不保留

此组件处理其状态完全独立,状态是在内部创建和处理的,没有值从外部传入。这是什么意思?该组件在其内部有其初始状态值,它不使用任何道具或任何其他东西来初始化状态。每次创建此组件时,状态都会再次使用该值初始化。因此,这就是您丢失对
复选框所做的所有更改的原因,因为当您离开此屏幕(组件)时,它将被卸载(我们将在下一个问题中讨论此问题),并且因为所有值都是在内部处理的,所以所有数据(包含复选框状态)都将丢失

现在让我们谈谈这个:

react native应该在返回屏幕时保留状态吗

简短的回答是否定的。每个组件在卸载时都会被销毁,包括它们的状态和数据

现在让我们来回答为什么

屏幕仍在内存堆栈中,没有被销毁

通常开发人员使用
react-navigation
RNRF
(构建在
react-navigation
之上)之类的软件包进行react-navigation,大多数时候我们并不关心他们如何处理这个导航逻辑,我们只使用提供给我们的界面。这些软件包中的每一个都有自己处理导航的方法。提供完整的答案,以确定为什么仍在内存中的屏幕需要完整的代码检查和大量的调试,但我想有两种可能性。首先,正如我所说的,由于某些原因,您使用的软件包可能会将未安装的屏幕保存在内存中至少一段时间。第二个问题是常见的
react
社区问题,即
未安装的组件仍在内存中
,您可以在以下位置进行检查:

最后让我们回答这个问题:

即使返回并丢失组件容器,如何保持复选框状态