2

I'm using keen-slider@6.8.5 in a next@13.4.7 project. When my page loads in initial state of loading before javascript load finishs, I get this result image before loading properly and when it's load finishes, I get this result which is fine imae after loading. I don't want users to see result of slider like first image. I have made a component for slider and this is my code. could anyone tell me what to do?

I tried changing flex style but it stucks on one image

this is the code of what I've done:

"use client";
import Image from "next/image";
import  "./styles.css";
import "keen-slider/keen-slider.min.css";
import KeenSlider from "keen-slider";
import { useKeenSlider } from "keen-slider/react";
import React, { useRef, useState } from "react";

export default function Home() {
  const [currentSlide, setCurrentSlide] = useState(0);
  const [loaded, setLoaded] = useState(false);
  const [sliderRef, instanceRef] = useKeenSlider<HTMLDivElement>({
    initial: 0,
    slideChanged(slider) {
      setCurrentSlide(slider.track.details.rel);
    },
    created() {
      setLoaded(true);
    },
  });

  return (
    <>
      <div className="navigation-wrapper">
        <div ref={sliderRef} className="keen-slider">
          <div className="keen-slider__slide number-slide1">1</div>
          <div className="keen-slider__slide number-slide2">2</div>
          <div className="keen-slider__slide number-slide3">3</div>
          <div className="keen-slider__slide number-slide4">4</div>
          <div className="keen-slider__slide number-slide5">5</div>
          <div className="keen-slider__slide number-slide6">6</div>
        </div>
        {loaded && instanceRef.current && (
          <>
            <Arrow
              left
              onClick={(e: any) =>
                e.stopPropagation() || instanceRef.current?.prev()
              }
              disabled={currentSlide === 0}
            />

            <Arrow
              onClick={(e: any) =>
                e.stopPropagation() || instanceRef.current?.next()
              }
              disabled={
                currentSlide ===
                instanceRef.current.track.details.slides.length - 1
              }
            />
          </>
        )}
      </div>
      {loaded && instanceRef.current && (
        <div className="dots">
          {[
            ...Array(instanceRef.current.track.details.slides.length).keys(),
          ].map((idx) => {
            return (
              <button
                key={idx}
                onClick={() => {
                  instanceRef.current?.moveToIdx(idx);
                }}
                className={"dot" + (currentSlide === idx ? " active" : "")}
              ></button>
            );
          })}
        </div>
      )}
    </>
  );
}

function Arrow(props: {
  disabled: boolean;
  left?: boolean;
  onClick: (e: any) => void;
}) {
  const disabeld = props.disabled ? " arrow--disabled" : "";
  return (
    <svg
      onClick={props.onClick}
      className={`arrow ${
        props.left ? "arrow--left" : "arrow--right"
      } ${disabeld}`}
      xmlns="http://www.w3.org/2000/svg"
      viewBox="0 0 24 24"
    >
      {props.left && (
        <path d="M16.67 0l2.83 2.829-9.339 9.175 9.339 9.167-2.83 2.829-12.17-11.996z" />
      )}
      {!props.left && (
        <path d="M5 3l3.057-3 11.943 12-11.943 12-3.057-3 9-9z" />
      )}
    </svg>
  );
}
[class^="number-slide"],
[class*=" number-slide"] {
  background: grey;
  display: flex;
  align-items: center;
  justify-content: center;
  font-size: 50px;
  color: #fff;
  font-weight: 500;
  height: 300px;
  max-height: 100vh;
}

.number-slide1 {
  background: rgb(64, 175, 255);
  background: linear-gradient(
    128deg,
    rgba(64, 175, 255, 1) 0%,
    rgba(63, 97, 255, 1) 100%
  );
}

.number-slide2 {
  background: rgb(255, 75, 64);
  background: linear-gradient(
    128deg,
    rgba(255, 154, 63, 1) 0%,
    rgba(255, 75, 64, 1) 100%
  );
}

