'Use js to append an ul to an li

yeah you read it right i'm trying to append an ul element in an existing li element and create a sub list. I'm using code from codepen (https://codepen.io/Pestov/pen/AvQmxv) to make a genealogy tree and i would like to create dynamically the tree. For this, i have to create a sub ul element in a previously created li, then had two li to that sub ul.

----EDIT---- My problem is: HierarchyRequestError: Failed to execute 'appendChild' on 'Node': The new child element contains the parent. Js seems to think that my ul is my parent but in fact it's a new sub ul.

Here's my code:

<div class="tree" id="tree"></div>

function launchTree(){
    var div = document.getElementById("tree");
  var ul = document.createElement("ul");
  var li = document.createElement("li");
  var a = document.createElement("a");
  //create the main ul element
  ul.setAttribute("id", "main_ul");   
  div.appendChild(ul)
  //put my first parent
  li.setAttribute("id", "AC_Lila_li");
  a.setAttribute("data-content", "AC Lila");
  a.setAttribute("id", "AC_Lila_a");
  
  ul.appendChild(li);
  li.appendChild(a);
  //create my sub ul to put childs !!!! here's the problem!!!
  ul.setAttribute("id", "AC_Lila_ul");   
  li.appendChild(ul)
  //create my first child
  li.setAttribute("id", "Queen_Elisa_li");
  a.setAttribute("data-content", "Queen Elisa");
  a.setAttribute("id", "Queen_Elisa_a");
  
  ul.appendChild(li);
  li.appendChild(a);
  //create my second child
  li.setAttribute("id", "Wendy_li");
  a.setAttribute("data-content", "Wendy");
  a.setAttribute("id", "Wendy_a");
  
  ul.appendChild(li);
  li.appendChild(a);
  
}

I hope i'm clear of what i wanted to do and thanks for your help!



Solution 1:[1]

It was so simple, in fact, ul was always the same so i had to define my variables again. Here's the new code:

function debut(){
    var div = document.getElementById("tree");
  var ul = document.createElement("ul");
  var li = document.createElement("li");
  var a = document.createElement("a");
  
  ul.setAttribute("id", "main_ul");   
  div.appendChild(ul)
  
  li.setAttribute("id", "AC_Lila_li");
  a.textContent = "AC Lila";
  a.setAttribute("id", "AC_Lila_a");
  
  ul.appendChild(li);
  li.appendChild(a);
  
  var ul = document.createElement("ul");
  
  ul.setAttribute("id", "AC_Lila_ul");   
  li.appendChild(ul)
  
  var li = document.createElement("li");
  var a = document.createElement("a");
  
  li.setAttribute("id", "Queen_Elisa_li");
  a.setAttribute("onclick","descend_click();");
  a.textContent = "Queen Elisa";
  a.setAttribute("id", "Queen_Elisa_a");
  
  ul.appendChild(li);
  li.appendChild(a);
  
  var li = document.createElement("li");
  var a = document.createElement("a");
  
  li.setAttribute("id", "Wendy_li");
  a.setAttribute("onclick","descend_click();");
  a.textContent = "Wendy";
  a.setAttribute("id", "Wendy_a");
  
  ul.appendChild(li);
  li.appendChild(a);
  
}

Solution 2:[2]

A way to do that :

const 
  divTree = document.querySelector('#tree')
,  infos = 
  [ { elmLI : { id:'AC_Lila_li' },     elmA: { id:'AC_Lila_a',     'data-content': 'AC Lila'     } }
  , { elmLI : { id:'Queen_Elisa_li' }, elmA: { id:'Queen_Elisa_a', 'data-content': 'Queen Elisa' } }
  , { elmLI : { id:'Wendy_li' },       elmA: { id:'Wendy_a',       'data-content': 'Wendy'       } }
  ];

// launchTree()

function launchTree()
  {
  let nvUL = divTree.appendChild( document.createElement('ul') )

  nvUL.id = 'main_ul'

  for (let { elmLI, elmA } of infos )
    {
    let
      nvLI = nvUL.appendChild( document.createElement('li') )
    , nvA  = nvLI.appendChild( document.createElement('a')  )
      ;
    nvLI.id             = elmLI.id
    nvA.id              = elmA.id
    nvA.dataset.content = elmA['data-content']
    nvA.textContent     = '-----'
    }
  }

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 Vincent Coulombe
Solution 2 Mister Jojo