【问题标题】:JQuery plugin not working when used multiple times in a page在页面中多次使用时,JQuery 插件不起作用
【发布时间】:2016-07-06 09:46:49
【问题描述】:

我正在尝试编写一个名为 grid2carousel 的 JQuery 插件,它在桌面设备上以 Bootstrap 样式的网格获取一些内容,并在较小的屏幕上变成一个轮播。

如果该插件是页面上的唯一实例,则该插件可以正常工作,但如果有多个,则会遇到一些问题。我在这里创建了一个 Codepen 来演示这个问题:

http://codepen.io/decodedcreative/pen/BzdBpb

尝试注释掉 codepen 的 HTML 部分中的一个组件,调整浏览器的大小直到它变成一个轮播,然后在取消注释的情况下再次重复此过程

每次浏览器宽度低于 HTML 中数据属性中指定的断点时,该插件通过运行一个名为 SetupPlugin 的内部函数来工作。如果浏览器宽度超过此断点,则名为 DestroyPlugin 的函数会将 HTML 恢复到其原始状态。像这样:

        checkDeviceState = function(){
            if($(window).width()>breakpointValue){
                destroyPlugin();
            }else{
                if(!$element.hasClass('loaded')){
                    setupPlugin();
                }
            }
        },

以下是我的完整插件代码。有人可以告诉我我在这里做错了什么吗?

(function (window, $){
$.grid2Carousel = function (node, options){
    var
    options = $.extend({slidesSelector: '.g2c-slides', buttonsSelector: '.g2c-controls .arrow'}, {},options),
    $element = $(node),
    elementHeight = 0,
    $slides = $element.find(options.slidesSelector).children(),
    $buttons = $element.find(options.buttonsSelector),
    noOfItems = $element.children().length + 1,
    breakpoint = $element.data("bp"),
    breakpointValue = 0;

    switch(breakpoint){
        case "sm":
            breakpointValue = 767;
            break;
        case "md":
            breakpointValue = 991;
            break;
        case "lg":
            breakpointValue = 1199;
            break;
    }

    setupPlugin = function(){

        // Add loaded CSS class to parent element which adds styles to turn grid layout into carousel layout
        $element.addClass("loaded");

        // Get the height of the tallest child element
        elementHeight = getTallestInCollection($slides)

        // As the carousel slides are stacked on top of each other with absolute positioning, the carousel doesn't have a height. Set its height using JS to the height of the tallest item;
        $element.height(elementHeight);

        // Add active class to the first slide
        $slides.first().addClass('active');


        $buttons.on("click", changeSlide);

    },

    destroyPlugin =  function(){
        $element.removeClass("loaded");
        $element.height("auto");
        $buttons.off("click");
        $slides.removeClass("active");
    },

    checkDeviceState = function(){
        if($(window).width()>breakpointValue){
            destroyPlugin();
        }else{
            if(!$element.hasClass('loaded')){
                setupPlugin();
            }
        }
    },

    changeSlide = function(){
        var $activeSlide = $slides.filter(".active"),
            $nextActive = null,
            prevSlideNo = $activeSlide.prev().index() + 1,
            nextSlideNo = $activeSlide.next().index() + 1;

        if($(this).hasClass('left')){


            if(prevSlideNo !== 0){
                $nextActive = $activeSlide.prev();
                $nextActive.addClass('active');
                $slides.filter(".active").not($nextActive).removeClass("active");
            }else{
                $nextActive = $slides.last();
                $nextActive.addClass('active');
                $slides.filter(".active").not($nextActive).removeClass("active");
            }

        }else if($(this).hasClass('right')){


            if(nextSlideNo !== 0){
                $nextActive = $activeSlide.next();
                $nextActive.addClass('active');
                $slides.filter(".active").not($nextActive).removeClass("active");
            }else{
                $nextActive = $slides.first();
                $nextActive.addClass('active');
                $slides.filter(".active").not($nextActive).removeClass("active");
            }

        }
    },

    getTallestInCollection = function(collection){

        $(collection).each(function(){
            if($(this).outerHeight() > elementHeight){
                elementHeight = $(this).outerHeight();
            }
        });

        return elementHeight;

    };

    setupPlugin();
    checkDeviceState();
    $(window).on("resize", checkDeviceState);

}




$.fn.grid2Carousel = function (options) {
    this.each( function (index, node) {
        $.grid2Carousel(node, options)
    });

    return this
}
})(window, jQuery);

非常感谢,

詹姆斯

【问题讨论】:

    标签: javascript jquery jquery-plugins multiple-instances


    【解决方案1】:

    请检查您插件代码中的第 30 行,看起来您只是忘记添加 var 关键字,因此您没有创建局部变量来存储函数 setupPlugin、destoryPlugin 等创建全局变量,然后插件的每个新初始化都重写此函数以指向新创建的滑块。

    setupPlugin = function(){
    

    应该是

    var setupPlugin = function(){
    

    更新代码here

    【讨论】:

    • *facepalm。非常感谢!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-05-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-05-11
    • 1970-01-01
    • 2018-12-03
    相关资源
    最近更新 更多