DOM Manipulation - Exercise 2
The document.createElement() method creates a new HTML element in memory. You pass the tag name as a string, and it returns a new element node that you can then add to the page.
// Create a new paragraph element
const newParagraph = document.createElement('p');
// Create a new div element
const newDiv = document.createElement('div');
// Create a new button element
const newButton = document.createElement('button');
// Set content and attributes
newParagraph.textContent = 'This is a new paragraph.';
newDiv.id = 'myDiv';
newButton.textContent = 'Click Me';
console.log(newParagraph); // <p>This is a new paragraph.</p>
The appendChild() method adds a node as the last child of a parent element. It returns the appended child node. If the child already exists in the DOM, it will be moved to the new position.
// Create a new list item
const newItem = document.createElement('li');
newItem.textContent = 'New List Item';
// Get the parent element
const list = document.getElementById('myList');
// Add the new item to the list
list.appendChild(newItem);
// You can also chain operations
const container = document.getElementById('container');
const paragraph = document.createElement('p');
paragraph.textContent = 'Added paragraph';
container.appendChild(paragraph);
The insertBefore() method inserts a new node before a specified reference node. It is called on the parent element and takes two arguments: the new node and the reference node.
// Create a new element
const newItem = document.createElement('li');
newItem.textContent = 'Inserted Item';
// Get the parent and reference elements
const list = document.getElementById('myList');
const secondItem = list.children[1];
// Insert newItem before secondItem
list.insertBefore(newItem, secondItem);
// If reference is null, it works like appendChild
list.insertBefore(newItem, null); // Adds at the end
The removeChild() method removes a specified child node from its parent and returns the removed node. You call it on the parent element and pass the child you want to remove.
// Get the parent and child elements
const list = document.getElementById('myList');
const itemToRemove = document.getElementById('item2');
// Remove the child from the parent
const removedItem = list.removeChild(itemToRemove);
console.log(removedItem); // The removed element
// Alternative: remove using parentNode
const element = document.getElementById('someElement');
element.parentNode.removeChild(element);
// Modern approach using remove() method
const item = document.getElementById('item3');
item.remove(); // Removes itself from the DOM
The replaceChild() method replaces a child node with a new node. It is called on the parent element and takes two arguments: the new node and the node to be replaced.
// Create a new element
const newHeading = document.createElement('h2');
newHeading.textContent = 'New Heading';
// Get the parent and the element to replace
const container = document.getElementById('container');
const oldHeading = document.getElementById('oldHeading');
// Replace old element with new element
const replacedElement = container.replaceChild(newHeading, oldHeading);
console.log(replacedElement); // The old element that was replaced
// Modern approach using replaceWith()
const oldParagraph = document.getElementById('oldPara');
const newParagraph = document.createElement('p');
newParagraph.textContent = 'Replacement paragraph';
oldParagraph.replaceWith(newParagraph);
The cloneNode() method creates a copy of a node. Pass true for a deep clone that includes all child elements, or false for a shallow clone that only copies the element itself.
// Get an element to clone
const originalCard = document.getElementById('card');
// Shallow clone (only the element, no children)
const shallowClone = originalCard.cloneNode(false);
console.log(shallowClone.children.length); // 0
// Deep clone (includes all children)
const deepClone = originalCard.cloneNode(true);
console.log(deepClone.children.length); // Same as original
// Add the clone to the page
document.body.appendChild(deepClone);
// Note: Cloned elements do not have event listeners
// You need to add event listeners to the clone separately
The addEventListener() method attaches an event handler to an element. It takes the event type as a string and a callback function that runs when the event occurs.
const button = document.getElementById('myButton');
// Add a click event listener
button.addEventListener('click', function() {
console.log('Button was clicked!');
});
// Using arrow function
button.addEventListener('click', () => {
console.log('Clicked with arrow function');
});
// Named function for reusability
function handleClick(event) {
console.log('Event type:', event.type);
console.log('Target element:', event.target);
}
button.addEventListener('click', handleClick);
// Multiple events on same element
const input = document.getElementById('myInput');
input.addEventListener('focus', () => console.log('Focused'));
input.addEventListener('blur', () => console.log('Blurred'));
The removeEventListener() method removes an event handler that was added with addEventListener(). You must pass the exact same function reference that was used when adding the listener.
const button = document.getElementById('myButton');
// Define the handler function
function handleClick() {
console.log('Button clicked!');
}
// Add the event listener
button.addEventListener('click', handleClick);
// Remove the event listener (same function reference)
button.removeEventListener('click', handleClick);
// This will NOT work (different function reference)
button.addEventListener('click', function() { console.log('Hi'); });
button.removeEventListener('click', function() { console.log('Hi'); });
// The above removal fails because they are different function objects
// One-time listener using options
button.addEventListener('click', handleClick, { once: true });
// Automatically removed after first trigger
The parentElement property returns the parent element of a node. It returns null if the node has no parent or if the parent is not an element node.
// Get an element
const listItem = document.getElementById('item1');
// Access its parent element
const parentList = listItem.parentElement;
console.log(parentList.tagName); // 'UL' or 'OL'
// Chain to go up multiple levels
const grandparent = listItem.parentElement.parentElement;
// Check if parent exists before using
if (listItem.parentElement) {
listItem.parentElement.style.border = '1px solid red';
}
// parentNode vs parentElement
// parentNode can return any node type
// parentElement only returns element nodes
const html = document.documentElement;
console.log(html.parentNode); // #document
console.log(html.parentElement); // null
The children property returns only element children, while childNodes returns all child nodes including text and comment nodes. Use children when you only need HTML elements.
const list = document.getElementById('myList');
// children returns HTMLCollection of element children only
console.log(list.children); // HTMLCollection of li elements
console.log(list.children.length); // Number of child elements
console.log(list.children[0]); // First child element
// childNodes returns NodeList including text nodes
console.log(list.childNodes); // NodeList with text nodes too
console.log(list.childNodes.length); // Usually more than children
// Useful properties
console.log(list.firstElementChild); // First child element
console.log(list.lastElementChild); // Last child element
// Loop through children
for (const child of list.children) {
console.log(child.textContent);
}
The nextElementSibling and previousElementSibling properties return the next and previous sibling elements. They skip text nodes and only return element nodes, or null if there is no sibling.
const secondItem = document.getElementById('item2');
// Get next sibling element
const nextItem = secondItem.nextElementSibling;
console.log(nextItem.textContent); // Content of item3
// Get previous sibling element
const prevItem = secondItem.previousElementSibling;
console.log(prevItem.textContent); // Content of item1
// Check for siblings before accessing
if (secondItem.nextElementSibling) {
secondItem.nextElementSibling.style.color = 'blue';
}
// Loop through all siblings
let sibling = secondItem.parentElement.firstElementChild;
while (sibling) {
console.log(sibling.textContent);
sibling = sibling.nextElementSibling;
}
The classList.toggle() method adds a class if it is not present, or removes it if it is. It returns true if the class was added and false if it was removed.
const box = document.getElementById('myBox');
// Toggle a class
box.classList.toggle('active');
// If 'active' was present, it is removed
// If 'active' was not present, it is added
// Check the return value
const wasAdded = box.classList.toggle('highlight');
console.log(wasAdded); // true if added, false if removed
// Force add or remove with second argument
box.classList.toggle('visible', true); // Always adds
box.classList.toggle('visible', false); // Always removes
// Common use case: toggle on click
const button = document.getElementById('toggleBtn');
button.addEventListener('click', () => {
box.classList.toggle('dark-mode');
});