javascript - 如何在 Live() 上绑定滚动事件?
前一阵子,我帮某人解决了一个问题,他希望他的文本区域可以自动增长。我写了一个函数,监听该区域的 scroll 和 keyup 事件,并重新计算行数。我想在另一个项目中使用这段代码,但出现了一个问题。这些文本区域还未知。为了解决这个问题,我使用 live 而不是 bind,这样未来的文本区域也会被绑定。
现在我发现 live 执行速度远慢于 bind。我在 jsFiddle 上创建了一个简化的示例。上面的文本区域按我想要的方式工作,但新添加的文本区域由于信号迟到而闪烁(我使用的是 Chrome)。
我如何让 问题是 live 和 bind 一样快?scroll 不能与 live 语句一起使用。有没有办法让 live 支持 scroll? 是否有一个 jQuery 事件可以告诉我有新的 TextArea 被添加,这样我就可以用 bind 将 scroll 添加到新创建的元素上?
我期待你的想法。
编辑:已更改代码链接。已移除 scrollingCode。添加了另一个按钮来创建不同的文本区域。问题与 'scroll' 有关。它没有触发。
澄清:我不知道哪个函数会创建文本区域。我在 Chrome 中看到动态添加的框闪烁。
致未来的读者:
在 jQuery 1.3.x 中,只有以下 JavaScript 事件(除了自定义事件)可以使用 .live() 绑定:
click, dblclick, keydown, keypress, keyup, mousedown, mousemove, mouseout, mouseover, 和 mouseup。从 jQuery 1.4 开始,.live() 方法支持自定义事件以及所有会冒泡的 JavaScript 事件。从 jQuery 1.4.1 开始,即使是 focus 和 blur 也能与 live 一起使用(映射到更合适的冒泡事件 focusin 和 focusout)。从 jQuery 1.4.1 开始,可以指定 hover 事件(映射到 mouseenter 和 mouseleave,而 mouseenter 和 mouseleave 又映射到 mouseover 和 mouseout)。
答案#1
答案很简单。scroll 是防止闪烁的原因,因为它会在调整大小的最初时刻触发。但 scroll 对 live 没有效果(因为它不冒泡),所以你新创建的文本区域将在 keyup 时调整大小,但它触发得较晚(因此会闪烁)。
更新: 当然,我甚至可以解决你的问题。你只需要问一下 :) [演示]
$('textarea.autoresize').live('keyup', function() {
var el = $(this);
if (!el.data("has-scroll")) {
el.data("has-scroll", true);
el.scroll(function(){
resizeTextArea(el);
});
}
resizeTextArea(el);
});
重点是,它将 live 与 bind 混合使用。keyup 事件会在所有元素上触发(因为使用了 live),并有条件地添加唯一的 scroll 事件。
更新 2:哦,顺便说一下,你的整个调整大小的代码可以更好地写成这样:
// resize text area (fixed version of Pointy's)
function resizeTextArea(elem) {
elem.height(1); elem.scrollTop(0);
elem.height(elem[0].scrollHeight - elem[0].clientHeight + elem.height())
}
答案#2
试试这个(JSFiddle):
$('#Add').click(function(){
var id = "newtextarea"+Math.floor(Math.random()*1000);
$('#pane').append($('<textarea class="new" rows="1" cols="40" id="'+id+'"></textarea><br/>'));
$('textarea:last').focus();
bindAgain(id);
});
//inital resize
resizeTextArea($('#tst'));
//'live' event
$('textarea.new').bind('keyup scroll', function() {
resizeTextArea($(this));
});
function bindAgain(id)
{
$('#'+id).bind('keyup scroll', function() {
resizeTextArea($(this));
});
}
基本上,它使用动态创建的ID重新绑定事件。没有karim79的解决方案那么优雅,但它有效。
