【问题标题】:What event fires when elements are added or removed in the document?在文档中添加或删除元素时会触发什么事件?
【发布时间】:2012-07-20 20:21:55
【问题描述】:

我正在为 Tiddlywiki 制作一种选项卡式界面,我想知道如何在每次打开或关闭 tiddler 时触发此代码。 Tiddlywiki 是一种在浏览器中运行的 HTML 笔记本类型的东西,tiddler 是#tiddlerDisplay 中的一个 div。一次可以有,而且通常不止一个。

我要列出的 div 包含在 #tiddlerDisplay 中,而列表本身是 jQuery("#mainMenu > #singleTiddlerList")

config.macros.singleTiddler.update = function(){
    jQuery("#mainMenu > #singleTiddlerList").empty();
    jQuery("#tiddlerDisplay > div").each(function(i,e){
        jQuery("#mainMenu > #singleTiddlerList").append(jQuery(
            createTiddlyButton(document.createElement("li"),jQuery(e).attr("tiddler"),"",config.macros.singleTiddler.clickHandler)
        ).parent());
    });
};

更新:我不能只添加自定义事件,除非我可以在当前代码之外执行此操作(例如在文档加载时触发的事件)。

【问题讨论】:

  • 如何使用 bind() 创建自定义事件,执行删除/附加并触发它们,以便您可以返回事件响应?
  • 我无法控制打开和关闭的代码,我也不想覆盖它。这可以通过插件完成吗?
  • 我会回答这个问题,见下文。

标签: javascript jquery events dom tiddlywiki


【解决方案1】:

首先为追加/清除 div 创建两个自定义事件。让它们绑定在您使用上面发布的代码的文档中。

jQuery(document).bind('div-removed',function(e){ 
  // code stuff to do for removal 
  jQuery("#mainMenu > #singleTiddlerList").empty(); // required
  // other stuff here
});
jQuery(document).bind('div-appended',function(e){ 
 // code stuff to do on append 
        jQuery("#tiddlerDisplay > div").each(function(i,e){
            jQuery("#mainMenu > #singleTiddlerList").append(jQuery(
                createTiddlyButton(document.createElement("li"),jQuery(e).attr("tiddler"),"",config.macros.singleTiddler.clickHandler)
            ).parent());
        }); // required
  //other stuff here
});

然后在你的代码中稍微改变一下执行:

config.macros.singleTiddler.update = function(){
  $(document).trigger("div-removed");
  $(document).trigger("div-appended");  
};

这绝对不是唯一的方法(我认为现在也可以使用 .promise() 完成,但这是一个开始。更新更新以检查这是否有效。

【讨论】:

  • 第一个触发器是否仅在所有 div 被删除或某个 div 被删除时触发?
  • 等等,我觉得这里有误会。提琴手在#tiddlerDisplay,列表在#singleTiddlerList。我已经更新了我的问题以反映这一点。我不想编辑的代码是在#tiddlerDisplay 中添加和删除 div 的代码。
  • 嗯,也许 this 会帮助你。也许你需要委托。
  • 我分配什么事件? JavaScript 是否具有函数挂钩功能,可以在调用函数时触发事件?
  • 你能看看新代码是否有效吗?实际上,您将内部代码分解为两个事件,它们被触发并执行内部多余的代码。
【解决方案2】:

一种方法是jQuery("#tiddlerDisplay").bind("DOMSubtreeModified", config.macros.singleTiddler.update);,但我认为这仅适用于 Chrome(可能是 Opera 或 Safari,不确定),而且似乎已被弃用。 Firefox 有两个事件来完成同样的事情,但我认为这些也已被弃用。

我在阅读this article 并探索 TiddlyWiki 源代码后发现的另一种方法是:

(function( $, oldRem ){
    Story.prototype.displayTiddler = function(){
        var resp = oldRem.apply( this, arguments );
        $("#tiddlerDisplay").trigger("displayTiddler");
        return(resp);
    };
})( jQuery, Story.prototype.displayTiddler );
(function( $, oldRem ){
    Story.prototype.closeTiddler = function(){
        var resp = oldRem.apply( this, arguments );
        $("#tiddlerDisplay").trigger("closeTiddler");
        return(resp);
    };
})( jQuery, Story.prototype.closeTiddler );
jQuery("#tiddlerDisplay").bind("displayTiddler", config.macros.singleTiddler.update);
jQuery("#tiddlerDisplay").bind("closeTiddler", config.macros.singleTiddler.update);

请注意,事件会在 tiddler 打开或关闭之后触发。此外,正如文章所述,jQuery 可以以同样的方式被窃听,但我不知道原生 DOM 方法,我对此表示怀疑。应该有一个事件,但无论如何,每个人都应该完全放弃它们并使用 jQuery!

【讨论】:

  • 我的大脑正在与这打开的所有可能性竞争!一年前,我正是希望如此。令人惊讶的是,有时当您无法弄清楚某些事情时,您稍后再回来,它就会落入适当的位置。
  • 我不知道这是否称为覆盖,但这对我很有用。我只需要提防另一个插件覆盖它。我称这种方法为窃听。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-10-10
  • 2020-09-16
  • 2019-08-29
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多