You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在条件下操作LocalStorage并解决Tenzies游戏计时显示异常

解决Tenzies游戏LocalStorage读写及UI展示问题

问题1:fetchPrevioustime多次执行

原因:直接将fetchPrevioustime()作为useState初始值时,组件每次渲染都会调用该函数。useState的函数式初始值写法才能保证仅在组件首次挂载时执行一次。

解决:
修改state初始化逻辑,改用函数式初始化:

const [recordTime, setRecordTime] = useState(() => fetchPreviousTime())

同时修正fetchPreviousTime的返回结构,确保统一:

function fetchPreviousTime() {
  const storedRecord = localStorage.getItem("recordTime");
  // 有记录则解析返回,无记录则返回默认最大时间(方便后续比较)
  if (storedRecord) {
    return JSON.parse(storedRecord);
  }
  return { mn: "99", sc: "59" };
}

问题2:recordTime.sc展示为空

原因:

  1. 数据结构混乱:获胜时存储数组[{mn, sc}],初始化时返回嵌套对象{recordedTime: 数组},导致recordTime结构时而为数组、时而为对象,无法稳定读取.sc属性。
  2. 未处理无历史记录的边界情况,初始值可能为undefined,读取属性会报错或为空。

解决:

步骤1:统一存储结构并加入时间比较逻辑

将存储格式改为单个时间对象,同时仅在当前耗时更短时更新记录:

useEffect(() => {
  if (tenzies) {
    // 转换为总秒数方便比较
    const currentTotalSeconds = parseInt(mn) * 60 + parseInt(sc);
    const recordTotalSeconds = parseInt(recordTime.mn) * 60 + parseInt(recordTime.sc);

    if (currentTotalSeconds < recordTotalSeconds) {
      const newRecord = { mn, sc };
      localStorage.setItem("recordTime", JSON.stringify(newRecord));
      setRecordTime(newRecord);
    }
  }
}, [tenzies, mn, sc, recordTime]);

步骤2:修正UI展示逻辑

现在recordTime始终是包含mn和sc的对象,直接读取即可,同时添加无记录的友好提示:

<div className="congrats" style={stylesWon}>
  Congrats! You have won the game. <br></br>
  You took {mn > 0 && `${mn} minutes and `} {sc} seconds.
  Your best time is {recordTime.mn !== "99" ? `${recordTime.mn}m ${recordTime.sc}s` : "暂无记录"}
</div>

完整关键代码总结

  1. 初始化state:
const [recordTime, setRecordTime] = useState(() => fetchPreviousTime());

function fetchPreviousTime() {
  const storedRecord = localStorage.getItem("recordTime");
  return storedRecord ? JSON.parse(storedRecord) : { mn: "99", sc: "59" };
}
  1. 获胜时的更新逻辑:
useEffect(() => {
  if (tenzies) {
    const currentTotal = parseInt(mn) * 60 + parseInt(sc);
    const recordTotal = parseInt(recordTime.mn) * 60 + parseInt(recordTime.sc);

    if (currentTotal < recordTotal) {
      const newRecord = { mn, sc };
      localStorage.setItem("recordTime", JSON.stringify(newRecord));
      setRecordTime(newRecord);
    }
  }
}, [tenzies, mn, sc, recordTime]);
  1. UI展示:
<div className="congrats" style={stylesWon}>
  Congrats! You have won the game. <br></br>
  You took {mn > 0 && `${mn} minutes and `} {sc} seconds.
  Your best time is {recordTime.mn !== "99" ? `${recordTime.mn}m ${recordTime.sc}s` : "暂无记录"}
</div>

内容的提问来源于stack exchange,提问作者nikita jd

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.20 00:45:52