Home > Back-end >  Custom React Native Slider
Custom React Native Slider

Time:03-03

Does anyone know how to render a slider in react-native like the below, with distinct sections? So far, have only seen sliders with one line and one dot.

Example Slider

CodePudding user response:

You can achieve this type of slider by using LayoutAnimation. Find the below code to get it done.

import React, { useState } from 'react';
import {Button,LayoutAnimation,Platform,StyleSheet,Text,UIManager,View} from 'react-native';

if (Platform.OS === 'android') {
  if (UIManager.setLayoutAnimationEnabledExperimental) {
    UIManager.setLayoutAnimationEnabledExperimental(true);
  }
}

const step = ['1', '2', '3', '4', '5', '6', '7'];
const activeColor = '#444';

export default function TrackingStatus() {
  const [activeIndex, setActive] = useState(0);
  const setActiveIndex = (val) => {
    LayoutAnimation.easeInEaseOut();
    setActive(val);
  };
  const marginLeft = (100 / (step.length - 1)) * activeIndex - 100   '%';
  return (
    <View style={styles.constainer}>
      <Text style={styles.prop}>{activeIndex}</Text>
      <View style={styles.statusContainer}>
        <View style={styles.line}>
          <View style={[styles.activeLine, { marginLeft }]} />
        </View>
        {step.map((step, index) => (
          <View style={[styles.dot]} key={step}>
            <View
              style={[
                index <= activeIndex
                  ? { height: '100%', width: '100%' }
                  : { height: '0%', width: '0%' },
                { backgroundColor: activeColor, borderRadius: 20 },
              ]}
            />
          </View>
        ))}
      </View>
      <View style={styles.btns}>
        <Button
          title="prev"
          onPress={() => setActiveIndex(activeIndex - 1)}
          disabled={activeIndex <= 0}
        />
        <Button
          title="next"
          onPress={() => setActiveIndex(activeIndex   1)}
          disabled={activeIndex >= step.length - 1}
        />
      </View>
    </View>
  );
}

const styles = StyleSheet.create({
  constainer: {
    flex: 1,
    justifyContent: 'center',
    alignItems: 'center',
    paddingHorizontal: 30,
  },
  statusContainer: {
    flexDirection: 'row',
    alignItems: 'center',
    width: '100%',
    height: 70,
    justifyContent: 'space-between',
  },
  dot: {
    height: 15,
    width: 15,
    borderRadius: 10,
    backgroundColor: '#ccc',
    overflow: 'hidden',
    alignItems: 'center',
    justifyContent: 'center',
  },    
  line: {
    height: 5,
    width: '100%',
    backgroundColor: '#ccc',
    position: 'absolute',
    borderRadius: 5,
    overflow: 'hidden',
  },
  activeLine: {
    height: '100%',
    width: '100%',
    backgroundColor: activeColor,
    borderRadius: 5,
  },
  btns: {
    width: '100%',
    flexDirection: 'row',
    justifyContent: 'space-evenly',
    marginTop: 20,
  },
  prop: {
    marginBottom: 20,
    width: 100,
    textAlign: 'center',
  },
});

In the above code, We simply create a UI clone as required and add margin-left as well as filling dots with colour. just before changing the state of margin-left & dot colour, we added layout animation to add an animation effect for progress.

Output enter image description here

I hope this explanation will help you understand the working

  • Related