React-responsive-carousel: Reset slider position on every render of carousel

Created on 28 Dec 2020  ·  5Comments  ·  Source: leandrowd/react-responsive-carousel

18

hey,
I am facing an issue with react-responsive-carousel.

I have a parent component :

//Main

 return (
    <>
        <Wrapper>
          <UserDisplay
            user={currentUserDisplay}
            handleLike={handleLike}
            handleUnLike={handleUnLike}
          />
        </Wrapper>
    </>
  );

and a child component:
//UserDisplay

const UserDisplay = ({ user, handleLike, handleUnLike }) => {

  const { firstName, images } = user;
      <div>
        <Carousel
          infiniteLoop={true}
          showStatus={false}
          showArrows={false}
          showThumbs={false}
          selectedItem={0}
        >
          {images.map(({ img }, i) => (
            <div className="item" key={i}>
              <ProfilePicture urlPath={img}>
                <Text>{`${firstName}`}</Text>
              </ProfilePicture>
            </div>
          ))}
        </Carousel>
      </div>
};

Whenever a user changes at parent component , different images will be displayed at the carousel, as expected.
My problem is , the slider's position from previous user remains the same for the next carousel.
The selectedItem property assigns 0 only for the first render .

for example:
if I was starting from position 0 , then scrolling to the third image at the first user ,
i will also view the third image of the next user, when the current user changes.

what I try to achieve is , resetting the slider's position to 0 whenever a user changes.
thanks :)

wontfix

Most helpful comment

A better workaround to your problem is to use the key prop since it creates a new instance rather than update the current one when the key changes.
Your code will be something like this:

const UserDisplay = ({ user, handleLike, handleUnLike }) => {

  const { firstName, images } = user;
      <div>
        <Carousel
          // When it changes, a new instance will be created and the state will reset
          key={user.someUniqueValue} 
          infiniteLoop={true}
          showStatus={false}
          showArrows={false}
          showThumbs={false}
          selectedItem={0}
        >
          {images.map(({ img }, i) => (
            <div className="item" key={i}>
              <ProfilePicture urlPath={img}>
                <Text>{`${firstName}`}</Text>
              </ProfilePicture>
            </div>
          ))}
        </Carousel>
      </div>
};

All 5 comments

I had the same problem with react-responsive-carousel days ago, I just did this:

I will use your component as example:

  // first import useRef
  import React, { useRef } from 'react';

  const UserDisplay = ({ user, handleLike, handleUnLike }) => {

  // use useRef to get the carousel instance
  let carousel = useRef(null);

  const { firstName, images } = user;

  // then in a useEffect that listen to user or images for example and waiting for a change, set
  // the valor of slider to 0

  useEffect(() => {
    // some validation to set the slider to 0
     if (carousel && carousel?.state?.selectedItem > 0) {
       carousel.state.selectedItem = 0;
     }
  }, [images]);


      <div>
        <Carousel
          ref={el => (carousel = el)} // useRef
          infiniteLoop={true}
          showStatus={false}
          showArrows={false}
          showThumbs={false}
          selectedItem={0}
        >
          {images.map(({ img }, i) => (
            <div className="item" key={i}>
              <ProfilePicture urlPath={img}>
                <Text>{`${firstName}`}</Text>
              </ProfilePicture>
            </div>
          ))}
        </Carousel>
      </div>
 };

I hope this could help you 👍

I had the same problem with react-responsive-carousel days ago, I just did this:

I will use your component as example:

  // first import useRef
  import React, { useRef } from 'react';

  const UserDisplay = ({ user, handleLike, handleUnLike }) => {

  // use useRef to get the carousel instance
  let carousel = useRef(null);

  const { firstName, images } = user;

  // then in a useEffect that listen to user or images for example and waiting for a change, set
  // the valor of slider to 0

  useEffect(() => {
    // some validation to set the slider to 0
     if (carousel && carousel?.state?.selectedItem > 0) {
       carousel.state.selectedItem = 0;
     }
  }, [images]);


      <div>
        <Carousel
          ref={el => (carousel = el)} // useRef
          infiniteLoop={true}
          showStatus={false}
          showArrows={false}
          showThumbs={false}
          selectedItem={0}
        >
          {images.map(({ img }, i) => (
            <div className="item" key={i}>
              <ProfilePicture urlPath={img}>
                <Text>{`${firstName}`}</Text>
              </ProfilePicture>
            </div>
          ))}
        </Carousel>
      </div>
 };

I hope this could help you 👍

Actually looking at it again , it looks like it should work , and when i debugged it , I could see the state of the carousel changes to 0 . but the component doesnt re-render, so the change cant be seen at the ui. I was able to solve it with a useForceUpdate hook , but it seems not the best approach to me :)

A better workaround to your problem is to use the key prop since it creates a new instance rather than update the current one when the key changes.
Your code will be something like this:

const UserDisplay = ({ user, handleLike, handleUnLike }) => {

  const { firstName, images } = user;
      <div>
        <Carousel
          // When it changes, a new instance will be created and the state will reset
          key={user.someUniqueValue} 
          infiniteLoop={true}
          showStatus={false}
          showArrows={false}
          showThumbs={false}
          selectedItem={0}
        >
          {images.map(({ img }, i) => (
            <div className="item" key={i}>
              <ProfilePicture urlPath={img}>
                <Text>{`${firstName}`}</Text>
              </ProfilePicture>
            </div>
          ))}
        </Carousel>
      </div>
};

Awsome!

בתאריך יום ד׳, 3 בפבר׳ 2021, 17:34, מאת Renan Cleyson ‏<
[email protected]>:

A better workaround to your problem is to use the key prop since it
creates a new instance rather than update the current one when the key
changes.
Your code will be something like this:

const UserDisplay = ({ user, handleLike, handleUnLike }) => {

const { firstName, images } = user;


// When it changes, a new instance will be created and the state will reset
key={user.someUniqueValue}
infiniteLoop={true}
showStatus={false}
showArrows={false}
showThumbs={false}
selectedItem={0}
>
{images.map(({ img }, i) => (
{${firstName}}


))}

};


You are receiving this because you authored the thread.
Reply to this email directly, view it on GitHub
https://github.com/leandrowd/react-responsive-carousel/issues/536#issuecomment-772599031,
or unsubscribe
https://github.com/notifications/unsubscribe-auth/AHG4VJIW5HI3RTDWASHB3Z3S5FUJLANCNFSM4VLXDEPA
.

This issue has been automatically marked as stale because it has not had recent activity. It will be closed if no further activity occurs. Thank you for your contributions.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

Jordanh1996 picture Jordanh1996  ·  6Comments

paulgasbarra picture paulgasbarra  ·  5Comments

PatrikKozak picture PatrikKozak  ·  3Comments

sinaler picture sinaler  ·  3Comments

ShineOfFire picture ShineOfFire  ·  6Comments