如何在jquery ui小部件工厂小部件中声明静态/类变量

时间:2011-03-30 09:51:10

标签: jquery jquery-plugins

关于jquery ui小部件工厂......

在所有实例之间共享静态变量/类级变量的最佳方法是什么?

e.g。

$.widget("ui.staticTest", {
    staticVar:'unchanged',
    test: function(a){
        if(a){
            this.staticVar= a;
        }
        alert(JSON.stringify(this.staticVar));
    }
});

$('#test').staticTest();
$('#parent').staticTest();

$('#test').staticTest('test','changed');
$('#parent').staticTest('test');

在上面,如果staticVar是静态的,$('#parent')。staticTest('test');会警告“已更改”,但会警告“未更改”。

(如果你想玩一个游戏,这段代码就在jsfiddle上:http://jsfiddle.net/alzclarke/Sx8pJ/

我能想到的解决方案很难看:

1)$('body')。data('sharedVariable',myData) - 这似乎不是一个好习惯,如果有人或某事清除数据主体会怎样 2)将其存储在原型命名空间中,例如= $ .ui.staticTest.prototype.staticVar = myData; 这也敲响了警钟

7 个答案:

答案 0 :(得分:25)

闭包是你的答案

(function($) {

var staticVariable = '';

$.widget('ui.newWidget', {
    options: {

    },
    _init: function() {
    }

});

})(jQuery);

