看板 Ajax 關於我們 聯絡資訊
※ [本文轉錄自 Web_Design 看板] 作者: TonyQ (沉默是金) 看板: Web_Design 標題: [心得]從 js 到 jQuery 之三:可怕的事件叢林 時間: Sat Aug 9 02:57:09 2008 感謝前兩篇各位版友的不吝支持 , 接下來要推出第三篇 , 還請各位版友多多指教、討論。︿︿ 希望看完這篇 , 你們能了解網頁上得事件有哪些 , 以及為什麼事件在跨平台這件事情上是件很棘手的事情. ──────────────────────────────── 繼「無所遁形的selector」一文體驗到的強大 jquery selector , 暫且讓我們放下 jquery 物件的各種attr css 的屬性不談 , 先來談談我們之前所講過 , javascript最重要的觸發點:事件. ──────────────────────────────── @事件,網頁樂團中的鼓手。 事件掌握著網頁上得所有節奏 , 就算你完全不使用任何javascript , 當你瀏覽網頁 , 就起碼有讀取(onload)跟離開(onunload)正在默默進行 , 當然要奏出美妙樂曲 , 還得要整個樂團的配合 , javascript 就是這整個 事件中的指揮家 , 指揮著各項元素各司其職, 演出一場美妙的狂想曲. 事實上 , 當我看到這個網頁時 , 才深深地體會js 的可能性. http://www.nihilogic.dk/labs/mario/mario_small_music.htm @事件聽起來是個通用名詞,那我們有哪些事件呢? 事件一定綁定(binding)著一個 dom物件, 這是先介紹selector的理由。 基本上大部分事件是所有元素通用的 , 比方說onmouseover , onclick等 , 也有些事件只有某些物件會使用 , 像是 onchange , onsubmit 等 . 底下簡單列表 , 將我們今天的各大主角簡單列出來 on click 物件被按下 on change 物件內容改變(select,input text等form類型元件專用) on mouseover 滑鼠進入dom元件四周的那一剎那觸發 on mouseout 滑鼠離開元件四周時觸發 on mousemove 介於over跟out之間的所有移動行為(會頻繁觸發) on focus 當元件被點選 或者透過tab鍵取得焦點時觸發 on load 在網頁最一開始讀取完成時執行 , 常用於body或iframe. on keydown 按下鍵盤按鍵時 ,主要用於body跟input text. on keyup 放開鍵盤按鍵時 還有更多其他種類 可見此網頁詳細介紹 , http://stuck.myweb.hinet.net/c/js/js_events.htm @這麼多種? 我統統都會用到嗎? 我自己常用的是前面七個 , 其中又以 click mouseover mouseout load居多, 各種事件常見的應用情境跟組合雖然非常有趣 , 但還是先留待以後再做介紹, 我們這篇接下來要告訴大家的是 , 「什麼是事件」. @什麼? 前面的介紹還不夠詳細嗎? 乍看之下你似乎知道所有事情 , 但繼續耐心看下去 , 你會了解前面介紹的只是事件的一半左右而已 , 接下來我們要教你的仍然是書上所不常提到 , 但是非常有趣的事情. @不是就像click一樣 , 按下去就一個事件嗎? 沒錯 , 在某些狀況下是這樣 , 你不需要了解任何事件的細節 , 就只是在對應的觸發時間點執行js 不需要任何其他資訊 . 但是當你想在網頁上追蹤你的滑鼠游標時 , 當你想知道你按下的鍵盤按鍵 究竟是哪一顆按鍵時 ,或者看完mario之後 , 你可能會有雄心壯志想做個網頁版的格鬥天王之類的 , 那你就需要一些關於事件的資訊. @事件紀錄者的歡喜與憂愁 值得高興的事情是 , 瀏覽器早就幫你想到了這件事情 , 於是每個事件必定會伴隨著一個紀錄事件資訊的物件.(底下以event代稱) event物件會紀錄是誰觸發了這個事件(srcElement), 滑鼠游標移到哪,或者keydown按下的按鍵是哪一個(keycode)之類的。 許多特效諸如tooltip , dragand drop 都是根據這些資訊做出來的 , 既然如此 , 那為什麼要說憂愁呢? 身為一個有志氣的網頁設計師, 你應該會想要至少支援Firefox跟ie雙平台 , 或者甚至於像筆者我所在的公司有兩位同事是mac愛好者 , safari 也是我們 需要考慮的對象. @能跨瀏覽器當然好呀 , why not? 問題在於這些瀏覽器對於事件參數的支援都各有一些不同的解讀 , 就以取得 event物件來講好了 , ie 提供 window.event 可取得, firefox則需要透過function傳遞參數. 而且事件提供的內容來講 , 更是各家都有所不同 , 像是要透過事件取得被綁定的對象是誰 , ie下是event.target, firefox下是 event.srcElement, 諸如此類的 . 在你撰寫程式碼時需要時時注意,是否需要寫一些 if-else , 以達到不同瀏覽器一樣的效果. @看起來跨瀏覽器很麻煩... 沒錯!所以有些人選擇只支援 ie體系 , ie only的是非不是我們所關心的 , 我們有更好的選擇!就是選用 jQuery當我們的平台媒介! 在jQuery底下 , 常見瀏覽器有支援的事件元素 , 全部被整合為同樣的介面, 而我們所關心的事件物件如何取得 , 則是透過function傳入param的方式. 有興趣的朋友們可以分別用fx跟ie開這個sample頁 , 透過mousemove一窺事件的全貌. http://tonyq.org/test/testMousemove.html 左右皆是將事件內容印出來的結果. 左邊是jquery element的內容物 , 右邊是當前browser的內容物. 可以發現fx跟ie底下右邊的資料會有所不同 , 左邊則是一致的. 在大部分的狀況下 , jQuery 都將 跨平台的問題謹記在心, 除了部份嚴重issue (ex. ie6 bgirame) 等需特別處理外 , jQuery通常能達到足以令人滿意的跨平台效果. (之後應會有機會繼續介紹其他跨平台特性的部份。) @一個元素只能綁定一種事件嗎? 答案當然是否定的 , 比方說我可能會希望 mouseover移動過inputtext, 時該text自動取得焦點(focus) , text改變時自動做一些檢查(change). 很多時候我們會用事件去呼叫別的元素執行事件 , 達到連環事件的效果. @可以在javascript中綁定事件嗎? 你可以把 onclick 等參數視為 dom成員中的一種 , 賦予其對應的事件成員一個 function 物件. 比方說 inputNode.onclick=function(){ alert("hi");}; 就是針對inputNode綁定onclick事件. 但是透過 = 指定的話 , 之前綁訂的事件會被覆蓋 , 如果你希望是附加而非覆蓋的話 , 應該要透過 attachEvent的方式進行. 這裡又有瀏覽器相容性的問題 attachEvent是ie only , addEventListener 則是 firefox有支援的 . @天啊怎麼又來了!!難道就沒有跨瀏覽器的好解法? 現在你知道為什麼我們要特地強調跨瀏覽器平台了吧(聳肩) 別擔心 , 要綁定幾次都沒問題 , jQuery會幫我們處理好一切的. $("#ele").click(function(e){alert("hi");}) .click(function(e){alert("hi");}) .click(function(e){alert("hi");}) .click(function(e){alert("hi");}); 你看 我們這不就綁定了四個事件給ele了嗎? ( http://tonyq.org/test/testEventBinding.html ) @咦? $("#ele").click(event).click(event) ...? 這是jquery的有趣特性之一 , 他幾乎所有成員都會回傳jquery物件本身, 所以我們可以達成這種稱之為「method chaining」的效果. 當然你想中規中矩的寫成 $("#ele").click(function(e){alert("hi");}); $("#ele").click(function(e){alert("hi");}); 也無妨 , 一切取決於你的習慣. 當物件被click時 , 會按照綁定的順序依序觸發. (當你不想要時 , 可透過 $("#ele").unbind("click") 來解除所有事件.)) @事件真是複雜 , 還有我應該知道的嗎? 關於事件其實我們聚焦在基礎資料的介紹 , 因為我們認為 你早晚會知道 hover事件 = mouseover + mouseout , 以及原來想要到處都擺個click+ajax的慾望是如此讓人興奮(害怕). 但是還有一件事情我們還沒有告訴你 , 那就是事件的相依性. 在能見到的區域中 , body是所有元素的根源 , 相信你不會否認這句話 , 當你在頁面上綁定一個元素, (以下例中的 input button) <body > <div> <input type="button" value="button" /> </div> </body> 則當button被click時 , div跟body的onclick也會被觸發. 因為button實際上也是div的成員 , div也會把它視為一體的觸發 同樣的理由 , 所以對body也觸發 , 有些時候我們會需要用這個trick 實做一些事情. @那能不能讓他不要觸發上級的元素呢? 可以 ,對事件方法 return false ; 告訴他我執行到這裡就結束. ex. $("[type=button]").click(function(e){return false;}); 相依性最常見的用途在於檢查表單資料是否正確填寫 , 我們可以透過 $("form").submit( function(e){ if($("#inputdata").val()=="") //如果某個input text是空白 return false; //我就不submit了 } ); @體驗時間 我們今天介紹的是 jquery corner這隻plug-in , 可以幫你把區塊式的元件很輕鬆的加上圓角的效果 . http://tonyq.org/jqtalk/jq3_jqCorner.html --- 剛剛歷經pcman當掉跟差點睡著 的危機, 總算還是順利寫完了 , 祝各位版友週末愉快..需要加班的也能早點休息 :) 最後再補一些注意事項 , 例子大多是針對CLICK寫 , 不過其他的事件其實大同小異, 另外 js 使用過度有害網頁健康 , 請不要真的作成到處都click +ajax, 以及各種酷炫特效不斷充斥 , 大多數狀況下這樣會導致網頁執行起來有笨重的感覺. -- What do you want to have ? / What do you have? 從書本中,你可以發現我的各種興趣。 從CD中,你可以瞭解我所喜歡的偶像明星。 或許從文字你很難以瞭解一個人,但從物品可以。 My PPolis , My past. http://ppolis.tw/user/Tony -- ※ 發信站: 批踢踢實業坊(ptt.cc) ◆ From: 220.132.59.247 ※ 編輯: TonyQ 來自: 220.132.59.247 (08/09 03:01) -- ※ 發信站: 批踢踢實業坊(ptt.cc) ◆ From: 220.132.59.247
TonyQ:JQ Corner 官網 http://malsup.com/jquery/corner/ 08/09 03:07
awpadam:請問我可以用jquery偵測滑鼠中鍵滾輪事件嗎 08/09 10:30
awpadam:我想做出如http://www.plurk.com/browse 08/09 10:31
awpadam:上方可以用滾輪捲動的效果 08/09 10:31
kosgroup:推 05/04 02:43
etman395:推 08/16 02:36
※ 編輯: TonyQ 來自: 61.224.239.208 (12/15 23:58)
Ting1024:XDDD 04/07 03:00