web-dev-qa-db-ja.com

jQueryイベント:divのhtml/textへの変更を検出

ajax requestsjquery functionsblurなど、内容が常に変わるdivがあります.

任意の時点で私のdivの変更を検出できる方法はありますか?

チェックされた間隔やデフォルト値は使用したくありません。

このような何かがするだろう

$('mydiv').contentchanged() {
 alert('changed')
}
238
BoqBoq

タイマーを使用したくなく、innerHTMLをチェックしたくない場合は、このイベントを試すことができます。

$('mydiv').bind("DOMSubtreeModified",function(){
  alert('changed');
});

より多くの詳細とブラウザサポートデータは ここ です。

重要:新しいjQueryバージョンのbind()では は推奨されないため、代わりにon()を使用してください。

$("body").on('DOMSubtreeModified', "mydiv", function() {
    alert('changed');
});
356
iman

あなたはこれを試すことができます

$('.myDiv').bind('DOMNodeInserted DOMNodeRemoved', function() {

});

しかし、これはInternet Explorerでは動作しないかもしれません、それをテストしていません

39
user1790464

$("#selector").bind()は廃止予定であるため 、次のようにしてください。

$("body").on('DOMSubtreeModified', "#selector", function() {
    // code here
});
37
Artley

MutationObserver または 突然変異イベント を探しています。どこでもサポートされているわけでもなければ、開発者の世界からあまりにも懐かしく見られているわけでもありません。

Divのサイズが変わることを知っている(そしてそれを確認できる)なら、 crossbrowser resizeイベント を使うことができるかもしれません。

30
rodneyrehm

Javascriptを使用する MutationObserver

  //More Details https://developer.mozilla.org/en-US/docs/Web/API/MutationObserver
 // select the target node
var target = document.querySelector('mydiv')
// create an observer instance
var observer = new MutationObserver(function(mutations) {
  console.log($('mydiv').text());   
});
// configuration of the observer:
var config = { attributes: true, childList: true, characterData: true };
// pass in the target node, as well as the observer options
observer.observe(target, config);
29
PPB

以下のコードは私のために働きます。

$("body").on('DOMSubtreeModified', "mydiv", function() {
    alert('changed');
});

それが誰かに役立つことを願っています:)

18
Sanchit Gupta

この問題に対する作り付けの解決策はありません、これはあなたのデザインとコーディングパターンに関する問題です。

発行者/購読者パターンを使用できます。これには、jQueryカスタムイベントまたは独自のイベントメカニズムを使用できます。

最初、

function changeHtml(selector, html) {
    var elem = $(selector);
    jQuery.event.trigger('htmlchanging', { elements: elem, content: { current: elem.html(), pending: html} });
    elem.html(html);
    jQuery.event.trigger('htmlchanged', { elements: elem, content: html });
}

以下のようにdivhtmlchanging/divhtmlchangedイベントを購読できます。

$(document).bind('htmlchanging', function (e, data) {
    //your before changing html, logic goes here
});

$(document).bind('htmlchanged', function (e, data) {
    //your after changed html, logic goes here
});

さて、あなたはこのchangeHtml()関数を通してあなたのdivの内容の変更を変えなければなりません。そのため、情報を含むコールバックデータ引数をバインドするため、必要に応じて監視または必要な変更を加えることができます。

あなたはdivのhtmlをこのように変更しなければなりません。

changeHtml('#mydiv', '<p>test content</p>');

また、input要素を除くすべてのhtml要素にこれを使用できます。とにかく、これを変更して任意の要素で使用することができます。

Mozilla によって提供され、 このブログ記事 から適応させたように MutationObserver を使用してください

あるいは、JQueryの例 このリンクに表示 を使用することもできます。

Chrome 18以降、Firefox 14以降、IE 11以降、Safari 6以降

// Select the node that will be observed for mutations
var targetNode = document.getElementById('some-id');

// Options for the observer (which mutations to observe)
var config = { attributes: true, childList: true };

// Callback function to execute when mutations are observed
var callback = function(mutationsList) {
    for(var mutation of mutationsList) {
        if (mutation.type == 'childList') {
            console.log('A child node has been added or removed.');
        }
        else if (mutation.type == 'attributes') {
            console.log('The ' + mutation.attributeName + ' attribute was modified.');
        }
    }
};

// Create an observer instance linked to the callback function
var observer = new MutationObserver(callback);

// Start observing the target node for configured mutations
observer.observe(targetNode, config);

// Later, you can stop observing
observer.disconnect();
8
Anthony Awuley

Divの古いinnerHTMLを変数に格納できます。古いコンテンツが現在のコンテンツと一致するかどうかを確認する間隔を設定します。そうでないときは何かをしてください。

3
codelove

MutationObserverを試してください。

ブラウザのサポート: http://caniuse.com/#feat=mutationobserver

<html>
  <!-- example from Microsoft https://developer.Microsoft.com/en-us/Microsoft-Edge/platform/documentation/dev-guide/dom/mutation-observers/ -->

  <head>
    </head>
  <body>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
    <script type="text/javascript">
      // Inspect the array of MutationRecord objects to identify the nature of the change
function mutationObjectCallback(mutationRecordsList) {
  console.log("mutationObjectCallback invoked.");

  mutationRecordsList.forEach(function(mutationRecord) {
    console.log("Type of mutation: " + mutationRecord.type);
    if ("attributes" === mutationRecord.type) {
      console.log("Old attribute value: " + mutationRecord.oldValue);
    }
  });
}
      
// Create an observer object and assign a callback function
var observerObject = new MutationObserver(mutationObjectCallback);

      // the target to watch, this could be #yourUniqueDiv 
      // we use the body to watch for changes
var targetObject = document.body; 
      
// Register the target node to observe and specify which DOM changes to watch
      
      
observerObject.observe(targetObject, { 
  attributes: true,
  attributeFilter: ["id", "dir"],
  attributeOldValue: true,
  childList: true
});

// This will invoke the mutationObjectCallback function (but only after all script in this
// scope has run). For now, it simply queues a MutationRecord object with the change information
targetObject.appendChild(document.createElement('div'));

// Now a second MutationRecord object will be added, this time for an attribute change
targetObject.dir = 'rtl';


      </script>
    </body>
  </html>
1
juFo

JQueryを介して、または直接DOM-APIを介してコンテンツをdivに追加すると、デフォルトで.appendChild()関数が使用されます。あなたができることは、現在のオブジェクトの.appendChild()関数をオーバーライドし、それにオブザーバを実装することです。 .appendChild()関数をオーバーライドしたので、内容を追加できるようにするために他のオブジェクトからその関数を借りる必要があります。そのため、他のdivの.appendChild()を呼び出して、最後にコンテンツを追加します。もちろん、これは.removeChild()にも当てはまります。

var obj = document.getElementById("mydiv");
    obj.appendChild = function(node) {
        alert("changed!");

        // call the .appendChild() function of some other div
        // and pass the current (this) to let the function affect it.
        document.createElement("div").appendChild.call(this, node);
        }
    };

ここであなたは素朴な例を見つけることができます。あなたは自分でそれを拡張することができると思います。 http://jsfiddle.net/RKLmA/31/

ところで、これはJavaScriptがOpenClosedの原則に準拠していることを示しています。 :)

0
Andries