Autor Zpráva
ronnie
Profil
K věci. Potřebuji vytvářet libovolně objemné pole selectů. Za každým selectem jsou tlačítka add/delete. Buttonek Add volá funkci add(), která najde první uzel tr (ve kterém je výchozí select), vytvoří kopii a připojí ho k tabulce.

Takto vypadá select:

<table id="members">
<tr>
<td>
<select name="members[]">
<option value="0"> - not defined - </option>
<option value="1">Štěpán Šmíd / Dirigent (Conducter) </option>
...
</select>
</td>
<td>
<input type="button" onclick="addMember()" value="Add another member" class="button" />
</td>
</tr>
</table>

A metody add a cloneObj vypadají takto:

function copyObj (obj) {
var objCopy = {};
for (var i in obj) {
objCopy[i] = obj[i];
}
return objCopy;
}

function addMember()
{
try {
var elm = document.getElementById('members').getElementsByTagName('tr')[0];
var emn = copyObj(elm);
document.getElementById('members').appendChild(emn);
} catch (e) {
alert(e.message);
}
}

Problém je, že tohle nefunguje, vyskočí hláška "Node cannot be inserted at the specified point of hiearchy". Když předám metodě appendChild() vytvořený element přes document.createElement('tr'), tak to funguje. Nevíte, v čem je problém? Javascript není můj primární obor, takže netuším, kde je problém. A nový element se mi složitě vytvářet nechce, ideální by bylo, kdyby fungovalo to kopírování...
Dero
Profil
Vytváříš ve skutečnosti jen mělkou kopii objektu. Uzel dokumentu se navíc v tomto konktextu nechová jako typický objekt, pokud ho chceš kopírovat, použij standardní metodu cloneNode.

http://www.w3schools.com/dom/met_element_clonenode.asp
centi
Profil
Tak v prvom rade zahoď tvoju funkciu copyObj() a použi DOM funkciu cloneNode(), ktorá je priamo na klonovanie určená. Tejto funkcii sa predáva jeden boolean parameter:
cloneNode(true) - naklonuje sa element spolu so všetkými jeho children elementami (to bude tvoj prípad)
cloneNode(false) - naklonuje sa len samotný element

Takže napr: elm.cloneNode(true);

No a po druhé odporúčam do tabuľky vložiť ešte <tbody> element, nastaviť mu dané id (members) a nové riadky pripájať do neho. IE totiž zvykne robiť problémy pri piamom zapisovaní do <table>.
Dero
Profil
No a po druhé odporúčam do tabuľky vložiť ešte <tbody> element, nastaviť mu dané id (members) a nové riadky pripájať do neho.

Správná připomínka, nevšiml jsem si, kam se snažíš prvek připojit. TBODY v HTML existuje, i pokud není v kódu explicitně uvedeno, pozor na to. Prvek TR nemůže být přímým potomkem prvku TABLE.
ronnie
Profil
Děkuji, pánové, hledal jsem ve špatných zdrojích a uvedenou metodu jsem nenašel. Bylo mi divné, že by nebylo možné jednodušeji kopírovat objekt.

O problémech s tbody vím, díky.
Toto téma je uzamčeno. Odpověď nelze zaslat.