父监听器$(this)监听所有选定的子元素

时间:2015-08-20 15:14:09

标签: javascript jquery

当用户点击添加项时,在父元素上附加一个新项目,然后单击该项目,textarea会提示编辑其文本。

HTML DOM / JS Fiddle

<div class="editor"></div>
<a href="#" class="additem">add an item</a>
<div class="options">
    <br><b>Item Text</b> <br>
    <textarea class="itemtext"></textarea>
</div>

JS(jQuery)/ JS Fiddle

var $item    = "<div class='item'>Text here...</div>",
    $itembtn = $('a.additem'),
    $editor  = $('div.editor'),
    $opt = $('div.options');
$itembtn.on('click', function(e){
    e.preventDefault();
    $editor.show();
    $editor.append($item);
});

$($editor).on('click', 'div.item', function(){
    var $this = $(this);
    $opt.show();
    $opt.find('textarea').val($this.text());
    $opt.find('textarea').on('keyup', function(){
        $this.text($opt.find('textarea').val());
    });
});

$($editor).on('blur', 'div.item', function(){
    $opt.hide();
});

但似乎$(this)并未指向单击的元素,而是指向所有单击/选中的子元素!

enter image description here

模糊事件也不起作用了!

我如何将$ this指向一个选定的项目但不是所有点击的项目?

3 个答案:

答案 0 :(得分:3)

嗯,这很容易......

改变这个:

$($editor).on('click', 'div.item', function(){
    var $this = $(this);
    console.log($this);
    $opt.show();
    $opt.find('textarea').val($this.text());
    $opt.find('textarea').on('keyup', function(){
        $this.text($opt.find('textarea').val());
    });
});

进入这个:

$($editor).on('click', 'div.item', function(){
    var $this = $(this);
    console.log($this);
    $opt.show();
    $opt.find('textarea').unbind('keyup').keyup(function(){
        $this.text($opt.find('textarea').val());
    }).val($this.text());
});

由于您要为每个元素添加.on([...]),因此您总是添加一个新的事件侦听器。您可.unbind()它,因此它不会绑定到该元素。然后你重新绑定它。

在此上下文中,使用.on() BAD

答案 1 :(得分:1)

在添加keyup事件之前,销毁你在点击div时添加的keyup事件,是的,已完成

使用$(element).off('keyup')取消绑定上一个keyup事件,然后使用$(element).on('keyup',function)添加当前事件。

检查代码段

var $item    = "<div class='item'>Text here...</div>",
    $itembtn = $('a.additem'),
    $editor  = $('div.editor'),
    $opt = $('div.options');
$itembtn.on('click', function(e){
	e.preventDefault();
    $editor.show();
    $editor.append($item);
});

$($editor).on('click', 'div.item', function(){
    var $this = $(this);
    $opt.show();
    
    var txtEd = $opt.find('textarea');
    txtEd.val($this.text());
    txtEd.off('keyup').on('keyup', function(){
    	$this.text($opt.find('textarea').val());
    });
});

$($editor).on('blur', 'div.item', function(){
    $opt.hide();
});
.editor { margin: 20px 0px; border: 1px solid #888; padding: 5px; display: none; }
.item { background: #ccc; margin: 5px; padding: 5px; }
.options textarea { width: 80%; height: 100px; }
.options { display: none; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div class="editor"></div>
<a href="#" class="additem">add an item</a>
<div class="options">
    <br><b>Item Text</b> <br>
    <textarea class="itemtext"></textarea>
</div>

答案 2 :(得分:1)

一种方法是保留当前“活动”div(单击div)的变量,并使用它来设置文本。

Fiddle

var $item    = "<div class='item'>Text here...</div>",
    $itembtn = $('a.additem'),
    $editor  = $('div.editor'),
    $opt = $('div.options'),
    $txt = $opt.find('textarea'),
    $curtxt;

$itembtn.on('click', function(e){
    e.preventDefault();
    $editor.show();
    $($item).appendTo($editor).click(function(){
        $curtxt = $(this); 
        $txt.val($curtxt.text());
        $opt.show();
        $txt.select().focus();
    });    
});

$txt.keyup(function(){
    $curtxt.html($txt.val().replace(/\r?\n/g, '<br>'));
}).blur(function(){
    $opt.hide();
});
相关问题