【问题标题】:react-slick carousel cycle through slides with scroll-event - react js, javascriptreact-slick carousel 通过滚动事件循环幻灯片 - 反应 js,javascript
【发布时间】:2018-05-18 09:52:29
【问题描述】:

这是我正在使用的轮播:react-slick

我希望能够使用鼠标向上或向下滚动事件滚动浏览每张幻灯片。

向上滚动以增加,向下滚动以减少。

在网上找到了我所需要的示例 - 只是不确定如何将其转换为反应解决方案。

示例:https://codepen.io/Grawl/pen/mMLQQb

在基于“react”组件的方法中实现这一目标的最佳方法是什么?

这是我的反应组件:

import React from 'react';
import PropTypes from 'prop-types';
import styles from './styles.css';
import ReactSVG from 'react-svg';
import Slider from 'react-slick';


import MobileSVG from '../../../assets/svg/icons/Mobile_Icon_Option2.svg';
import TabletSVG from '../../../assets/svg/icons/Tablet_Icon_Option2.svg';
import DesktopSVG from '../../../assets/svg/icons/Desktop_Icon_Option2.svg';

const deviceIcons = {'mobile': MobileSVG, 'tablet': TabletSVG, 'desktop': DesktopSVG};

import BackToTopButton from '../BackToTopButton';

export default class ProductComponent extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
        };

    }

    render() {
        const {productData} = this.props

        //Slider settings
        const settings = {
            dots: true,
            infinite: false,
            speed: 500,
            fade: true,
            arrows: false,
            centerMode: true,
            slidesToShow: 1,
            slidesToScroll: 1
        }

        //Slider items
        const sliderItems = productData.map((obj, i) => {
            return (
                <div className="product-component row" key={i}>
                    <div className="product-component-image-wrap col-xs-12 col-sm-8">
                        <span className="product-heading">{obj.category}</span>
                        <div className="product-detail-wrap">
                            <img className="product-component-image" src={`${process.env.DB_URL}${obj.image}`} />
                            <ul className="list-device-support">
                                {obj.categoryDeviceSupport.map((obj, i) => {
                                    return (<li key={i}>
                                        <span className="svg-icon">
                                            <ReactSVG path={deviceIcons[obj.value]} />
                                        </span>
                                        <span className="product-label">{obj.label}</span>
                                    </li>)
                                })}
                            </ul>
                        </div>
                    </div>
                    <div className="product-component-info col-xs-12 col-sm-3"> 
                        <span className="align-bottom">{obj.title}</span>
                        <p className="align-bottom">{obj.categoryBrief}</p>
                    </div>
                </div>
            )
        });
        return (
            <div className="product-component-wrap col-xs-12">
                <Slider {...settings}>
                    {sliderItems}
                </Slider>
                <BackToTopButton scrollStepInPx="50" delayInMs="7" />
            </div>
        )
    }
}

ProductComponent.propTypes = {
    productData: PropTypes.array
};

ProductComponent.defaultProps = {
    productData: []
};

