变异观察者能否听取数据中的变化 - "属性

时间:2017-01-08 22:41:54

标签: javascript jquery dom mutation-observers

所以问题是我有一个html元素,在"数据中有一个对象 - "属性(通过jQuery ofc设置),我想听取该属性的变化。

我已经尝试了很多东西,例如在MutationObserverInit object中设置几乎所有可能的组合值,但这些都没有帮助。

有人知道是否有可能吗?



$('#some-id').click( function() {
  //$('#some-id').attr('title', 'some-title'); //this works
  $('#some-id').data('foo', 'bar1'); //this don't
});

var functionCallBack = function(mutations) {
  alert('something changed')
}

// select the target node
var target = document.getElementById("some-id");

// create an observer instance
var observer = new MutationObserver(functionCallBack);

// configuration of the observer:
var config = { subtree: true, childList: true , attributes: true};

// pass in the target node, as well as the observer options
observer.observe(target, config);

$('#some-id').data('foo', 'bar');

<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="some-id">HEY</div>
&#13;
&#13;
&#13;

2 个答案:

答案 0 :(得分:2)

新答案(基于Oriol's Answer):

我认为Oriol提供了更好的方法,但可以进一步优化。

var object = {
  'key': 'value'
};

$('.addObj').click(function() {
  $('#some-id').observeData('foo', object, function() {
    console.log("Object Added");
  });
});

$('.removeObj').click(function() {
  $('#some-id').observeData('foo', null, function() {
    console.log("Object removed");
  });
});


jQuery.fn.observeData = function(name, object, callback) {
  // Get elemenet
  var element = $(this[0]);

  // Add data
  element.data(name, object);

  // Call the callback function
  callback();

  // Return this for a chainable function
  return this;
};
span {
  padding: 10px;
  float: left;
  margin: 5px;
  cursor: pointer;
  background-color: green;
  border: 1px solid black;
  border-radius: 5px;
  transition: all 0.5s;
  color: white;
  font-size: 13px;
}
span:hover {
  opacity: 0.8;
}
#some-id {
  text-align: center;
  width: 100%;
  margin: 10px 0;
  font-size: 20px;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="some-id">HEY</div>

<span class='addObj'>Add Object</span>
<span class='removeObj'>Remove Object</span>

JSFiddle:https://jsfiddle.net/t012rb9j/1/

旧答案:

正如您在代码中所述:

$('#some-id').click(function() {

 // $('#some-id').attr('title', 'some-title'); //this works
 $('#some-id').data('foo', 'bar1'); //this don't
});

.attr()在.data()不起作用时有效。原因是.attr()将属性值添加到HTML标记中,而数据将此数据存储在内存中。

来自jQuery文档:

  

.data() :存储与指定元素关联的任意数据和/或返回已设置的值。

     

.attr() :获取匹配元素集中第一个元素的属性值,或者为每个元素设置一个或多个属性   匹配元素。

检测数据更改的一种方法(如果要存储对象)是将两个函数组合在一起。

var object = {
  'key': 'value'
};

$('.addObj').click(function() {
  $('#some-id').data('foo', object).attr("data-attached", "true");
});

$('.removeObj').click(function() {
  $('#some-id').data('foo', null).attr("data-attached", "false");
});


var functionCallBack = function(mutations) {
  mutations.forEach(function(mutation) {
    if (jQuery(mutation.target).attr("data-attached") == "true") {
      // Your code here
      console.log("Object Added");
    } else {
      console.log("Object removed");
    }
  });
}

// select the target node
var target = document.getElementById("some-id");

// create an observer instance
var observer = new MutationObserver(functionCallBack);

// configuration of the observer:
var config = {
  subtree: true,
  childList: true,
  attributes: true
};

// pass in the target node, as well as the observer options
observer.observe(target, config);
.addObj, .removeObj {
  padding: 10px;
  float: left;
  margin: 5px;
  cursor: pointer;
  background-color: green;
  border: 1px solid black;
  border-radius: 5px;
  transition: all 0.5s;
  color: white;
  font-size: 13px;
}

.addObj:hover, .removeObj:hover {
  opacity: 0.8;
}

#some-id {
  text-align: center;
  width: 100%;
  margin: 10px 0;
  font-size: 20px;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="some-id">HEY</div>

<span class='addObj'>Add Object</span>
<span class='removeObj'>Remove Object</span>

JSFiddle:https://jsfiddle.net/9xkb6jv4/

答案 1 :(得分:1)

如果您想使用jQuery&#39; data检测新数据集,您可以随时劫持它。

&#13;
&#13;
var functionCallBack;
var $data = jQuery.fn.data;
jQuery.fn.data = function(key, value) {
  var ret = $data.apply(this, arguments);
  if(functionCallBack && this[0] && value !== undefined) {
    functionCallBack(this, key, value);
  }
  return ret;
};

$('#some-id').click( function() {
  $(this).data('foo', 'bar1');
}).data('foo', 'bar');
functionCallBack = function(elements, key, value) {
  console.log('something changed')
};
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="some-id">HEY</div>
&#13;
&#13;
&#13;