Search justacoding.blog. [Enter] to search. Click anywhere to close.

August 30th, 2022

Hide An Element When The Keyboard Is Shown In React Native

There may be cases when working in React Native when you need to hide an element (or a set of elements) whenever the keyboard appears.

Once the keyboard is dismissed; the element(s) should then become visible again.

Fortunately, the Keyboard module makes this fairly trivial for us to implement.

Using event listeners to detect and react to keyboard visibility

As part of React Native’s Keyboard module, there are numerous events that we can we can listen out for. Specifically, there are 6 different events:

  • keyboardWillShow
  • keyboardWillHide
  • keyboardWillChangeFrame
  • keyboardDidShow
  • keyboardDidHide
  • keyboardDidChangeFrame

In this case, the two events that we are interested in in particular are keyboardDidShow and keyboardDidHide.

As you may have guessed, these events are fired whenever the keyboard becomes is shown and whenever it is hidden, respectively. That’s exactly what we need, here.

Given this, we can use Keyboard’s addListener method to go about attaching our required functionality to each of these events. This will form the crux of our solution — and ultimately allow us to hide an element (or a set of elements) whenever the keyboard is shown in our React Native application!

But first, let’s briefly recap how these events actually work.

A brief summary on events and event listeners

In basic terms, an event listener is simply a piece of functionality that waits (or “listens”) for a specific event to happen or occur within the application.

Functionality is executed once the underlying event is fired.

In this case, the keyboardDidShow and keyboardDidHide events are fired off by React Native’s Keyboard module; we can listen for these events and thus attach an event handler to react to each and every occurrence of the event(s) being fired off.

Utilising these events thus provides us the majority of the behaviours we need to actually hide elements when the keyboard appears (on when it shows).

Using Keyboard.addListener

The examples provided here use function components along with their associated functionality (ie. hooks).

If you’re using class-based components, however, it works in much the same way and the exact same principles apply.

Regardless, to actually listen for events emitted via React Native’s Keyboard module, you can do something like this:

import { Keyboard } from "react-native"

...

useEffect(() => {
    Keyboard.addListener("keyboardDidShow", () => {
        console.log("Keyboard visible")
    })
    Keyboard.addListener("keyboardDidHide", () => {
        console.log("Keyboard hidden")
    })
}, [])

Firstly, we want the listeners to be attached as soon as the component loads.

For that, we can use the useEffect hook with an empty array passed as the second parameter. This means the listeners will only be attached initially, one time — once the component actually mounts.

That’s exactly what we want.

At this point, we are listening for the relevant events – keyboardDidShow and keyboardDidHide.

If you try out the example yourself, you’ll see the logs output to the console every time you show or hide the keyboard in your application.

That’s great, but how do we now show and/or hide our target element(s) once this happens?

Attaching functionality to the listeners

It’s as simple as defining some state to track the keyboard’s visibility, for example:

const [keyboardIsVisible, setKeyboardIsVisible] = useState(false)

The idea here is that we’ll modify this value provided by the useState hook (to either true or false) once the keyboard visibility actually changes, using the listeners we defined above.

We can then use this boolean to dictate whether other elements in the app should be visible or not:

useEffect(() => {
    Keyboard.addListener("keyboardDidShow", () => {
        setKeyboardIsVisible(true)
    })
    Keyboard.addListener("keyboardDidHide", () => {
        setKeyboardIsVisible(false)
    })
}, [])

So to recap so far, we have:

  • attached an event listener to detect when the keyboard is shown
  • attached an event listener to detect when the keyboard is hidden
  • attached functionality to each event listener; which effectively modifies a boolean value in our application’s state

Now it’s time to use that boolean value to dictate whether we should show or hide our target elements.

Showing or hiding elements once the keyboard visibility changes

We can simply consult the boolean value (keyboardIsVisible) to dictate visibility:

{keyboardIsVisible && <Text>Show me when the keyboard is visible</Text>

The keyboardIsVisible boolean can be used throughout the app as and when required; due to the event listeners we’ve implemented, we know it’ll always be updated to correctly inform us of the keyboard visibility.

Note: there are a few things to be aware of when showing and hiding elements or other components in React, particularly when operating inside JSX output. Be sure to familiarise yourself with these quirks!

And that’s it.

This should be all you need to react to the keyboard visibility changes through your React Native application; event listeners coupled with a boolean within your app’s state.

Cleaning up after ourselves – using Keyboard.removeListener

The snippet we have now works fine, however, it’s lacking something very important.

It should be updated to look like this:

useEffect(() => {
    const showListener = Keyboard.addListener("keyboardDidShow", () => {
        setKeyboardIsVisible(true)
    })
    const hideListener = Keyboard.addListener("keyboardDidHide", () => {
        setKeyboardIsVisible(false)
    })

    return () => {
        showListener.remove()
        hideListener.remove()
    }
}, [])

You’ll notice the addition of:

return () => {
    showListener.remove()
    hideListener.remove()
}

If you aren’t familiar, the function we return from the useEffect hook here will execute once the component unmounts.

This makes it the ideal place for cleanup code. In fact, this return function is commonly referred to as a cleanup function.

In this case, we want to remove the Keyboard event listeners entirely to avoid any unwanted side-effects or problematic behaviours. It’s always good practice to clean up after yourself in this manner.

If something is registered in some way in your component; it’s likely it should be deregistered once the component is no longer in use (or mounted). Remember to consider this (whether anything should happen on component unmount) when working in React Native and, by extension, in React in general.

Other cases when you may need to cleanup after yourself

If you’ve ever created a component that makes web requests, you’re likely familiar with the issues that can occur here.

As an example, let’s say your component makes a web request upon initial load to fetch some data.

However, the component unmounts before this request actually completes. The user may navigate away from the given page, for instance. This would cause the component to unmount.

But what happens now?

Well, you’ll get an error.

That’s because the component didn’t really finish it’s work, and the promise (ie. the web request) didn’t get to resolve before the component was unmounted. So there’s still “stuff” happening, functionality in flight — even though the component is no longer actually mounted.

This is a no-go.

To rectify this, we can handle this scenario in the same way that we handle event subscriptions above; add a cleanup function that would cancel or abort the request!

To summarise

We’ve looked at using event listeners to aid with showing and hiding elements or other components in your React Native application when the keyboard is either shown or hidden.

These event listeners are provided via the Keyboard module.

Thanks for reading!

You can check out other, similar articles in the React Native section.

Thanks for reading!

Have any questions? Ping me over at @justacodingblog
← Back to blog