丢失对jQuery存储的select元素的引用

时间:2015-03-03 15:55:07

标签: javascript jquery

我在某种程度上失去了对页面上的select元素的引用。我正在使用遗留代码,而我正试图重建其中的一部分。除了我在这里发布的代码之外,还有其他代码可以更改我正在尝试使用的select元素的值。

我为页面上的每个visualizer div元素创建一个新对象。我选择了类master_select的所有select元素,并将它们存储在masterSelects中,如下所示:

masterSelects = wrapper.find( ".master_select" );

然后,只要页面上的任何选择框发生变化,我就会调用updatePreview,它应该能够对masterSelects进行更改。

首次加载页面时,手动触发updatePreview,然后调用:

masterSelects.css('background-color', 'blue')

可以正常工作并更改这些选择框的bg颜色。但是,如果我更改了一个select选项并且事件调用了updatePreview,请使用:

masterSelects.css('background-color', 'orange');

无法更新bg颜色。我将masterSelects对象打印到控制台日志,它仍然包含我期望的信息。它就像我想要在页面上更改的元素不再是我保存引用的元素。但是,尝试重新选择它也不起作用。 尽管控制台日志打印出预期的信息,其他遗留代码是否会以某种方式破坏我对这些元素的引用?我很抱歉我还没有发布该代码,它是'因为我没有写过1000条线并且是一团糟,我将开始除草它,但我想知道在开始之前这是否可能。

var Visualizer = (function() {
    /*********************************
     * Internal Variables
     *********************************/
    var wrapper,
        selects,
        masterSelects;

    /*********************************
     * Constructor
     *********************************/
    function Visualizer( newElement ) {
        wrapper = $(newElement);
        selects = wrapper.find( "select" );
        masterSelects = wrapper.find( ".master_select" );
    };

    /*********************************
     * Internal Methods
     *********************************/
    var updatePreview = function( isManual ) {
        // Default isManual to false if it is not already true
        if (isManual != true) isManual = false;

        if(isManual) {
            masterSelects.css('background-color', 'blue');
            console.log(masterSelects);
        }

        if(!isManual) {
            // Even tried reselecting the masterSelects, but it didn't work
            // masterSelects = wrapper.find( ".master_select" );
            masterSelects.css('background-color', 'orange');
            console.log(masterSelects);
        }
    };

    // Bind on change events to the select boxes inside the wrapper div
    var bindEvents = function() {
        selects.change( updatePreview );
    };

    /*********************************
     * Public Methods
     *********************************/
    // Initialize the Visualizer object
    Visualizer.prototype.init = function() {
        bindEvents();
        updatePreview( true );
    };

    // Return the Visualizer object
    return Visualizer;
})();

/*********************************
 * Usage
 *********************************/
$( document ).ready( function() {
    $( "div.visualizer-wrapper" ).each( function( key, value ) {
        var vis = new Visualizer( value );
        vis.init();
    });
});

哦,这段代码在另一个与其他遗留代码略有不同的类似页面上工作。

2 个答案:

答案 0 :(得分:1)

感谢Bergi的帮助。这就是我解释你的建议的方式,我会把它作为其他任何人的答案发布。如果我在这里做错了,请告诉我。

/*********************************
 * Constructor
 *********************************/
function Visualizer( newElement ) {
    /*********************************
     * Internal Variables
     *********************************/
    var wrapper,
        selects,
        masterSelects;

    wrapper = $(newElement);
    selects = wrapper.find( "select" );
    masterSelects = wrapper.find( ".master_select" );

    /*********************************
     * Internal Methods
     *********************************/
    this.updatePreview = function( isManual ) {
        // Default isManual to false if it is not already true
        if (isManual != true) isManual = false;

        if(isManual) {
            masterSelects.css('background-color', 'blue');
            console.log(masterSelects);
        }

        if(!isManual) {
            masterSelects = wrapper.find( ".master_select" );
            masterSelects.css('background', 'transparent');
            masterSelects.css('background-color', 'orange');
            //$(".master_select").css('background-color', 'orange');
            console.log(masterSelects);
        }
    };

    // Bind on change events to the select boxes inside the wrapper div
    this.bindEvents = function() {
        selects.change( this.updatePreview.bind(this) );
    };
}

/*********************************
 * Public Methods
 *********************************/
// Initialize the Visualizer object
Visualizer.prototype.init = function() {
    this.bindEvents();
    this.updatePreview( true );
}

/*********************************
 * Usage
 *********************************/
$( document ).ready( function() {
    $( "div.visualizer-wrapper" ).each( function( key, value ) {
        var vis = new Visualizer( value );
        vis.init();
    });
});

答案 1 :(得分:0)

这可以很好地表达为jQuery pugin。

(function($){
    // **********************************
    // ***** Start: Private Members *****
    var pluginName = 'visualizer';
    // ***** Fin: Private Members *****
    // ********************************

    // *********************************
    // ***** Start: Public Methods *****
    var methods = {
        init : function(options) {
            //"this" is a jquery object on which this plugin has been invoked.
            return this.each(function(index) {
                var $this = $(this);
                var data = $this.data(pluginName);
                // If the plugin hasn't been initialized yet
                if (!data) {
                    var settings = {
                        init_bgColor: 'blue',
                        alt_bgColor: 'orange'
                    };
                    if(options) { $.extend(true, settings, options); }
                    var masterSelects = $this.find( ".master_select" );
                    $this.find( "select" ).on('change', function(event) {
                        if(event.originalEvent) {
                            masterSelects.css('background-color', settings.init_bgColor);
                        } else {
                            masterSelects.css('background-color', settings.alt_bgColor);
                        }
                    });
                    $this.data(pluginName, {
                        target : $this,
                        settings: settings,
                        masterSelects: masterSelects
                    });
                }
            });
        },
    };
    // ***** Fin: Public Methods *****
    // *******************************

    // *****************************
    // ***** Start: Supervisor *****
    $.fn[pluginName] = function( method ) {
        if ( methods[method] ) {
            return methods[method].apply( this, Array.prototype.slice.call( arguments, 1 ));
        } else if ( typeof method === 'object' || !method ) {
            return methods.init.apply( this, arguments );
        } else {
            $.error( 'Method ' + method + ' does not exist in jQuery.' + pluginName );
        }
    };
    // ***** Fin: Supervisor *****
    // ***************************
})( jQuery );

这是更加冗长的,这是绝对必要的,但如果需要额外的插件方法,我已经留下了所有的钩子。

用法:

$( document ).ready( function() {
    $( "div.visualizer-wrapper" ).visualizer();
});

或者,覆盖默认颜色方案:

$( document ).ready( function() {
    $( "div.visualizer-wrapper" ).visualizer({
        init_bgColor: 'green',
        alt_bgColor: 'red'
    });
});