1. 程式人生 > >JS DOM(2017.12.28)

JS DOM(2017.12.28)

init 屬性 don -s 它的 事件 this ppr auto

  一.獲得元素節點的方法

document.getElementById() 根據Id獲取元素節點

document.getElementsByName() 根據name獲取元素節點 遍歷出來的是一個數字

document.getElementsByTagName() 根據HTML標簽名獲取元素節點,註意選擇器返回的是一個NodeList對象,能根據索引號選擇其中1個,可以遍歷輸出。

document.getElementsByClassName() 根據class獲取元素節點

  二、節點關系
(1)作為節點數的文檔
1、parentNode 獲取該節點的父節點

技術分享圖片


2、childNodes 獲取該節點的子節點數組

技術分享圖片


3、firstChild 獲取該節點的第一個子節點
4、lastChild 獲取該節點的最後一個子節點

技術分享圖片


5、nextSibling 獲取該節點的下一個兄弟元素
6、previoursSibling 獲取該節點的上一個兄弟元素

技術分享圖片


7、nodeType 節點的類型,9代表Document節點,1代表Element節點,3代表Text節點,8代表Comment節點,11代表DocumentFragment節點
8、nodeVlue Text節點或Comment節點的文本內容
9、nodeName 元素的標簽名(如P,SPAN,#text(文本節點),DIV),以大寫形式表示

    (2)作為元素樹的文檔
1、firstElementChild 第一個子元素節點
2、lastElementChild 最後一個子元素節點
3、nextElementSibling 下一個兄弟元素節點
4、previousElementSibling 前一個兄弟元素節點
5、childElementCount 子元素節點個數量
註意,此5個方法文本節點不算進去

技術分享圖片

   三、節點操作:創建,插入,刪除節點
1、document.createTextNode() 創建一個文本節點

技術分享圖片


2、document.createElement() 創建一個元素節點,這個方法只接受一個參數,即要創建元素的標簽名。這個標簽名在HTML文檔中不區分大小寫,在XHTML中區分大小寫。

 3、插入節點

appendChild() //將一個節點插入到調用節點的最後面
insertBefore() //接受兩個參數,第一個為待插入的節點,第二個指明在哪個節點前面,如果不傳入第二個參數,則跟appendChild一樣,放在最後。

  insertAfter() //可以自己創建一個在指定節點後面插入節點的函數,代碼如下:

1 function insertAfter(newElement,targetElement){
2         var parent = targetElement.parentNode;
3         if(parentNode.lastChild == targetElement){
4        parent.appendChild(newElement);
5                                                                    }
6 else{parent.insertBefore(newElement,targetElement.nextSibling)
7       }
8                                                                   }                            


  4、刪除和替換節點。
1、removeChild(); 由父元素調用,刪除一個子節點。註意是直接父元素調用,刪除直接子元素才有效,刪除孫子元素就沒有效果了。該方法移除節點,接受一個參數,即要移除的節點,同時該方法返回被移除的節點。只能是一個節點,不能是一組節點。

 2、replaceChild() //刪除一個子節點,並用一個新節點代替它,第一個參數為新建的節點,第二個節點為被替換的節點

技術分享圖片

技術分享圖片

5、document.write()可以方便快捷的把字符串插入到文檔中。

  四、屬性操作

1.

setAttribute()

添加一個新屬性(attribute)到元素上,或改變元素上已經存在的屬性的值。註意:在IE7下,修改了元素的class,如果已有class,則會出現兩個class,通過setAttribute()添加的不生效;如果沒有class,則添加上class,但這個添加上去的class的樣式不會生效。

2.

removeAttribute()

該方法用於移除元素的屬性。

3.

getAttribute()

該方法返回元素上指定屬性(attribute)的值。如果指定的屬性不存在,則返回 null"" (空字符串)(IE5+都返回null)。註意IE7下不能正確返回class,返回的是null,其他正常。

4.

hasAttribute()

hasAttribute() 返回一個布爾值,指示該元素是否包含有指定的屬性(attribute)。註意IE7不支持該方法。

5.

自定義屬性data-*

html5裏有一個data-*去設置獲取元素的自定義屬性值。

<div id="div1" data-aa="11">

利用div1.dataset可以獲得一個DOMStringMap,包含了元素的所有data-*
使用div1.dataset.aa就可以獲取11的值。
同樣,通過設置div1.dataset.bb = "22"就可以設置一個自定義屬性值。
在不兼容的瀏覽器裏,就使用getAttributesetAttribute

五、事件

四、共享onload事件

function addLoadevent(func) {

  var oldonload = window.onload;

 if(typeof window.onload !=‘ function‘){

  window.onload = func;

       }else{

  window.onload = function(){

  func;

  oldonload;

              }

         }


}

addEventListener()

addEventListener()將指定的事件監聽器註冊到目標對象上,當目標對象觸發制定的事件時,指定的回調函數就會觸發。目標對象可以是 文檔上的元素、 document、 window 或者XMLHttpRequest(比如onreadystatechange事件)。

IE8及以下不支持此方法且只有事件冒泡沒有事件捕獲。IE9開始支持此方法,也就有了事件捕獲。

    var div1 = document.getElementById("div1");
    div1.addEventListener("click", listener, false);
    function listener() {
        console.log(‘test‘);
    }
    
    var cloneHtml = div1.cloneNode(true);
    document.body.appendChild(cloneHtml);

第一個參數是事件名,第二個是回調函數,第三個參數為true表示捕獲,false表示冒泡。

    var div1 = document.getElementById("div1");
    div1.addEventListener("click", listener1, true/fasle);
    function listener1() {
        console.log(‘test1‘);
    }

    var div2 = document.getElementById("div2");
    div2.addEventListener("click", listener2, true/fasle);
    function listener2() {
        console.log(‘test2‘);
    }

有一點要註意的是,當對某一個元素1既綁定了捕獲事件,又綁定了冒泡事件時:
當這個元素1並不是觸發事件的那個元素2時,則觸發順序會按照先 捕獲 後 冒泡 的順序觸發;
當這個元素1就是最底層的觸發事件的元素時,則這個元素沒有捕獲和冒泡的區別,誰先綁定就先觸發誰。

    var div2 = document.getElementById("div2");
    
    div2.addEventListener("click", listener2, true);
    function listener2() {
        console.log(‘test2‘);
    }

    div2.addEventListener("click", listener1, false);
    function listener1() {
        console.log(‘test1‘);
    }
    // 按綁定順序執行,兩個`addEventLister()`顛倒過來則執行順序也變化
    // 如果再對`div1`綁定一個捕獲、一個冒泡,則會先觸發捕獲 再 觸發冒泡,與綁定順序無關

removeEventListener()

addEventListener()綁定事件對應的就是移除已綁定的事件。第三個參數的布爾值代表解綁的是捕獲事件還是冒泡事件。兩個事件互不相關。

    var div2 = document.getElementById("div2"); 
    div2.addEventListener("click", listener2, true);
    function listener2() {
        console.log(‘test2‘);
    }
    div2.removeEventListener("click", listener2, true);

註意:只能通過removeEventListener()解綁有名字的函數,對於綁定的匿名函數無法解除綁定。

    div2.addEventListener("click", function(){
        console.log(‘test‘);
        console.log(this);
    }, true);

    div2.removeEventListener("click", function() {
        console.log("test");
    }, true);
    div2.onclick = null;
    // 點擊div2依然打印出test

註意:這裏this指向觸發事件的元素自身。

attachEvent()、detachEvent()

IE8及以下使用這兩個方法綁定和解綁事件,當然,IE9+也支持這個事件。但這個方法綁定的事件默認為冒泡也只有冒泡。

    // 這裏需要在事件前加 on
    div2.attachEvent("onclick", listener1);
    function listener1() {
        console.log(‘test‘);
        console.log(this);
    }
    div2.detachEvent("onclick", listener1);

addEventListener()一樣,也不能解綁匿名函數。
註意:這裏this指向 window

阻止默認事件和冒泡

標準事件和IE事件中的阻止默認事件和冒泡事件也有很大區別。

    var div2 = document.getElementById("div2");
    if (div2.addEventListener) {
        div2.addEventListener("click", function(e) {
            e.preventDefault(); // 阻止默認事件
            e.stopPropagation(); // 阻止冒泡
            console.log(e.target.innerHTML);
        }, false);
    } else {
        div2.attachEvent("onclick", function() {
            var e = window.event;
            e.returnValue = false; // 阻止默認事件
            e.cancelBubble = true; // 阻止冒泡
            console.log(e.srcElement.innerHTML);
        });
    }

IE8及以下的event是綁定在window上的。(我的IE11裏,仿真到IE7IE8也可以取到標準事件裏的 e 對象,估計是升級到IE11的原因)。

自定義事件:createEvent()

createEvent()用於創建一個新的 event ,而後這個 event 必須調用它的 init() 方法進行初始化。最後就可以在目標元素上使用dispatchEvent()調用新創建的event事件了。

createEvent()的參數一般有:UIEvents、MouseEvents、MutationEvents、HTMLEvents、Event(s)等等,分別有對應的init()方法。HTMLEvents、Event(s)對應的都是initEvent()方法。

initEvent(type, bubbles, cancelable)

type表示自定義的事件類型,bubbles表示是否冒泡,cancelable表示是否阻止默認事件。

target.dispatchEvent(ev)

target就是要觸發自定義事件的DOM元素

        var div1 = document.getElementById("div1");
        div1.addEventListener("message", function(){
            console.log(‘test‘);
        }, false);

        var div2 = document.getElementById("div2");
        div2.addEventListener("message", function(e){
            console.log(this);
            console.log(e);
        }, false);
        var ev = document.createEvent("Event");
        ev.initEvent("message", false, true); // 起泡參數變為true,div1的事件就會觸發
        div2.dispatchEvent(ev);

六.獲取元素相關計算後的值

getComputedStyle()、currentStyle()

當我們想獲取元素計算後實際呈現在頁面上的各個值,就用這兩個方法。IE8及以下用currentStyle(),IE9+及其他標準瀏覽器用getComputedStyle()

    var div2 = document.getElementById("div2");
    var result = "";
    if (window.getComputedStyle) {
        result = (window || document.defaultView).getComputedStyle(div2, null)[‘cssFloat‘];
    } else {
        result = div2.currentStyle["styleFloat"];
    }
    console.log(result);
    // document.defaultView返回document對象所關聯的window

這兩個方法在不同的瀏覽器裏差距也很大。
比如float屬性:
getComputedStyleIE9以上需要用cssFloat,其他標準的用float
currentStyleIE8及以下可用styleFloat或者float

比如height屬性:
假如未設置height值,標準瀏覽器裏能計算出高度值,而currentStyle計算出來是auto

上面的例子getComputedStyle是用鍵值去訪問的,也可用getPropertyValue()去訪問。(IE8IE7不支持)

result = (window || document.defaultView).getComputedStyle(div2, null).getPropertyValue("float");

getBoundingClientRect()、getClientRects()

getBoundingClientRect()該方法獲得頁面中某個元素的上、右、下、左分別相對瀏覽器視窗的位置。getBoundingClientRectDOM元素到瀏覽器可視範圍的距離(到瀏覽器頂部而不是文檔頂部)。該函數返回一個Object對象,該對象有6個屬性:top,lef,right,bottom,width,height;這裏的top、leftcss中的理解很相似,width、height是元素自身的寬高,但是rightbottomcss中的理解有點不一樣。right是指元素右邊界距窗口最左邊的距離,bottom是指元素下邊界距窗口最上面的距離。

getClientRects()是返回一個ClientRectList集合。

    var div1 = document.getElementById("div1");
    var rects1 = div1.getClientRects();
    var rects2 = div1.getBoundingClientRect();
    console.log(rects1[0].top);
    console.log(rects2.top);

JS DOM(2017.12.28)