SVG滑鼠事件響應的四種寫法
SVG滑鼠事件實現方式的例子效果是:單擊一個紅色的矩形後,它的填充顏色會變成藍色
1 SMIL方式
例程1 滑鼠事件之SMIL方式
- <svg>
- <rectx="15"y="15"width="40"height="40"fill="red">
-
<setattributeName="fill"to="blue"begin="click"
- </rect>
- </svg>
在前面有關“動畫”效果的章節中我們使用過類似的方法,也就是在單擊後觸發一個動畫效果,此例中被改變的是“fill”屬性,由紅變藍,中間沒有漸變的過程,一次到位。
2 Attributes方式
例程2 滑鼠事件之Attributes方式
- <svgxmlns="http://www.w3.org/2000/svg"
- xmlns:xlink=http://www.w3.org/1999/xlink
- xmlns:a3="http://ns.adobe.com/AdobeSVGViewerExtensions/3.0/"
-
a3:scriptImplementation
- <scripttype="text/ecmascript"a3:scriptImplementation="Adobe">
- <![CDATA[
- function changeColor(evt)
- {
- var rect = evt.target;
- rect.setAttributeNS(null, "fill", "blue")
- }
- ]]></script>
- <rectx="5"y="5"width="40"height="40"
- fill="red"
- onclick= "changeColor(evt)"/> u
-
</
這種事件觸發方式想必大家已經很熟悉了,在上一節中,滿眼盡是這種事件觸發方式,即把事件觸發作為元素的屬性與其它其他屬性寫在一起。事件屬性在u處,“onclick”事件呼叫的是“changeColor”函式,引數是“evt”,這樣使得函式內部指令碼可以從“evt”獲得事件相關資訊。這種方式比較常用。
3 JavaScript+SMIL方式
例程3 滑鼠事件之JavaScript+SMIL方式
- <svgonload="makeShape(evt)">
- <script><![CDATA[
- var svgns = "http://www.w3.org/2000/svg";u
- function makeShape(evt) {
- svgDoc = evt.target.ownerDocument;
- var rect = svgDoc.createElementNS(svgns, "rect");v
- rect.setAttributeNS(null, "x", "5");
- rect.setAttributeNS(null, "y", "5");
- rect.setAttributeNS(null, "width", "40");
- rect.setAttributeNS(null, "height", "40");
- rect.setAttributeNS(null, "fill", "red");
- var set = svgDoc.createElementNS(svgns, "set");
- set.setAttributeNS(null, "attributeName", "fill");
- set.setAttributeNS(null, "to", "blue");
- set.setAttributeNS(null, "begin", "click");
- rect.appendChild(set);
- svgDoc.rootElement.appendChild(rect);
- }
- ]]></script>
- </svg>
這個例子沒有圖形元素的事先定義,所有定義都是通過指令碼完成的,包括事件的定義也都是動態指令碼完成的,最後在記憶體中的SVG DOM機構與例程1是類似的。例程3中,v處的“createElementNS”方法,有了一個字尾“NS”是需要新增名稱空間引數的,這裡的名稱空間定義在u處。
作者注:本方式本人測試在FF(Firefox)下沒成功,報了一個錯誤。
4 EventListener方式
例程4 滑鼠事件之EventListener方式
- <svgonload="makeShape(evt)">
- <script><![CDATA[
- var svgns = "http://www.w3.org/2000/svg";
- function makeShape(evt) {
- if ( window.svgDocument == null )
- svgDoc = evt.target.ownerDocument;
- var rect = svgDoc.createElementNS(svgns, "rect");
- rect.setAttributeNS(null, "x", 15);
- rect.setAttributeNS(null, "y", 15);
- rect.setAttributeNS(null, "width", 40);
- rect.setAttributeNS(null, "height", 40);
- rect.setAttributeNS(null, "fill", "red");
- rect.addEventListener("click", changeColor, false); u
- svgDoc.documentElement.appendChild(rect);
- }
- function changeColor(evt) {
- var target = evt.target;
- target.setAttributeNS(null, "fill", "blue");
- }
- ]]></script>
- </svg>
這種方法也是經常用到的,W3C為是DOM元素繫結事件處理函式唯一真正的標準方式。原理就是使用“addEventListener”方法來註冊事件方法,而且一次性可以很方便地註冊很多事件,“EventListener”被稱為“事件監聽器”。 “addEventListener”這個方法的引數依次是:事件的名稱(如:click)、處理該事件的函式名和是否啟用事件捕獲的布林量(一般是false)。
作者注:本方式本人測試在FF下沒成功,報了一個錯誤。
例程4中,u處呼叫了“addEventListener”方法來註冊“onclick”事件,事件處理函式是“changeColor”。值得注意的是寫在引數裡的事件名稱,要去掉“on””,所以填寫的是“click”,而不是“onclick”。
在“addEventListener”的方法中有一個引數表示是否啟用事件捕捉,要理解這個變數的作用,我們需要了解一下在DOM2事件模型中,事件傳播的三個階段。
首先,在捕獲階段(capturing phase),事件是從文件物件(Document object)開始,沿著文件樹向下一直到目標物件傳播.。如果任何目標物件的祖輩(不包括目標物件本身)也有一些指定註冊的捕獲事件的處理程式,在事件傳播的這個階段(捕獲階段)將執行它們,是否啟用事件捕捉的變數的意義也就在於此。
事件傳播的下一個階段發生在目標物件本身:所有註冊到目標物件的對應事件處理程式都被執行。
事件傳播的第三階段是冒泡階段,或者說按文件層次倒序進行,從目標元素到文件物件(Document object)。儘管所有的事件都受事件傳播的捕獲階段(capturing phase)的影響,但是並不是所有型別的事件都冒泡,像“mousedown”這樣的一般事件對文件中的其它其他元素是有意義的,所以這些事件才沿著文件層次向上冒泡,並且觸發目標元素的祖元素的相應事件的處理程式。通常情況下,原始的輸入事件冒泡,而高階的語義事件不會。