是否有可能在JS中有一个事件,当某个变量的值发生变化时触发?JQuery被接受。
当前回答
对于那些几年后收听的人来说:
大多数浏览器(和IE6+)都有一个解决方案,它使用onpropertychange事件和更新的规范defineProperty。有一点需要注意的是,您需要将变量设置为dom对象。
详情:
http://johndyer.name/native-browser-get-set-properties-in-javascript/
其他回答
如果你正在使用jQuery {UI}(每个人都应该使用:-)),你可以使用.change()和一个隐藏的<input/>元素。
基于akira的回答,我补充说,你可以通过listerner操纵dom。
https://jsfiddle.net/2zcr0Lnh/2/
javascript:
x = {
aInternal: 10,
aListener: function(val) {},
set a(val) {
this.aInternal = val;
this.aListener(val);
},
get a() {
return this.aInternal;
},
registerListener: function(listener) {
this.aListener = listener;
}
}
x.registerListener(function(val) {
document.getElementById('showNumber').innerHTML = val;
});
x.a = 50;
function onClick(){
x.a = x.a + 1;
}
html:
<div id="showNumber">
</div>
<button onclick="onClick()">
click me to rerender
</button>
当变量x.a发生变化时,registerListener方法将被触发。
Utils = {
eventRegister_globalVariable : function(variableName,handlers){
eventRegister_JsonVariable(this,variableName,handlers);
},
eventRegister_jsonVariable : function(jsonObj,variableName,handlers){
if(jsonObj.eventRegisteredVariable === undefined) {
jsonObj.eventRegisteredVariable={};//this Object is used for trigger event in javascript variable value changes ku
}
Object.defineProperty(jsonObj, variableName , {
get: function() {
return jsonObj.eventRegisteredVariable[variableName] },
set: function(value) {
jsonObj.eventRegisteredVariable[variableName] = value; handlers(jsonObj.eventRegisteredVariable[variableName]);}
});
}
最近我发现自己也有同样的问题。想要监听变量的变化并在变量变化时做一些事情。
有人提出了一个使用setter设置值的简单解决方案。
声明一个简单的对象来保存变量的值:
var variableObject = {
value: false,
set: function (value) {
this.value = value;
this.getOnChange();
}
}
对象包含一个set方法,通过该方法可以更改值。但是它也调用了一个getOnChange()方法。将定义它。
variableObject.getOnChange = function() {
if(this.value) {
// do some stuff
}
}
现在,每当我做variableObject.set(true)时,getOnChange方法就会触发,如果值被设置为所需的值(在我的例子中:true), if块也会执行。
这是我发现的最简单的方法。
在getter和setter的帮助下,您可以定义一个JavaScript类来做这样的事情。
首先,我们定义一个名为MonitoredVariable的类:
class MonitoredVariable {
constructor(initialValue) {
this._innerValue = initialValue;
this.beforeSet = (newValue, oldValue) => {};
this.beforeChange = (newValue, oldValue) => {};
this.afterChange = (newValue, oldValue) => {};
this.afterSet = (newValue, oldValue) => {};
}
set val(newValue) {
const oldValue = this._innerValue;
// newValue, oldValue may be the same
this.beforeSet(newValue, oldValue);
if (oldValue !== newValue) {
this.beforeChange(newValue, oldValue);
this._innerValue = newValue;
this.afterChange(newValue, oldValue);
}
// newValue, oldValue may be the same
this.afterSet(newValue, oldValue);
}
get val() {
return this._innerValue;
}
}
假设我们想监听钱的变化,让我们创建一个初始值为0的MonitoredVariable实例:
const money = new MonitoredVariable(0);
然后我们可以使用money来获取或设置它的值。
console.log(money.val); // Get its value
money.val = 2; // Set its value
因为我们没有为它定义任何监听器,所以在钱之后没有什么特别的事情发生。Val变成了2。
现在让我们定义一些侦听器。我们有四个可用的侦听器:beforeSet、beforeChange、afterChange、afterSet。 当你使用金钱时,下面的事情会依次发生。val = newValue更改变量的值:
钱。beforeSet (newValue oldValue); 钱。beforeChange (newValue oldValue);(如果它的值没有改变,将被跳过) 钱。val = newValue; 钱。afterChange (newValue oldValue);(如果它的值没有改变,将被跳过) 钱。afterSet (newValue oldValue);
现在我们定义了afterChange监听器,它只会在金钱之后被触发。val已经改变(而afterSet将被触发,即使新值与旧值相同):
money.afterChange = (newValue, oldValue) => {
console.log(`Money has been changed from ${oldValue} to ${newValue}`);
};
现在设置一个新的值3,看看会发生什么:
money.val = 3;
您将在控制台中看到以下内容:
Money has been changed from 2 to 3
完整代码请参见https://gist.github.com/yusanshi/65745acd23c8587236c50e54f25731ab。