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

如何仅在光标移动但输入内容未变更时触发onSelectionChange事件

实现方案

核心思路为通过缓存上一次的输入文本和光标选区状态,在onSelectionChange触发时做双重校验,只有文本未变更、选区发生变化的场景才执行业务逻辑。

具体实现步骤

  • 声明两个状态分别缓存上一次的输入文本prevText、上一次的光标选区prevSelection
  • 在onChangeText回调中同步最新输入文本到状态
  • 在onSelectionChange回调中先判断当前文本是否和prevText相等:
    • 不相等:说明本次触发由文本变更(输入/删除/粘贴等)导致,直接更新prevText和prevSelection缓存后返回,不执行业务逻辑
    • 相等:再判断当前选区和prevSelection是否不一致,不一致则说明是纯光标移动,执行@提及相关业务逻辑,之后更新prevSelection即可

代码示例

import React, { useState } from 'react';
import { TextInput } from 'react-native';

const MentionInput = () => {
  const [text, setText] = useState('');
  // 缓存上一次的文本和选区状态
  const [prevText, setPrevText] = useState('');
  const [prevSelection, setPrevSelection] = useState({ start: 0, end: 0 });

  const handleSelectionChange = (e) => {
    const currentSelection = e.nativeEvent.selection;
    // 文本发生变更,直接更新缓存后返回,不执行业务逻辑
    if (text !== prevText) {
      setPrevText(text);
      setPrevSelection(currentSelection);
      return;
    }
    // 文本未变更,且选区发生变化,说明是纯光标移动/选区调整
    if (currentSelection.start !== prevSelection.start || currentSelection.end !== prevSelection.end) {
      // 此处写入@提及相关业务逻辑
      console.log('仅光标移动,触发业务逻辑', currentSelection);
      setPrevSelection(currentSelection);
    }
  };

  return (
    <TextInput
      value={text}
      onChangeText={setText}
      onSelectionChange={handleSelectionChange}
      multiline
      style={{ height: 100, borderWidth: 1, padding: 8 }}
    />
  );
};

export default MentionInput;

注意事项

  • 该方案兼容所有文本变更场景:包括输入、删除、剪切、粘贴等操作导致的选区变化,都会被正常过滤
  • 支持长按选中文本的场景识别,选中文本时文本内容未变更仅选区范围变化,会正常触发业务逻辑
  • 受控组件场景下需确保text状态更新逻辑正常,避免出现状态不同步导致的判断错误

内容的提问来源于stack exchange,提问作者Talmacel Marian Silviu

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.01 11:45:05