Jag sitter här och gör ett litet enkelt drag'n'drop script som gör att man kan dra rader mellan 2 tabeller. Nu är det så att jag har utvecklat det för FF men behöver få det att funka i IE.
Följande händer idag.
1. Jag sparar den rad som man vill dra till en variabel.
2. När man släpper raden så läggs den till den nya tabellen.
Detta fungerar perfekt i FF men givetvis inte i IE. I IE försvinner bara den rad man släpat från sin tabell och inget läggs till det nya målet.
Problemet verkar ligga i att IE inte förstår att det är en rad som skall läggas till utan IE säger att det är ett objekt av typ object och inget HTMLTableRowElement som FF säger. Då blir IE arg och lägger inte till raden.
Här är all min kod:
<html>
<head>
<title>Untitled</title>
<meta http-equiv="generator" content="PHP Designer 2005" />
<script language="JavaScript" type="text/JavaScript">
<!--
// The row that is grabbed
draggedRow = false;
/**
* Init event handlers
*/
function init(){
// Enable rows to be grabbed
document.getElementById('L0001').onmousedown = grabRow;
document.getElementById('L0002').onmousedown = grabRow;
document.getElementById('L0003').onmousedown = grabRow;
document.getElementById('L0004').onmousedown = grabRow;
document.getElementById('L0005').onmousedown = grabRow;
// Enable drop support for tables
document.getElementById('table1').onmouseup = dropRow;
document.getElementById('table2').onmouseup = dropRow;
}
/**
* Grabs the row that the user wants to grab
*/
function grabRow(e){
// Get event
if(!e)
e = window.event;
// Get grabbed row
elem = getTargetElement(e);
// Loop until the element is a row
while(elem.tagName != 'TR')
elem = elem.parentNode;
draggedRow = elem;
}
/**
* Used to drop the row in a new table
*/
function dropRow(e){
// Get event
if(!e)
e = window.event;
// Get where row was dropped
elem = getTargetElement(e);
// Loop until the elem is a table
while(elem.tagName != 'TABLE')
elem = elem.parentNode;
// If a row was dragged
if(draggedRow){
// Add row to table
addRow(elem, draggedRow);
draggedRow = false;
}
}
/**
* Adds a row to the table
*/
function addRow(table, row){
// Dump the row
document.getElementById('posDiv').innerHTML = dumpObject(row);
// Well, IE says row is an object and the same for table so this doesn't work
table.appendChild(row);
}
/**
* Dumps object data
*/
function dumpObject(obj) {
if(typeof obj == "object") {
type = "Type: "+typeof(obj);
type += obj.constructor ? "<br>Constructor: "+obj.constructor : "";
type += "<br>Value: " + obj;
type += "<br>toString: " + obj.toString();
for (property in obj) {
type += "<br>" + property + " = " + obj[property];
}
} else {
type = "Type: "+typeof(obj);
type += "<br>Value: " + obj;
type += "<br>toString: " + obj.toString();
for (property in obj) {
type += "<br>" + property + " = " + obj[property];
}
}
return type;
}
/**
* Returns the target of an event
*/
function getTargetElement(e){
var targ;
if (e.target)
targ = e.target;
else if (e.srcElement)
targ = e.srcElement;
return targ;
}
-->
</script>
</head>
<body id="mybody" onload="init();">
<table id="table1" name="table1" bgcolor="green" width="300">
<tr id="L0001" name="L0001">
<td>L0001</td>
<td>Magnus Karlsson</td>
<td>ER</td>
</tr>
<tr id="L0002" name="L0002">
<td>L0002</td>
<td>Magnus Larsson</td>
<td>ER</td>
</tr>
</table>
<br>
<table id="table2" name="table2" bgcolor="grey" width="300">
<tr id="L0003" name="L0003">
<td>L0003</td>
<td>Per Svensson</td>
<td>Compact</td>
</tr>
<tr id="L0004" name="L0004">
<td>L0004</td>
<td>Sven Willsson</td>
<td>ER</td>
</tr>
<tr id="L0005" name="L0005">
<td id="L0005" name="L0005">L0005</td>
<td id="L0005" name="L0005">Kristian Bengtsson</td>
<td id="L0005" name="L0005">Compact</td>
</tr>
</table>
<div id="posDiv">
</div>
</body>
</html>
1. Ha en korrekt doctype (lämpligen xhtml)
2. Validera koden. Gör det här: http://validator.w3.org/
När du har validerande kod är det lättare att hitta eventuella resterande fel. Oftast löser sig mycket bara genom att rätta till det man får fram vid validering dock.
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html>
<head>
<title>Untitled</title>
<script type="text/JavaScript">
<!--
// The row that is grabbed
draggedRow = false;
/**
* Init event handlers
*/
function init(){
// Enable rows to be grabbed
document.getElementById('L0001').onmousedown = grabRow;
document.getElementById('L0002').onmousedown = grabRow;
document.getElementById('L0003').onmousedown = grabRow;
document.getElementById('L0004').onmousedown = grabRow;
document.getElementById('L0005').onmousedown = grabRow;
// Enable drop support for tables
// document.getElementById('table1').onmouseup = dropRow;
// document.getElementById('table2').onmouseup = dropRow;
document.getElementById('L0001').onmouseup = dropRow;
document.getElementById('L0002').onmouseup = dropRow;
document.getElementById('L0003').onmouseup = dropRow;
document.getElementById('L0004').onmouseup = dropRow;
document.getElementById('L0005').onmouseup = dropRow;
}
/**
* Grabs the row that the user wants to grab
*/
function grabRow(e){
// Get event
if(!e)
e = window.event;
// Get grabbed row
elem = getTargetElement(e);
// Loop until the element is a row
while(elem.tagName != 'TR')
elem = elem.parentNode;
draggedRow = elem;
}
/**
* Used to drop the row in a new table
*/
function dropRow(e){
// Get event
if(!e)
e = window.event;
// Get where row was dropped
elem = getTargetElement(e);
// Loop until the elem is a table
while(elem.tagName != 'TABLE')
elem = elem.parentNode;
// If a row was dragged
if(draggedRow){
// Add row to table
addRow(elem, draggedRow);
draggedRow = false;
}
}
/**
* Adds a row to the table
*/
function addRow(table, row){
// Dump the row
document.getElementById('posDiv').innerHTML = dumpObject(row);
// Well, IE says row is an object and the same for table so this doesn't work
table.appendChild(row);
}
/**
* Dumps object data
*/
function dumpObject(obj) {
if(typeof obj == "object") {
type = "Type: "+typeof(obj);
type += obj.constructor ? "<br>Constructor: "+obj.constructor : "";
type += "<br>Value: " + obj;
type += "<br>toString: " + obj.toString();
for (property in obj) {
type += "<br>" + property + " = " + obj[property];
}
} else {
type = "Type: "+typeof(obj);
type += "<br>Value: " + obj;
type += "<br>toString: " + obj.toString();
for (property in obj) {
type += "<br>" + property + " = " + obj[property];
}
}
return type;
}
/**
* Returns the target of an event
*/
function getTargetElement(e){
var targ;
if (e.target)
targ = e.target;
else if (e.srcElement)
targ = e.srcElement;
return targ;
}
-->
</script>
</head>
<body id="mybody" onload="init();">
<table id="table1" width="300">
<tr id="L0001">
<td>L0001</td>
<td>Magnus Karlsson</td>
<td>ER</td>
</tr>
<tr id="L0002">
<td>L0002</td>
<td>Magnus Larsson</td>
<td>ER</td>
</tr>
</table>
<p></p>
<table id="table2" width="300">
<tr id="L0003">
<td>L0003</td>
<td>Per Svensson</td>
<td>Compact</td>
</tr>
<tr id="L0004">
<td>L0004</td>
<td>Sven Willsson</td>
<td>ER</td>
</tr>
<tr id="L0005">
<td>L0005</td>
<td>Kristian Bengtsson</td>
<td>Compact</td>
</tr>
</table>
<div id="posDiv">
</div>
</body>
</html>
ehhh, hehe...nej! Det är fortfarande samma fel. Jag har provat att hämta ett element genom att använda document.getElementById() och märkte att IE returnerar ett object istället för ett objekt av HTMLElement typ som FF gör. Jag känner på mig att detta kan vara felet. Om man försöker lägga till ett child till ett object och inte ett HTMLElement så funkar säkert inte IE, vilket man kan förstå. Ska det vara så?
Jag har testat en jävla massa fram och tillbaka och börjar bli tokig på dumma IE!
elem = document.getElementByID('L0001');
ger elem == object och inte elem == HTMLTableRowElement som man tycker det borde göra. Verkar mycket skumt.
Efter typ en dags googlande så hittade jag följande: IE appendChild bug
Det var alltså så att IE kräver en <TBODY> tag för att funka. Hur bra är det på en skala?!
Så här är min kod som funkar:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html>
<head>
<title>Untitled</title>
<script type="text/JavaScript">
<!--
// The row that is grabbed
draggedRow = false;
/**
* Init event handlers
*/
function init(){
// Enable rows to be grabbed
document.getElementById('L0001').onmousedown = grabRow;
document.getElementById('L0002').onmousedown = grabRow;
document.getElementById('L0003').onmousedown = grabRow;
document.getElementById('L0004').onmousedown = grabRow;
document.getElementById('L0005').onmousedown = grabRow;
document.getElementById('L0001').onmouseup = dropRow;
document.getElementById('L0002').onmouseup = dropRow;
document.getElementById('L0003').onmouseup = dropRow;
document.getElementById('L0004').onmouseup = dropRow;
document.getElementById('L0005').onmouseup = dropRow;
}
/**
* Grabs the row that the user wants to grab
*/
function grabRow(e){
// Get event
if(!e)
e = window.event;
// Get grabbed row
elem = getTargetElement(e);
// Loop until the element is a row
while(elem.tagName != 'TR')
elem = elem.parentNode;
draggedRow = elem.id;
}
/**
* Used to drop the row in a new table
*/
function dropRow(e){
// Get event
if(!e)
e = window.event;
// Get where row was dropped
elem = getTargetElement(e);
// Loop until the elem is a table
while(elem.tagName != 'TBODY')
elem = elem.parentNode;
// If a row was dragged
if(draggedRow){
// Add row to table
addRow(elem.id, draggedRow);
draggedRow = false;
}
}
/**
* Adds a row to the table
*/
function addRow(tableId, rowId){
// Dump the row
var table = document.getElementById(tableId);
row = document.getElementById(rowId);
table.appendChild(row);
}
/**
* Dumps object data
*/
function dumpObject(obj) {
if(typeof obj == "object") {
type = "Type: "+typeof(obj);
type += obj.constructor ? "<br>Constructor: "+obj.constructor : "";
type += "<br>Value: " + obj;
type += "<br>toString: " + obj.toString();
for (property in obj) {
type += "<br>" + property + " = " + obj[property];
}
} else {
type = "Type: "+typeof(obj);
type += "<br>Value: " + obj;
type += "<br>toString: " + obj.toString();
for (property in obj) {
type += "<br>" + property + " = " + obj[property];
}
}
return type;
}
/**
* Returns the target of an event
*/
function getTargetElement(e){
var targ;
if (e.target)
targ = e.target;
else if (e.srcElement)
targ = e.srcElement;
return targ;
}
-->
</script>
</head>
<body id="mybody" onload="init();">
<table width="300">
<tbody id="table1">
<tr id="L0001">
<td>L0001</td>
<td>Magnus Karlsson</td>
<td>ER</td>
</tr>
<tr id="L0002">
<td>L0002</td>
<td>Magnus Larsson</td>
<td>ER</td>
</tr>
</tbody>
</table>
<p></p>
<table width="300">
<tbody id="table2">
<tr id="L0003">
<td>L0003</td>
<td>Per Svensson</td>
<td>Compact</td>
</tr>
<tr id="L0004">
<td>L0004</td>
<td>Sven Willsson</td>
<td>ER</td>
</tr>
<tr id="L0005">
<td>L0005</td>
<td>Kristian Bengtsson</td>
<td>Compact</td>
</tr>
</tbody>
</table>
<div id="posDiv">
</div>
</body>
</html>