I'm trying to put a content div into each parent div, but this way it puts all the content divs to the first parent div, not each parent div. I've tried to do it in 2 for loops, tried forEach, but just can't figure it out.
for (let i = 0; i < 5; i++) {
const parent = document.createElement("div");
parent.classList.add("parent");
parent.setAttribute("id","parent");
document.getElementById("container").appendChild(parent);
const content = document.createElement("div");
content.classList.add("content");
document.getElementById("parnet").appendChild(content);
}
Ty for your answer
You're using id's to select your parents with. But you can't have multiple elements with the same id value. getElementById will also look for the first occurence of the id, so you will always get the first parent element.
Besides that, you already have a reference to the parent in your parent variable. No need to look it up again, just use the reference you already have.
const container = document.getElementById("container");
for (let i = 0; i < 5; i++) {
const content = document.createElement("div");
content.classList.add("content");
const parent = document.createElement("div");
parent.classList.add("parent");
parent.append(content);
container.append(parent);
}
Related
I'm attempting to use JavaScript to add rows to a table. I created an anonymous function iterate that iterates id names, and that works fine. The problem is somewhere in my class.
class CreateTable{
constructor(text) {
this.text = text
}
makeTableRow(){
let self = this;
let row = document.createElement('tr');
for (let i = 0; i < 1; i++) {
let el = document.createElement('td');
el.setAttribute('id', iterate(i));
row.appendChild(el);
}
let en = document.getElementById('id1');
console.log(en);
en.innerHTML = self.text;
return row;
}
}
I adapted this class from something that already works, with some tweaks. The en variable is returning a typeError:en is null, and I can't figure it out. What I want to do is create two empty td elements with callable ids, and then add text to the first element immediately. What is the actual problem that is going on here?
The document.getElementById() function returns null if there is no element with the specified ID in the DOM. The elements that you create in the loop have not been added to the DOM, they're appended to a tr that isn't in the DOM either (it's just returned from your function without having been appended to anything).
Just add the required text directly at the time you create the element:
makeTableRow(){
let self = this;
let row = document.createElement('tr');
for (let i = 0; i < 1; i++) {
let el = document.createElement('td');
el.setAttribute('id', iterate(i));
if (i === 0) // for first element
el.innerHTML = self.text; // set the content
row.appendChild(el);
}
return row;
}
Incidentally, you say you want to create two td elements, but your loop only runs for one iteration. The for condition should be i < 2 if you want it to run twice.
Is null because doesn't is identifying the "id", that meaning that you are writing your script before the id="id1".
You need to write your script at the end, just before of "body"
.......
<div id="id1">
</div>
.....
<script>
....
</script>
</body>
I'm currently learning JavaScript and as far as I know have not learned anything that could explain the following:
<div id="parent">
<div>One</div>
<div>Two</div>
</div>
<script>
function test(node) {
var divs = node.children;
console.log(divs);
var div = document.createElement("div");
node.appendChild(div);
console.log(divs);
}
test(document.querySelector("#parent"));
</script>
I want the variable divs to be an object containing the children divs of node that exist when that line of code is run. Which it is, however it seems to update when a child is added to the parent node. What explains this behaviour; am I creating a reference to the element, and if so how do I achieve what I want to?
In JavaScript, every object is passed by a reference instead of value. The .children property of a node is an object (HTMLCollection object to be specific). What that means is that 'divs' variable will not contain the children at the time it is run, it will refer to the children property. When children change and new nodes are added, accessing the divs variable will return the current state of children, so it will contain the new child as well. If you just want to just copy the reference to initial children, you can create another variable.
function test(node) {
var children = node.children;
var divs = [];
// copy every child to the divs array
for (var i = 0; i < children.length; i++) {
divs.push(children[i]);
}
var div = document.createElement("div");
node.appendChild(div);
// since divs is just an array copy of the initial children,
// when children change, the divs still only contains the initial nodes
console.log(divs);
// however, as we said before, children will still be a reference to
// current node's children, so
console.log(children); // outputs 3 divs
}
test(document.querySelector("#parent"));
divs holds a reference to the children property of the selected node. For this reason, if you change this children property, the content of divs also changes.
If you want to keep divs stable, create a shallow copy of the array-like object children:
function test(node) {
var divs = Array.prototype.slice.call(node.children);
console.log(divs);
var div = document.createElement("div");
node.appendChild(div);
console.log(divs);
}
You could create a new array
var divs = new Array(node.children.length);
for(var i = 0; i < node.children.length; i++){
divs[i] = node.children[i]
}
console.log(divs);
var div = document.createElement("div");
node.appendChild(div);
console.log(divs);
You can use querySelectorAll, it returns a static list not live. For more details you can check this link.
https://www.w3.org/TR/selectors-api/#queryselectorall
<div id="parent">
<div>One</div>
<div>Two</div>
</div>
<script>
function test(node) {
var divs = document.querySelectorAll('#'+node.id +' div');
console.log(divs);
var div = document.createElement("div");
node.appendChild(div);
console.log(divs);
}
test(document.querySelector("#parent",'#parent div'));
</script>
I'm trying to change the lay-out for WooCommerce, but since I can't get that working I decided to change it to my wishes by using Javascript to create a div and append it to the existing div. I do have some lines that go through every div with a certain class, but that only works when I let them change the innerHTML. But when I use appendChild, it only appends to the last div. Anyone have an idea what could be it? This is the code I use. The class "product-type-simple" is the div that already exists.
var product_item_wrapper = document.createElement("div");
product_item_wrapper.style.width = "100px";
product_item_wrapper.style.height = "100px";
product_item_wrapper.style.background = "red";
product_item_wrapper.style.color = "white";
product_item_wrapper.innerHTML = "Hello";
product_item_wrapper.className = "product";
var divjes = document.getElementsByClassName("product-type-simple");
for(var i = 0; i < divjes.length; i++){
divjes[i].appendChild(product_item_wrapper);
}
You are creating one element. Then you append it as a child of multiple elements. Each time you do, you remove it from where it was before and place it in the new element.
If you want multiple elements, then you need to create multiple elements.
Move the first 7 lines of your code so they are inside the loop.
One element can only be appended to a single div. Consider making a function which returns a new element to be appended:
function createWrapper()
{
var product_item_wrapper = document.createElement("div");
product_item_wrapper.style.width = "100px";
product_item_wrapper.style.height = "100px";
product_item_wrapper.style.background = "red";
product_item_wrapper.style.color = "white";
product_item_wrapper.innerHTML = "Hello";
product_item_wrapper.className = "product";
return product_item_wrapper;
}
var divjes = {};
divjes = document.getElementsByClassName("product-type-simple");
for (var i = 0; i < divjes.length; i++)
{
divjes[i].appendChild(createWrapper());
}
I am trying to get my game2 element to have two child divs containing the contents of the gameTwo array, but what is happening in this script is that the first time it iterates through the loop, it creates the child div I want, but the second time it creates a child of the child. Can someone advise on how I can edit this so that the divs are both siblings of each other?
var gameTwo = ['Kansas', 'Villanova']
var gameTwoText = '';
for (i = 0; i < gameTwo.length; i++) {
gameTwoText += "<div>" + gameTwo[i];
}
var secondGame = document.getElementById('game2').innerHTML = gameTwoText;
You need a closing tag on each div - try:
gameTwoText += "<div>" + gameTwo[i] + "</div>";
Without the </div>, you never close the first div so each subsequent one is created as a child of the last.
As others have said, make sure you close your DIV tag in the loop, however you can always do this the old fashion way which will build the elements via the DOM:
var secondGame = document.getElementById('game2');
var gameTwo = ['Kansas', 'Villanova'];
var div = null;
for (var i = 0, len = gameTwo.length; i < len; i++) {
div = document.createElement('div');
div.appendChild(document.createTextNode(gameTwo[i]));
secondGame.appendChild(div);
}
I'm writing a javascript function where I get a ul object from my HTML and want to set the text of one of the li elements in theul`. I'm doing:
list = document.getElementById('list_name');
Then I want to access the ith li element of list using a loop.
I have:
for (i = 0; i < 5; i++) {
list[i].innerHTML = "<a>text</a>";
}
but this is not working. What is the proper way to do it?
You need to access the child li elements of the ul. JavaScript and the DOM API can't automagically do that for you.
var list = document.getElementById('list_name'),
items = list.childNodes;
for (var i = 0, length = childNodes.length; i < length; i++)
{
if (items[i].nodeType != 1) {
continue;
}
items[i].innerHTML = "<a>text</a>";
}
You could also use getElementsByTagName('li') but it will get all descendent li elements, and it seems you want only the direct descendants.
You could also avoid innerHTML if you want.
var a = document.createElement('a'),
text = document.createTextNode('text');
a.appendChild(text);
items[i].appendChild(a);
innerHTML can cause issues, such as lost event handlers and the performance issue of serialising and re-parsing the HTML structure. This should be negligible in your example, however.
jQuery Sample code, although the others work:
$("#list_name li").text("<a href=''>text</a>");
Its much more succinct with jQuery
You can try the following
var el = document.createElement("li"),
content = document.createTextNode("My sample text"),
myUl = document.getElementById("ulOne");
el.appendChild(content);
el.id = "bar";
myUl.appendChild(el);
Here's the demo: http://jsfiddle.net/x32j00h5/
I prefer a aproach using getElemenetByTagName, if somehow you get a extra node like a script tag or a span you will have problems. A guess this code will help you:
var list = document.getElementById("mylist");
var items = list.getElementsByTagName("li");
for(var i = 0, size = items.length; i< size; i++){
items[i].innerHTML = "<a href='#'>LINK</a>";
}