2012-08-20 83 views
0

考慮下面的代碼:<TR>標籤未訂閱事件

<!DOCTYPE html> <!-- HTML5 --> 
<html> 
    <head> 
     <meta http-equiv="Expires" content="Fri, Jan 01 1900 00:00:00 GMT"> 
     <meta http-equiv="Pragma" content="no-cache"> 
     <meta http-equiv="Cache-Control" content="no-cache"> 
     <meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1"> 
     <meta http-equiv="content-language" content="en"> 
     <title>Untitled</title> 
     <script type='text/javascript'> 
      function createTableRow() { 
       var tr = document.createElement("tr"); 
       var strWork = "<tr onmouseover='this.style.cursor=\"pointer\";'"; 
       strWork += " onmouseout='this.style.cursor=\"auto\";'"; 
       strWork += " onclick='ShowClick(this);'"; 
       strWork += " id='TestCell'><td>Test!</td></tr>"; 
       alert(strWork); 
       tr.outerHTML = strWork; 
       return tr; 
      } 

      function BuildTable() { 
       var table = document.createElement("table"); 
       table.appendChild(createTableRow()); 
       return table; 
      } 

      function ShowClick(obj) { 
       alert(obj.id); 
      } 
     </script> 
    </head> 
    <body onload='alert(BuildTable().outerHTML);'> 
    &nbsp; 
    </body> 
</html> 

第一個「警告」對話框中顯示的標籤,我想形成它,但是,在「的onload =警報」行返回結果「 <表> < tr> </tr> </table>「。

我在做什麼錯?爲什麼這些事件不與TR標籤綁定?

另外,我想補充一點,我最初分配使用JavaScript的事件,即:

tr.onclick = function() { ShowClick(this); }; 

但有完全相同的結果...

我真的不明白這一點,我無法在任何地方找到任何有關該問題的討論......任何幫助將不勝感激!

+0

請學習在現代瀏覽器中使用'console.log()'。 – 2012-08-20 01:12:30

+0

@ JaredFarrish--請學會寬容使用的瀏覽器。 – RobG 2012-08-20 01:52:03

+0

@RobG - 哈哈,有趣的東西。除非你認真,在這種情況下,你呢? – 2012-08-20 01:53:35

回答

1

您的代碼會在JavaScript控制檯中拋出NO_MODIFICATION_ALLOWED_ERR。該W3C spec具有這樣說的:

[element.outerHTML]拋出一個NO_MODIFICATION_ALLOWED_ERR異常,如果元素的父是Document節點。

同樣的事情發生在你的代碼中。在將其添加到另一個節點(例如table)之前,您正在設置trouterHTML。這就是爲什麼它的outerHTML無法更改。

最簡單的解決方案是不使用outerHTML。試試你的原始的方法:

function createTableRow() { 
    var tr = document.createElement('tr'); 
    tr.onmouseover = function() { 
    this.style.cursor = 'pointer'; 
    }; 
    tr.onmouseout = function() { 
    this.style.cursor = 'auto'; 
    }; 
    tr.onclick = function() { 
    ShowClick(this); 
    }; 
    tr.id = 'TestCell'; 
    tr.innerHTML = '<td>Test!</td>'; 
    return tr; 
} 

注意,當你alert(或console.log)的tableouterHTML,你會看到這樣的事情:

<table><tr id="TestCell"><td>Test!</td></tr></table> 

但不要讓這種欺騙你。事件處理程序不顯示,但這是因爲它們直接連接到DOM節點,因此繞過了HTML。請放心,他們完美地工作。

看到自己,試試這個現場演示:jsbin.com/oterit/1/edit

+0

如果您特別針對Moziall瀏覽器,MDN是一個適當的參考。更一般地說,(草案)[W3C DOM分析和序列化規範](http://html5.org/specs/dom-parsing.html#outerhtml)是一個更好的參考,因爲它適用於所有瀏覽器,而不是特定的子集。 – RobG 2012-08-20 01:58:20

+0

@RobG:謝謝你的建議。:) – PPvG 2012-08-20 02:00:17

+0

@ JaredFarrish-較新的W3C **規範**沒有版本號,只是「最後更新」日期,因爲它們是「活文件」,而不是靜態的。 MDN甚至沒有這個願望,它是Mozilla瀏覽器中觀察到的行爲的社區維基。 W3C規範針對**所有**瀏覽器的當前和未來行爲。 – RobG 2012-08-20 03:14:52

2

你createTableRow功能是關閉...

您已經創建了 「TR」 的對象。然後你把"<tr"放在下一行。作爲strWork變量的一部分。你基本上正在重複這個任務,那會破壞DOM。

function createTableRow () { 
    var tr = document.createElement("tr"); 
    tr.setAttribute("onmouseover" , "this.style.cursor='pointer';"); 
    tr.setAttribute("onmouseout" , "this.style.cursor='auto';"); 
    tr.setAttribute("onclick" , "showClick(this);"); 
    tr.setAttribute("id" , "TestCell"); 
    var td = document.createElement("td"); 
    td.appendChild(document.createTextNode("Test!")); 
    tr.appendChild(td); 

    return tr; 
} 
+0

這是因爲他使用'outerHTML'來考慮元素本身,而且在瀏覽器中也很不一致。 – 2012-08-20 01:30:22

0

你缺少的一部分,你居然添加的表身,即:

document.body.appendChild(table); 

無論哪種方式,outerHTML和創建trtddocument.createElement是跨瀏覽器頗不一致,您最好的選擇是使用table.insertRowrow.insertCell

function createTableRow(table) { 
    var tr = table.insertRow(0); 
    tr.onmouseover = function() { this.style.cursor = "pointer"; } 
    tr.onmouseout = function() { this.style.cursor="auto"; } 
    tr.onclick = function() { ShowClick(tr); } 
    tr.id = "TestCell"; 
    var cell = tr.insertCell(0); 
    cell.innerHTML = "Test!"; 
} 

function BuildTable() { 
    var table = document.createElement("table"); 
    table.appendChild(createTableRow()); 
    document.body.appendChild(table); // here's where you add the table to the page 
    return table; 
} 

下面是一個jsfiddle的例子。

+0

請注意,爲了與正在使用的瀏覽器(即舊版本的IE)兼容,您必須將新的tr添加到tbody元素,並將tbody添加到表中。 – RobG 2012-08-20 02:57:58

1

其他答案有有用的信息,這裏的多。如果你想使用標記來初始化一個DOM片段,你最好創建一個父節點,並插入標記爲innerHTML的,如:

function createTableRow() { 
    var tBody = document.createElement('tbody'); 
    var strWork = "<tr onmouseover='this.style.cursor=\"pointer\";'" 
       + " onmouseout='this.style.cursor=\"auto\";'" 
       + " onclick='ShowClick(this);'" 
       + " id='TestCell'><td>Test!</td></tr>"; 
    tBody.innerHTML = strWork; 
    return tBody.firstChild; 
} 

但是,這不會在大多數版本的IE作爲工作您不能使用innerHTML或outerHTML創建表格的某些部分,儘管您可以使用它來創建整個表格。

此外,(再次在IE中),您必須將tr元素添加到tbody元素,而不是直接添加到表中,因爲tr不能是表格的子元素,它必須是tbody的子元素 - 並且人們說IE不符合標準:-)

底線是,你最好使用純粹的DOM來創建表格,而不是標記,其他答案。

+0

我會贊成,雖然我承認我不在「IE標準」部分。 – 2012-08-20 03:09:37