The toggle switch button in React Native is a component which is used commonly in our projects. React Native core modules has it’s predefined toggle switch component which is interacting differently in android and ios platforms. We are going to create a custom switch react native with reanimated v2. So the toggle switch button that we are going to implement will interact the same on both android and IOS platforms.
Now let’s look at what the native toggle switch button looks like;
Now let’s see what we are going to achieve in this article.
This will look the same on android and IOS both. Let’s check how to implement this with react-native-reanimated. This is the only package that we need to create our custom toggle switch button.
Let’s get to the coding part of the react native switch. First I will share the full code and then we will discuss them one by one.
This is a rough diagram of the constants that we have declared.
Before checking the code please note that I have created this as a custom component that can be used in our switch lists in react native easily. So you can reuse and customize this custom switch button according to your requirement.
Props Delcared
onChange
: To pass the current value of the react native switch button(true or false),value
: This is the default value for the toggle switch button,containerStyle
: React native switch styletoggleOffColor
: The colour of the toggle area when the toggle value is set to falsetoggleOnColor
: The colour of the toggle area when the toggle value is set to true,height
: Height of the toggle switch,width
: Width of the toggle,BUTTON_WIDTH,BUTTON_HEIGHT
and added the width which is coming from the props. Then we have declared the inner circle which is animatable as SWITCH_BUTTON_AREA.
Also, we have declared a useState
function so that we can set the current switch value and pass that value through onChange
function when switching as given below. We have used useSharedValue
to keep the track of the switch area and to animate it.How onPressSwitch function works?
When we tap on the list item we need to set the shared value. So if the current shared value is 0 then set it as 1 and vice versa. Also, we have not set the shared values directly we have added withTiming
which are coming in the reanimated module. So that the shared values change accordingly between the time frame. withTiming
allows parameters duration
, easing
. Here we have given 800 milliseconds for the duration. In 800 milliseconds the shared values change periodically. And also for Easing how the animation should happen. After all this, we called the onChangeToggle
function which sets the current switch value in the component itself and also we are sending that value through the onChange
function.
You can find a visualization of some common easing functions at http://easings.net/.
How to animate the toggle switch button and use colour interpolation.
So we have created a TouchableOpacity
and inside that button, we have created our animated switch area(View
) with absolute positioning. You can refer to the styles that we have given when creating the toggle switch button. And to get rid of the opacity when tapping on the button we have given the activeOpacity to 1. Then for styles, we have given the containerScale
style which is nothing but the react native switch size(height and width). Then we declared the height and width of the animated switch area which is the rounded circle as switchScale
. That is our animated view.
Interpolating switch area
We are using the useAnimatedStyle
hook from react native reanimated to implement our animations for the switch button. When we tap on the switch button the switch rounded circle should navigate in the X direction to the end of the button with padding SWITCH_BUTTON_PADDING.
So the inner switch circle should move from 0 to BUTTON_WIDTH - SWITCH_BUTTON_AREA - 2 * SWITCH_BUTTON_PADDING
amount of pixels in X direction to finish the switching. For that, we have used interpolate
. It will accept four parameters.
It is sometimes necessary to map a value from one range to another. Here, you should make use of the interpolate function, which allows you to translate a value from the input range to a similar approximation in the output range and approximates values between points in the output range. In order to enable mapping outside the range, it additionally supports a few types of extrapolation. So we have given the shared value as the current value and the input range as 0 to 1. Then the outputt range is 0 toBUTTON_WIDTH - SWITCH_BUTTON_AREA - 2 * SWITCH_BUTTON_PADDING.
So the switch will animate in X direction accordingly. The fourth param that we are adding is how the extrapolation should happen. So the default extrapolation is extend.
By applying the clamp
the switch button will behave only inside the button. That means suppose we set the output shared value to 2. Then in that case clamp
will only use the input range that we provide only. That is 0 to 1.
Here is a nice article where you can get more information about extrapolate.
Interpolate background colour
And lastly, we have to set the colour of the toggle switch button when it is in the OFF state and ON state. So we use interpolateColor which is coming from the reanimated module that we can interpolate colours also. There also we can add our shared value which is the value that changes an input range from 0 to 1. Then when the input changes we can give the colours that we want to change.
And lastly, we can add our animations to the View that we created above. That’s it for the development of the custom react native switch button.
Finally, you can create a list of items like the below as your requirement.
That’s it pretty much. I will attach all my projects here with the GitHub link. you can refer me anytime.
https://github.com/pasindu1/AnimateSwipeButton. This contains all the projects that I have been working on so far.
If you have any questions, or comments or think that there is a better way to implement this — feel free to comment here or reach out at [email protected]. Thank you.
1 comment(s)
Aryk Grosz
https://gist.github.com/Aryk/380dffa6464603ec7b1e0c3598edff65 :)