.number-slide3 {
  background: rgb(182, 255, 64);
  background: linear-gradient(
    128deg,
    rgba(182, 255, 64, 1) 0%,
    rgba(63, 255, 71, 1) 100%
  );
  background: linear-gradient(
    128deg,
    rgba(189, 255, 83, 1) 0%,
    rgba(43, 250, 82, 1) 100%
  );
}

.number-slide4 {
  background: rgb(64, 255, 242);
  background: linear-gradient(
    128deg,
    rgba(64, 255, 242, 1) 0%,
    rgba(63, 188, 255, 1) 100%
  );
}

.number-slide5 {
  background: rgb(255, 64, 156);
  background: linear-gradient(
    128deg,
    rgba(255, 64, 156, 1) 0%,
    rgba(255, 63, 63, 1) 100%
  );
}

.number-slide6 {
  background: rgb(64, 76, 255);
  background: linear-gradient(
    128deg,
    rgba(64, 76, 255, 1) 0%,
    rgba(174, 63, 255, 1) 100%
  );
}

.navigation-wrapper {
  position: relative;
}

.dots {
  display: flex;
  padding: 10px 0;
  justify-content: center;
}

.dot {
  border: none;
  width: 10px;
  height: 10px;
  background: #c5c5c5;
  border-radius: 50%;
  margin: 0 5px;
  padding: 5px;
  cursor: pointer;
}

.dot:focus {
  outline: none;
}

.dot.active {
  background: #000;
}

.arrow {
  width: 30px;
  height: 30px;
  position: absolute;
  top: 50%;
  transform: translateY(-50%);
  -webkit-transform: translateY(-50%);
  fill: #fff;
  cursor: pointer;
}

.arrow--left {
  left: 5px;
}

.arrow--right {
  left: auto;
  right: 5px;
}

.arrow--disabled {
  fill: rgba(255, 255, 255, 0.5);
}
gnerkus
  • 11,357
  • 6
  • 47
  • 71
  • 1
    It would help provide more context if you could share the code for the slider component. – gnerkus Jul 18 '23 at 08:19
  • Please provide enough code so others can better understand or reproduce the problem. – Community Jul 18 '23 at 13:48
  • @gnerkus I added the codes you asked for. – Ali Asadollahi Jul 18 '23 at 20:33
  • I've edited the question to add in the code you provided. – gnerkus Jul 19 '23 at 07:55
  • I've been unable to reproduce the issue as the Keen slider library loads immediately. Could you share how the images are being displayed; the CSS in the code provided doesn't seem to match the screenshot. – gnerkus Jul 19 '23 at 10:17
  • @gnerkus Yeah, I added it to codesandbox to share it but it needed a premium account for sharing code. I used another library for now but I need this problem to be resolved cause I need to work with this package in another project. I'm looking for a free alternative to codesandbox. I must say that this problem exist just on next.js@13 – Ali Asadollahi Jul 19 '23 at 11:33
  • 1
    @gnerkus here is my code in stackblitz codespace https://stackblitz.com/edit/stackblitz-starters-m3vrxi – Ali Asadollahi Jul 20 '23 at 21:36

1 Answers1

1

Edit:
The example has been edited to display the first slide as a placeholder image until the slider library has been successfully loaded. The edit introduces replaces the previous loading placeholder with the line:

<div className={`number-slide1 ${loaded ? 'slide-cover' : ''}`}>1</div>

If you only need to hide the images prior to the initialization of the Keen Slider library, you can use CSS:

// imports

export default () => {
...

  return (
    <>
      // custom loading component; removed once the slider library has been loaded
      <div className={`number-slide1 ${loaded ? 'slide-cover' : ''}`}>1</div>
      <div ref={sliderRef} className={`keen-slider ${loaded ? "" : "slide-hidden"}`}>
        <div className="keen-slider__slide number-slide1">1</div>
        <div className="keen-slider__slide number-slide2">2</div>
      </div>
    </>
  );
}

styles.css

.slide-cover {
    display: none;
}
.slide-hidden {
    visibility: hidden;
}
gnerkus
  • 11,357
  • 6
  • 47
  • 71