仅在点击屏幕时检测到状态变化

State change detected only when screen is tapped

我有几个 TouchOpacity 组件,它们在按下时触发一个功能。此函数检索数据然后设置状态。

const Summary = () => {
  const [timeSpan, setTimeSpan] = useState('Day');
  const [derivedData, setDerivedData] = useState({
    chartTimeSpan: 'Day',
    sales: [],
    totalSales: 0,
    orders: 0,
    logins: 0,
  });

  const _fetchSummary = async (timeSpan) => {
    console.log(`_fetchSummary HIT : ${timeSpan}`);
    try {
      const res = await axios.get(`/summary/${timeSpan.toLowerCase()}`);
      const { loginCount, orderQty, sales, totalSales } = res.data;
      await setDerivedData({
        chartTimeSpan: timeSpan,
        sales,
        totalSales,
        orders: orderQty,
        logins: loginCount,
      });
      await setTimeSpan(timeSpan);
      console.log(timeSpan, loginCount, orderQty, sales, totalSales);
    } catch (err) {
      console.log(err);
    }
  };

  const _switchTimeSpan = (newTimeSpan) => {
    console.log(`TimeSpan : ${timeSpan}`);
    console.log(`NewTimeSpan : ${newTimeSpan}`);
    if (timeSpan !== newTimeSpan) {
      _fetchSummary(newTimeSpan);
    }
  };

  const { chartTimeSpan, sales, totalSales, orders, logins } = derivedData;
  console.log(derivedData);
  return (
    <>
  <TouchableOpacity onPress={() => _switchTimeSpan('Day')}>
    <Text style={dropDownItemStyle}>Day</Text>
  </TouchableOpacity>
  <TouchableOpacity onPress={() => _switchTimeSpan('Week')}>
    <Text style={dropDownItemStyle}>Week</Text>
  </TouchableOpacity>
  <TouchableOpacity onPress={() => _switchTimeSpan('Month')}>
    <Text style={dropDownItemStyle}>Month</Text>
  </TouchableOpacity>
  <TouchableOpacity onPress={() => _switchTimeSpan('Year')}>
    <Text style={dropDownItemStyle}>Year</Text>
  </TouchableOpacity>
    </>
  );
};

一切正常。当我也点击按钮时,数据被获取。但是,在获取数据后状态不会更新。我知道这一点是因为 console.log(derivedData); 就在 return 语句之上 运行。当我点击屏幕上的任意位置时,console.log(derivedData); 会给出预期的输出。请注意,我还没有设置任何在触摸屏幕时检测此事件的功能。

I have used the derivedData in some other components but did not include those for simplicity sake.

当需要重新渲染组件时,console.log(derivedData) 将是 运行。这取决于注入的状态和道具变量。由于 JSX 中未使用状态变量,因此无需重新渲染组件并记录新的 derivedData.

您可以使用 import { useEffect } from 'react' 绕过它。尝试使用以下方式记录派生数据:

useEffect(() => {
  console.log(derivedData);
});

这个问题是因为我在 App.js 文件中包含了以下代码行。

XMLHttpRequest = GLOBAL.originalXMLHttpRequest
  ? GLOBAL.originalXMLHttpRequest
  : GLOBAL.XMLHttpRequest;

// fetch logger
global._fetch = fetch;
global.fetch = (uri, options, ...args) => (global._fetch(uri, options, ...args)
  .then((response) => {
    console.log('Fetch', { request: { uri, options, ...args }, response });
    return response;
  }));

以上代码允许检测网络请求。我不知道为什么,但尽管上面的代码显示了网络请求,它也会延迟从请求传递到组件的数据,除非点击屏幕。

在生产环境中注释掉以上几行可以让代码正常工作。