Open In App

What are Refs used for in React Native ?

Improve
Improve
Like Article
Like
Save
Share
Report

Refs can be used to access DOM nodes or React Native components created in the render method.

We can use Refs in react native with the help of the useRef hook which returns a ref object. The object has a .current property through which the React native components can be accessed. 

The returned object will remain persistent for the whole component lifespan. It means that whenever the ref object is updated it does not cause your component to re-render.

It’s helpful for keeping any mutable value around, similar to how you’d use instance fields in classes.

Let’s use an illustration to assist you comprehend it:

Creating Application: Follow the below steps to create a React Native application:

Step 1: Open your terminal and install expo-cli by the following command.

npm install -g expo-cli

Step 2: Now create a project by the following command.

expo init Project

Step 3: Now go into your project folder i.e. Project

cd Project

Project Structure:

 

Example 1: We will be using ref in this example to create a button,  on click of which the focus should shift to the TextInput component.

In App.js First, we are importing the useRef hook from ‘react’. Then, inside the component, we are creating a ref object using useRef which is named as textRef. 

Pressing the button will call the createFocusOnTextInput() function, which in this case will shift the focus to the TextInput component. In this function, we are accessing the component with the help of .current property.

App.js




import { useState, useRef } from 'react';
import { Text, View, StyleSheet, TextInput, Button } 
    from 'react-native';
  
export default function App() {
    const [name, setName] = useState("")
  
    // Creating a ref Object using useRef Hook
    const textRef = useRef()
  
    // Function to shift focus on TextInput component
    function createFocusOnTextInput() {
        textRef.current.focus();
    }
  
    return (
        <View style={styles.container}>
            <TextInput
  
                // Creating reference to the TextInput component 
                ref={textRef}
                onChangeText={text => setName(text)}
                style={styles.input}
            />
            <Text style={styles.text}>My Name is {name}</Text>
            <Button
                onPress={createFocusOnTextInput}
                title="Focus On Text Input Component"
            />
        </View>
    );
}
  
// Styles for Text and View components
const styles = StyleSheet.create({
    container: {
        flex: 1,
        justifyContent: 'center',
        alignItems: 'center',
        backgroundColor: '#72e6e8',
        padding: 8,
        color: 'white'
    },
    input: {
        height: 40,
        width: 300,
        margin: 12,
        borderWidth: 3,
        color: '#000000',
        padding: 10,
    },
    text: {
        margin: 14,
        fontSize: 20,
        fontWeight: 'bold',
        textAlign: 'center',
        color: 'white',
    },
});


Step to run application: Open the terminal and type the following command.

npm start

Output:

 

As you can see in the output. With the press of the button, the focus gets shifted to the TextInput component. Another use of useRef is to show the no. of times a component is re-rendered on the screen.

Example 2: In the following example, we are creating a Text Input and showing its value in a text component.  Whenever we type something in the text input it triggers an event which in turn is updating the name state. As soon as the value of the state changes the components get re-rendered. Our goal is to count how many times the component is re-rending. So, we are updating renderCount.current by incrementing it. This update will never ever gonna causes our component to re-render bcz it’s completely separate from our component render lifecycle. 

App.js




import { useState, useEffect, useRef } from 'react';
import { Text, View, StyleSheet, TextInput }
    from 'react-native';
  
export default function App() {
    const [name, setName] = useState('')
    const renderCount = useRef(0)
  
    // It's an object with current property {current: 0}
    useEffect(() => {
  
        // Updating the counter value on each re-render
        renderCount.current = renderCount.current + 1
    })
  
    return (
        <View style={styles.container}>
            <TextInput
                onChangeText={text => setName(text)}
                style={styles.input}
            />
            <Text style={styles.text}>My Name is {name}</Text>
            <Text style={styles.text}>
                I rendered {renderCount.current} times
            </Text>
        </View>
    );
}
  
// Styles for Text and View components
const styles = StyleSheet.create({
    container: {
        flex: 1,
        justifyContent: 'center',
        alignItems: 'center',
        backgroundColor: '#72e6e8',
        padding: 8,
        color: 'white'
    },
    input: {
        height: 40,
        width: 300,
        margin: 12,
        borderWidth: 3,
        color: '#000000',
        padding: 10,
    },
    text: {
        margin: 14,
        fontSize: 20,
        fontWeight: 'bold',
        textAlign: 'center',
        color: 'white',
    },
});


Step to run application: Open the terminal and type the following command.

npm start

Output:

 

As you can see in the output, as soon as the value in TextInput is getting changed the name value is getting re-rendered and the renderCount is incremented at the same time. 

Why we can’t count the re-render using a simple UseState hook instead of UseRef?

It is because when the first time component renders it’s going to change the renderCount state, which causes re-render, then this state gets updated and again pushes the component to re-render and this goes on in an infinity loop. This is happening because the useState hook doesn’t persist values between renders. There is no way we can do this with the help useState because we can’t persist state values without useRef in functional components. 



Last Updated : 28 Dec, 2022
Like Article
Save Article
Previous
Next
Share your thoughts in the comments
Similar Reads