2014-09-28 139 views
1

我有一個textarea字段,我希望它在獲得焦點時展開,並在失去焦點時收縮。這裏是我的測試代碼:jquery點擊事件模糊後丟失

$(function() { 
    var rows = parseInt(
    $('textarea[name=details]').attr('rows') 
); 

    $('textarea[name=details]').focus(function() { 
    $(this).animate({ rows: rows + 10 }, 250); 
    }).blur(function(e) { 
    $(this).animate({ rows: rows }, 250); 
    }); 
}); 

小提琴: http://jsfiddle.net/p0t1pzh7/3/

問題是,當textarea的具有焦點,並且用戶點擊另一個輸入元素上。 textarea在這種情況下摺疊回來,但點擊事件似乎丟失。

什麼我相信正在發生,是blur()處理程序正在更改頁面,以便點擊的目標更改位置。由於模糊在點擊之前運行,因此點擊實際上正在發生,但由於目標移動了位置,點擊不再觸及某個元素。這是在Linux下的Chrome 37.0.2062.120上。

我認爲的原因是,如果您註釋掉模糊處理程序中textarea的大小調整,則一切都按預期工作。

小提琴:http://jsfiddle.net/p0t1pzh7/4/

我GOOGLE和SO搜索相關的問題,並沒有發現在模糊的順序了多次討論,並單擊事件。通常,解決方案似乎涉及在blur()操作上添加延遲,或者在其他頁面元素上綁定事件以跟蹤發生的事件。

這兩種方法看起來相當脆弱和容易出錯。這種行爲實際上只是一個很好的做法,所以如果沒有「乾淨」的方式去做,我寧願完全放棄它。

僅供參考,延遲的方法做工作,可以在這個小提琴可以看出: http://jsfiddle.net/p0t1pzh7/5/

我明白爲什麼模糊點擊之前觸發,但發現它令人驚訝的是,點擊事件」不是個目標t在模糊被觸發之前「設置」。這是預期的行爲還是不同瀏覽器之間?

回答

2

你可以使用setTimeout函數:

$('textarea[name=details]').focus(function() { 
    $(this).animate({ rows: rows + 10 }, 250); 
}).blur(function(e) { 
    setTimeout(function(){ 
     $(this).animate({ rows: rows }, 250); 
    }.bind(this),400); 

demo

+0

謝謝,但我希望有一個不依賴於延遲的解決方案。我在問題結束時提到我已確認延遲方法確實有效,並與一個小提琴例子相關聯。 – mla 2014-09-28 22:31:49

+0

沒有任何其他選擇,因爲您必須管理代碼之間的差距...... – 2014-09-28 22:41:51

+0

我意識到最初我希望沒有超時的解決方案,但實際上,這似乎是最簡單的方法。我已經有一段時間在生產中運行,沒有用戶的投訴。 – mla 2015-02-20 03:07:24

1

Try this solution

$(window).load(function() { 
     $('textarea.expand').focus(function() { 
      $(this).addClass("expanding") 
      $(this).animate({ 
       height: "10em" 
      }, 500); 
     }); 
     $('textarea.expand').blur(function() { 
      $(this).animate({ 
       height: "1em" 
      }, 500); 
      // $(this).removeClass("expanding") 
     }); 
    }); 


<table> 
    <tr> 
     <td> 
      <textarea class="expand" rows="1" cols="10"></textarea> 
     </td> 
    </tr> 
    <tr> 
     <td>Here is some text just below. Does it move?</td> 
    </tr> 
</table> 


.expand { 
    height: 1em; 
    line-height: 1em; 
    width: 300px; 
    padding: 3px; 
} 
.expanding { 
    position: absolute; 
    z-index: 9; 
} 
textarea { 
    resize: none; 
} 
+0

這似乎不適用於我。編輯示例小提琴包括一堆鏈接:http://jsfiddle.net/JdA6L/45/ 至少對我來說,當我在textarea並點擊其中一個鏈接時,textarea會崩潰,但我不要警惕。 – mla 2014-09-28 22:25:52

+0

評論這條線它的工作// $(this).removeClass(「擴大」) – 2014-09-28 22:40:26

+0

嘿,這對我有用:)你明白爲什麼註釋掉removeClass()修復它? – mla 2014-09-28 22:45:52

0

引入的延遲作品:

$(function() { 
    var rows = parseInt(
    $('textarea[name=details]').attr('rows') 
); 

    $('textarea[name=details]').focus(function() { 
    if (typeof(toDetails) != "undefined") { clearTimeout(toDetails); } 
    $(this).animate({ rows: rows + 10 }, 250); 
    }).blur(function(e) { 
    toDetails = setTimeout(function() { $(this).animate({ rows: rows }, 250); }.bind(this), 250); 
    }); 
}); 
1

他re是一種不使用任何超時的解決方案。見http://jsfiddle.net/29sw1abb/

HTML:

<textarea name="details" rows="5"></textarea> 

<p> 
    <a href="#" class="button">click me</a> 
</p> 

JS

$(function() { 
    var target = undefined; 
    var rows = parseInt(
     $('textarea[name=details]').attr('rows') 
    ); 

    $('textarea[name=details]').focus(function() { 
     $(this).animate({ rows: rows + 10 }, 250); 
    }).blur(function(e) { 
     $(this).animate({ rows: rows }, 250); 
    }); 

    $('.button').mousedown(function (e){ 
     target = $(e.target).attr('class'); 
    }); 
    $(document).mouseup(function (e){ 
     if (target) { 
      alert(target); 
      target = undefined; 
     } 
    }); 

}); 

我beleive你是在假設原始點擊事件正確不點火,因爲目標區域移出的位置之前的事件可以是評估。'mousedown'似乎在模糊之前評估,因此我們可以用'mousedown'捕獲點擊目標信息,然後在'mouseup'上操作事件。擁有更大的目標,更少戲劇性的動畫和更慢的動畫也可以解決這個問題。