staticVariable只能在你刚刚定义的小部件的范围内使用,因为它被包含在一个立即被调用的匿名函数中(就像你应该已经为你的jquery / jquery ui插件做的那样。

答案 1 :(得分:2)

似乎小部件没有共享范围。任何。所以我要做的就是在jQuery UI对象本身上定义一个共享对象,就像你自己提出的那样。

注意:共享对象名称应反映窗口小部件名称和命名空间。

$.ui.staticShared = { color: "#fff" };

$.widget("ui.static", {
    color: function (o)
    {
        if (typeof o !== "undefined") $.ui.staticShared.color = o;

        return $.ui.staticShared.color;
    }
});

这就像它在我眼中一样干净。当然;存在着人们压倒共享对象的风险,但如果发生这种情况,世界就不会崩溃。

如果您想要某种故障安全/反馈,如果共享对象无效或已被覆盖,您可以检查_init事件上的对象结构。

$.widget("ui.static", {
    _init: function ()
    {
        if (typeof $.ui.staticShared === "undefined")
        {
            alert("$.ui.staticShared is required for this plug-in to run");
        }
    },
});

每当创建实例时都会触发_init事件。

答案 2 :(得分:1)

实际上如果你的变量是一个对象,它会自动静态... HMMMMMMMM非常有帮助! (不)...特别是考虑到包含基元的变量表现出相反的行为。必须与旧的“指针不是对象”成语有关。

... ANYWHO

如果你的变量包含一个物体{}以下将是正确的答案,否则,请看其他答案:

静态示例:

$.widget("ui.staticTest", {
    staticVar:{val:'unchanged'},
    _create: function(){
    },
    test: function(a){
        if(a){
            this.staticVar.val= a;
        }
        alert(JSON.stringify(this.staticVar.val));
    }
});


$('#test').staticTest();
$('#parent').staticTest();

$('#test').staticTest('test','changed');
$('#parent').staticTest('test');

http://jsfiddle.net/alzclarke/Sx8pJ/9/

非静态示例:

$.widget("ui.staticTest", {
    _create: function(){
      this.staticVar={val:'unchanged'};
    },
    test: function(a){
        if(a){
            this.staticVar.val= a;
        }
        alert(JSON.stringify(this.staticVar.val));
    }
});


$('#test').staticTest();
$('#parent').staticTest();

$('#test').staticTest('test','changed');
$('#parent').staticTest('test');

http://jsfiddle.net/alzclarke/Sx8pJ/10/

答案 3 :(得分:0)

似乎对“this”关键字有点误解。此关键字将该变量设置为特定于实例。请尝试以下代码。

$.widget("ui.staticTest", {
    staticVar:'unchanged',
    test: function(a){
        if(a){
            staticVar= a;
        }
        alert(JSON.stringify(staticVar));
    }
});

$('#test').staticTest();
$('#parent').staticTest();

$('#test').staticTest('test','changed');
$('#parent').staticTest('test');

答案 4 :(得分:0)

//解释小部件范围中的静态,实例和全局变量的详细示例

$.widget("ui.staticTest", {
    //staticVar is an instance variable, regardless of what it is named as
    staticVar: 'brownMamba',

    _create: function() {

    },

    //test the static variable
    testStatic: function(a) {
        if (a) {
        //Here you're actually creating a new static variable called 
        //staticVar which is associated with the staticTest object as you assign 
        //value to it. 
            //Lemme show you what I mean with an example
            //Here it alerts 'Undefined' as 'staticVar' does not exists
            //don't confuse it with the staticVar: 'brownMamba' declared above, 
            //that one is an instance variable
            alert("Type of $.ui.staticTest.staticVar before assignment: " + typeof $.ui.staticTest.staticVar);

            $.ui.staticTest.staticVar = a; 
            //At this point it alerts the type of 'a', which in our case is  'string'            
            alert("Type of $.ui.staticTest.staticVar after assignment: " + typeof $.ui.staticTest.staticVar);

            //value of instance variable at this point
            alert("typeof this.staticVar: " + typeof this.staticVar);
            alert("Value of this.staticVar: " +  this.staticVar);
            //value of global variable at this point
            //'Undefined' as it does not exist
            alert("Type of staticVar: " + typeof staticVar); //or window.staticVar


        } else {
            alert("value of staticVar in testStatic with no argument: " + $.ui.staticTest.staticVar);
        }
    },

    //test the instance variable
    testInstance: function(a) {
        if (a) {
        //Here you're actually working with the instance variable declared above, 
        //with the value 'brownMamba' 
        //Lemme show you what I mean with an example
        //Here it alerts 'string' as 'staticVar' exists and is assigned a string
            alert("typeof this.staticVar is " + typeof this.staticVar + " and its 
value is " + this.staticVar);

            this.staticVar = a; 
            alert("typeof this.staticVar after assignment is " + typeof this.staticVar);
            alert("Value of this.staticVar after assignment is " + this.staticVar);
        } else {
            alert("value of this.staticVar in testInstance with no argument: " + this.staticVar);
        }
    },

    //test the Global variable
    testGlobal: function(a) {
        if (a) {
        /*Here you're actually creating a global variable called staticVar*/ 
            //Lemme show you what I mean with an example
            //Here it alerts 'Undefined' as 'staticVar' does not exists
            alert("Type of staticVar before assignment: " + typeof staticVar);

            staticVar = a; //creating a global variable, which will be declared 
in window scope, i.e. window.staticVar 
            //At this point it alerts the type of a, which in our case is a 'string'            
            alert("Type staticVar after assignment: " + typeof staticVar);
            alert("Value of staticVar after assignment: " + staticVar)
        } else {
            alert("value of staticVar in testGlobal with no argument: " + staticVar);
        }
    }
});

//instantiating widget
$('#test').staticTest();
//instantiating widget
$('#parent').staticTest();

$('#test').staticTest('testStatic', 'changed');
//value will be sustained as its associated to the object
$('#parent').staticTest('testStatic');

$('#test').staticTest('testInstance', 'bluemamba');
//here the value doesn't change as its an instance variable and its value is not altered
$('#parent').staticTest('testInstance');

$('#test').staticTest('testGlobal', 'bluemamba');
//here the value is still sustained as the global is created in the previous call
$('#parent').staticTest('testGlobal');

http://jsfiddle.net/hiteshubharani/z5k4E/6/

答案 5 :(得分:0)

简单实施公鸡的解决方案:

$.widget("ui.staticTest", {
test: function(a){
    if(a){
        $.ui.staticTest.staticVar= a;
    }
    alert(JSON.stringify($.ui.staticTest.staticVar));
}
});
$.ui.staticTest.staticVar =  'unchanged';


$('#test').staticTest();
$('#parent').staticTest();
$('#test').staticTest('test');
$('#test').staticTest('test','changed');
$('#parent').staticTest('test');

答案 6 :(得分:0)

您可以使用常规JS封装模式:

$.widget("ui.staticTest", (function() {

    staticVar:'unchanged';

    return {
        test: function(a){
            if(a){
                staticVar= a;
            }
            alert(JSON.stringify(staticVar));
        }
    };
} ()));

你的jsFiddle的分叉:http://jsfiddle.net/pettys/RwKdZ/

Pro:没有任何神奇的事情发生,根本没有搞乱jQuery空间。 Con:将您的小部件缩进到另一个级别。