miblanchard / react-native-slider

A pure JavaScript <Slider> component for react-native and react-native-web

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Is there anyway to make just the trackmarks clickable?

dlinds opened this issue · comments

Hello!

I have a screen I'm working with where we have 10 or so sliders, and have to scroll to get to the bottom of the screen. We currently have the trackClickable prop set to false and that works for page scrolling, and enabling it makes it so scrolling is a bit more difficult (since the slider is grabbing the press).

We have five track marks that we would like to be pressable, so I am wondering the best way to accomplish this? We have a custom trackmark component that I've rendering as a Pressable with a large hitSlop but that doesn't totally help (the track gets in the way I believe - though outside of the Slider component I can locate and press the hitslop).

  const customTrackMark = (mark: number) => (
    <Pressable
      onPress={() => setSelectedValue(mark)}
      hitSlop={{ top: 20, bottom: 20, left: 20, right: 20 }}
      style={{
        backgroundColor: "pink",
        height: 10,
        width: 10,
        borderRadius: 10,
      }}
    />
  )

Essentially, we want pressability for trackmarks, but not the entire track.

Thanks!

For anyone else who ever has this question (and if the library doesn't support it at time of reading), the workaround I had was to add a group of transparent components on top of each track mark. Whichever index the thumb is currently at, the zIndex of that track mark will not be set (dropping it behind the thumb), otherwise the transparent track mark area zIndex is set to 100.

const { width: screenWidth } = Dimensions.get("screen")

 const transparentTrackMarks = () =>
   values.map((value) => (
     <Pressable
       key={value}
       style={{
         ...styles.transparentTrackMark,
         width: screenWidth * 0.08, // set a width for the pressable area
         left: `${value * 23}%`,
         ...(currentSliderPosition === value ? {} : { zIndex: 100 }),
       }}
       onPress={() => handleOnValueChange([value])}
     />
   )) 

styles =

  transparentTrackMark: {
    position: "absolute",
    top: 2,
    height: 32,
    width: 32,
    backgroundColor: "pink" //remove this, only used for demoing clickable area
  },

  sliderContainer: {
    zIndex: 10,
  },

implementation

  return (
    <>
      {transparentTrackMarks()}
      <View style={styles.sliderContainer}>
        <Slider
          value={currentSliderPosition}
          trackClickable={false}
          onValueChange={handleOnValueChange} //same handler for transparent track mark
         ....