Friday 28 January 2022

React Native Issue Highlighting Hashtags/Mentions in TextInput as User Types

I'm attempting to create a TextInput that detects and highlights #hashtags or @mentions as the user types. I'm using the code from this gist as a starting point which, from the GIFs on the gist, appears to do exactly what I want. However, I'm seeing some unexpected lag when I implement this solution.

I have "mention" color set to red, and all other text set to green. You'll notice in the GIF that after I move the cursor back to the highlighted portion of the code, then press space and start typing again, each letter from then on is very briefly colored red then flips to green. It's very subtle, and only appears to happen if I move the cursor back to a highlighted word and start typing from there.

I observed the same behavior on iOS simulator (14.5 and 15.2), a physical device (15.2) running Expo Go, and when running the app from Xcode directly on my physical device (outside of Expo Go).

How can I avoid the delay in formatting?

This is a fresh react native project created via expo init. The entirety of the project is pasted below:

package.json

{
  "name": "reactnativeplayground",
  "version": "1.0.0",
  "main": "index.js",
  "scripts": {
    "start": "expo start --dev-client",
    "android": "expo run:android",
    "ios": "expo run:ios",
    "web": "expo start --web"
  },
  "dependencies": {
    "expo": "~44.0.2",
    "expo-splash-screen": "~0.14.1",
    "expo-status-bar": "~1.2.0",
    "react": "17.0.1",
    "react-dom": "17.0.1",
    "react-native": "0.64.3",
    "react-native-web": "0.17.1"
  },
  "devDependencies": {
    "@babel/core": "^7.12.9"
  },
  "private": true
}

App.js

import { StatusBar } from 'expo-status-bar';
import React from 'react';
import { StyleSheet, Text, View, TextInput } from 'react-native';

export default function App() {
  const [testFormattedContent, setTestFormattedContent] = React.useState('');

  const handleChangeText = (inputText) => {
    const retLines = inputText.split("\n");
    const formattedText = [];
    retLines.forEach((retLine) => {
      const words = retLine.split(" ");
      const contentLength = words.length;
      var format = /[ !#@$%^&*()_+\-=\[\]{};':"\\|,.<>\/?\n]/;
      words.forEach((word,index) => {
        if (
          (word.startsWith("@") && !format.test(word.substr(1))) ||
          (word.startsWith("#") && !format.test(word.substr(1)))
        ) {
          const mention = (
            <Text key={index} style=>
              {word}
            </Text>
          );
          if (index !== contentLength - 1) formattedText.push(mention, " ");
          else formattedText.push(mention);
        } else {
          if (index !== contentLength - 1) return formattedText.push(word, " ");
          else return formattedText.push(word);
        }
      });
    });

    setTestFormattedContent(formattedText);
  };

  return (
    <View style={styles.container}>
      <TextInput
        style=
        onChangeText={handleChangeText}
      >
        <Text>{testFormattedContent}</Text>
      </TextInput>
    </View>
  );
}

const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: '#fff',
    // alignItems: 'center',
    // justifyContent: 'center',
  },
});




from React Native Issue Highlighting Hashtags/Mentions in TextInput as User Types

No comments:

Post a Comment