【问题标题】:javascript property change eventjavascript 属性更改事件
【发布时间】:2011-05-09 08:16:20
【问题描述】:

每次更新/更改属性时,我都需要触发一个事件,以使 dom 元素与模型上的属性值保持同步(我使用的是 john resig 的简单继承 http://ejohn.org/blog/simple-javascript-inheritance/)。这可能以跨浏览器的方式进行吗?在我看来,如果我可以包装 js 用来设置属性并使其触发事件的任何函数,它就可以工作,我只是不知道该怎么做。

【问题讨论】:

    标签: javascript jquery watch


    【解决方案1】:

    JavaScript 不使用函数来设置属性。它们只是变量,设置它们不需要任何复杂的包装器。

    可以使用一个函数来设置属性,不过,你可以在支持类中的私有数据的语言中使用相同的 getter/setter 安排.这样,您的函数可以轻松运行已注册为回调的其他函数。使用 jQuery,您甚至可以将它们作为事件处理。

    $(yourObject).bind('some-event-you-made-up', function() { 
        // This code will run whenever some-event-you-made-up is triggered on yourObject
    });
    
    // ... 
    
    $(yourObject).trigger('some-event-you-made-up');
    

    【讨论】:

    • 在 Mozilla 扩展的 Javascript 中,实际上可以为对象属性提供“getter”和“setter”函数。
    • 问题是我要监听事件的对象不是jquery对象,只是存储在jquery objects数据对象中的通用对象。我不知道如何将事件绑定到它。
    • 正如我展示的那样。 yourObject 可以是任何你想要的。它与 jQuery 无关。然后,您使用 jQuery 仅跟踪您可能绑定到 yourObject 的所有回调函数。
    • @GuilhermeFerreira 这个问题和答案来自七年前,早于Object.defineProperty。如果您觉得这个问题仍然会从中受益,我当然鼓励您为 2017 年写一个合适的答案。
    【解决方案2】:

    也许您已经使用 jQuery 绑定/触发器解决了您的问题,但我想告诉您,我正在构建一个更改跟踪和(最重要的是)实体建模 Javascript 框架,名为“帐篷”,它解决了您暴露的问题,不需要任何特殊的对象操作语法,其开源并托管在:

    https://github.com/benjamine/tent

    使用 JSDoc 记录并使用 js-test-driver 进行单元测试。

    您可以通过这种方式使用更改跟踪模块:

       var myobject = { name: 'john', age: 34 };
    
       // add a change handler that shows changes on alert dialogs
       tent.changes.bind(myobject, function(change) {
           alert('myobject property '+change.data.propertyName+' changed!');
       });
    
       myobject.name = 'charly'; // gets notified on an alert dialog
    

    它也适用于数组更改(添加、删除)。 此外,您可以使用“实体”上下文将所有检测到的更改(添加、删除、修改的项目)的变更集分组在集合上、级联添加和删除、保持反向属性同步、跟踪 1 对 1、1 对 N和 N 对 M 关系等。

    【讨论】:

      【解决方案3】:

      你可以试试Javascript Property Events (jpe.js)

      我遇到了类似的问题,并最终为 Object.defineProperty 编写了一个重载函数,该函数将事件处理程序添加到属性中。它还提供类型检查(js-base-types)并在内部存储其值,防止不必要的更改。

      普通defineProperty示例:

      Object.defineProperty(document, "property", {
          get:function(){return myProperty},
          set:function(value){myProperty = value},
      })
      var myProperty = false;
      

      带有 onchange 事件的属性示例:

      Object.defineProperty(document, "property", {
          default:false,
          get:function(){},
          set:function(value){},
          onchange:function(event){console.info(event)}
      })
      

      【讨论】:

      • 我很震惊地看到里面有一个“onchange”事件,但后来我才看到它是一个框架哈哈
      【解决方案4】:

      Object defineProperty/defineProperties 可以解决问题。 这是一个简单的代码。我已经基于它构建了一些数据绑定框架,它可能会变得非常复杂,但是要像这样练习它:

      var oScope = {
          $privateScope:{},
          notify:function(sPropertyPath){
              console.log(sPropertyPath,"changed");
          }
      };
      Object.defineProperties(oScope,{
          myPropertyA:{
              get:function(){
                  return oScope.$privateScope.myPropertyA
              },
              set:function(oValue){
                  oScope.$privateScope.myPropertyA = oValue;
                  oScope.notify("myPropertyA");
              }
          }
      });
      
      oScope.myPropertyA = "Some Value";
      //console will log: myPropertyA changed
      

      【讨论】:

        猜你喜欢
        • 2020-01-26
        • 1970-01-01
        • 1970-01-01
        • 2011-04-18
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2016-07-09
        相关资源
        最近更新 更多