【问题讨论】:

    标签: javascript reactjs react-slick


    【解决方案1】:

    你想做这样的事情:

    constructor(props){
        super(props);
        this.slide = this.slide.bind(this);
    }
    slide(y){
        y > 0 ? (
           this.slider.slickNext()
        ) : (
           this.slider.slickPrev()
        )
    }
    componentWillMount(){
        window.addEventListener('wheel', (e) => {
            this.slide(e.wheelDelta);
        })
    }
    render(){...
    

    并为您的滑块添加参考:

    <Slider ref={slider => this.slider = slider }>
    

    所以当滚轮事件的y值大于0即向上滚动显示下一张幻灯片时,向下滚动显示上一张。

    【讨论】:

    • 首先,感谢您的回复。尝试滚动时遇到一个有趣的错误:无法在“窗口”上执行“滚动”:参数 1(“选项”)不是对象。是否可能是因为使用了 eventListener "wheel"?
    • 这可能是上下文问题,将scroll 函数的名称更改为slide 或其他内容并将事件侦听器回调更改为粗箭头
    • 我不知道你把事件监听回调改成粗箭头是什么意思?
    • 对不起,粗箭头是 es6 语法的东西。它只是定义函数的另一种方式,而不是你说的function(e){} (e) =&gt; {}。我在编辑中添加了它
    • window.addEventListener('wheel', (e) =&gt; { this.scroll(e.wheelDelta);})
    【解决方案2】:

    以下内容应该适合您:

    componentDidMount(){
      let slickListDiv = document.getElementsByClassName('slick-list')[0]
      slickListDiv.addEventListener('wheel', event => {
        event.preventDefault()
        event.deltaY > 0 ? this.slider.slickNext() : this.slider.slickPrev()
      })
    }
    

    你应该像这样初始化组件:

    <Slider {...settings} ref={slider => this.slider = slider.innerSlider}>
    ...
    </Slider>
    

    【讨论】:

    • ref={slider =&gt; this.slider = slider.innerSlider} 与我的 Cannot read property 'innerSlider' of null 崩溃
    • ref={slider => this.slider = slider && slider['innerSlider']}
    【解决方案3】:

    我在我的 CustomSlider 组件中使用以下代码:

      constructor(props) {
        super(props);
        this.handleWheel = this.handleWheel.bind(this);
      }
    
      componentDidMount() {
        ReactDOM.findDOMNode(this).addEventListener('wheel', this.handleWheel);
      }
    
      componentWillUnmount() {
        ReactDOM.findDOMNode(this).removeEventListener('wheel', this.handleWheel);
      }
    
      handleWheel(e) {
        e.preventDefault();
        e.deltaY > 0 ? this.slider.slickNext() : this.slider.slickPrev();
      }
    

    组件初始化

     <Slider ref={slider => this.slider = slider}>
       ...
     </Slider>
    

    【讨论】:

      【解决方案4】:

      带挂钩

      const sliderRef = createRef();
      const scroll = useCallback(
          y => {
            if (y > 0) {
              return sliderRef?.current?.slickNext(); /// ? <- using description below 
            } else {
              return sliderRef?.current?.slickPrev();
            }
          },
          [sliderRef]
        );
       useEffect(() => {
          window.addEventListener("wheel", e => {
            scroll(e.deltaY);
          });
        }, [scroll]);
      

      我使用了与 babel 插件连接的 typescript 的可选链接,但你可以使用如下验证:

       sliderRef.current && sliderRef.current.slickNext() 

      【讨论】:

        【解决方案5】:

        我能够在引用 Slider 组件(react-slick JS 库)的函数组件中滚动工作,使用钩子(useRef 获取对 Slider 组件的引用和 useEffect 来添加和删除侦听器(滚动函数) ) 到车轮事件)。

        const myComponent () => {
        
         const settings = {
            dots: true,
            slidesToShow: 1,
            slidesToScroll: 1,};
        
        const slider = useRef(null);
        
        function scroll(e){
            if (slider === null)
                return 0;
        
            e.wheelDelta > 0 ? (
                slider.current.slickNext()
            ) : (
                slider.current.slickPrev()
            );
        
        };
        
        useEffect(() => {
            window.addEventListener("wheel", scroll,true);
        
            return () => {
                window.removeEventListener("wheel", scroll, true);
            };
        }, []);
        
        return (
         <Slider {...settings} ref={slider}>
         </Slider>
        );
        }
        
        export default myComponent;
        

        【讨论】:

          猜你喜欢
          • 2017-05-22
          • 1970-01-01
          • 2021-12-17
          • 1970-01-01
          • 2018-02-12
          • 1970-01-01
          • 1970-01-01
          • 2012-09-19
          • 1970-01-01
          相关资源
          最近更新 更多