← JavaScript EnglishChapter 10 of 13

DOM Manipulation

## Learning Objectives - Select and traverse DOM elements - Modify elements and their content - Handle events effectively - Create and remove elements dynamically ## Selecting Elements ### Single Elements ```javascript // By ID const element = document.getElementById("myId"); // By CSS selector (first match) const first = document.querySelector(".myClass"); const nested = document.querySelector("div.container > p"); // getElementById vs querySelector // - getElementById: faster, directly by ID // - querySelector: more flexible, CSS selectors ``` ### Multiple Elements ```javascript // By tag name const paragraphs = document.getElementsByTagName("p"); // By class name const items = document.getElementsByClassName("item"); // By CSS selector (all matches) const allLinks = document.querySelectorAll("a.nav-link"); // querySelectorAll returns NodeList (forEach available) // getElementsBy* returns HTMLCollection (array-like, no forEach) ``` ## Traversing the DOM ```javascript const element = document.querySelector(".item"); // Parent element.parentElement; element.parentNode; // Children element.children; // HTMLCollection element.childNodes; // NodeList (includes text nodes) element.firstChild; // First node element.firstElementChild; // First element child element.lastChild; element.lastElementChild; // Siblings element.nextSibling; element.nextElementSibling; element.previousSibling; element.previousElementSibling; ``` ## Modifying Elements ### Changing Content ```javascript const div = document.getElementById("content"); // textContent (plain text) div.textContent = "Hello, World!"; // innerHTML (HTML parsing) div.innerHTML = "

Paragraph

"; // innerText (visible text, respects CSS) div.innerText = "Visible text"; // Best for security: createElement + textContent const p = document.createElement("p"); p.textContent = "Safe content"; div.appendChild(p); ``` ### Changing Attributes ```javascript const link = document.querySelector("a"); link.getAttribute("href"); link.setAttribute("href", "https://example.com"); link.removeAttribute("href"); link.hasAttribute("href"); // Direct property access (for id, className, value, etc.) link.href = "https://example.com"; input.value = "text"; img.src = "image.jpg"; ``` ### Changing Styles ```javascript const element = document.querySelector(".box"); element.style.color = "blue"; element.style.backgroundColor = "#f0f0f0"; element.style.fontSize = "16px"; // CSS custom properties element.style.setProperty("--my-color", "red"); // Best approach: class toggling element.classList.add("active"); element.classList.remove("hidden"); element.classList.toggle("active"); element.classList.contains("active"); ``` ## Creating and Inserting Elements ```javascript // Create element const newDiv = document.createElement("div"); newDiv.textContent = "I'm new!"; // Insert const parent = document.querySelector(".container"); // Append as last child parent.appendChild(newDiv); // Insert before another element const reference = parent.querySelector(".special"); parent.insertBefore(newDiv, reference); // Modern insertion methods parent.append(newDiv); // Append multiple children parent.prepend(newDiv); // Insert as first child element.before(newDiv); // Insert before element element.after(newDiv); // Insert after element // With text parent.append("Just text"); // Insert text node parent.prepend(document.createTextNode("Text")); ``` ### Removing Elements ```javascript const element = document.querySelector(".to-remove"); element.remove(); // Modern element.parentNode.removeChild(element); // Legacy // Remove children const parent = document.querySelector(".container"); parent.innerHTML = ""; // Remove all children while (parent.firstChild) { parent.removeChild(parent.firstChild); // Remove one by one } ``` ## Working with Classes ```javascript const element = document.querySelector(".box"); // Add class element.classList.add("active"); // Remove class element.classList.remove("disabled"); // Toggle class element.classList.toggle("expanded"); // Check class if (element.classList.contains("active")) { // Do something } // Multiple classes element.classList.add("active", "highlighted"); element.classList.remove("old", "outdated"); ``` ## Event Handling ### Adding Event Listeners ```javascript const button = document.querySelector("#myButton"); // addEventListener button.addEventListener("click", function(event) { console.log("Clicked!", event.target); }); // Arrow function button.addEventListener("click", (event) => { console.log("Clicked!", event.target); }); // Reference to named function function handleClick(event) { console.log("Clicked!", event.target); } button.addEventListener("click", handleClick); // Remove listener button.removeEventListener("click", handleClick); ``` ### Event Types ```javascript // Mouse events element.addEventListener("click", handler); element.addEventListener("dblclick", handler); element.addEventListener("mouseenter", handler); element.addEventListener("mouseleave", handler); // Keyboard events document.addEventListener("keydown", (e) => { console.log("Key:", e.key); console.log("Code:", e.code); }); document.addEventListener("keyup", handler); // Form events form.addEventListener("submit", handler); input.addEventListener("focus", handler); input.addEventListener("blur", handler); input.addEventListener("change", handler); // On change input.addEventListener("input", handler); // On every input // Document events document.addEventListener("DOMContentLoaded", handler); window.addEventListener("load", handler); window.addEventListener("resize", handler); window.addEventListener("scroll", handler); ``` ### Event Object ```javascript element.addEventListener("click", (event) => { event.target; // Element that triggered event event.currentTarget; // Element with listener event.type; // Event type ("click") event.clientX; // Mouse X position event.eventY; // Mouse Y position event.preventDefault(); // Prevent default action event.stopPropagation(); // Stop bubbling }); ``` ### Event Delegation ```javascript // Instead of adding listeners to each item document.querySelector("ul").addEventListener("click", (e) => { if (e.target.matches("li")) { console.log("Clicked:", e.target.textContent); } }); ``` ### once Option ```javascript button.addEventListener("click", handler, { once: true }); // Fires only once ``` ### preventDefault ```javascript const form = document.querySelector("form"); form.addEventListener("submit", (e) => { e.preventDefault(); // Stop form submission // Handle manually }); const link = document.querySelector("a"); link.addEventListener("click", (e) => { e.preventDefault(); // Stop navigation }); ``` ## Working with Forms ```javascript const form = document.querySelector("form"); const input = form.querySelector("input[name='username']"); // Get form data const formData = new FormData(form); const data = Object.fromEntries(formData); // Input value input.value; // Get value input.value = "new value"; // Set value input.checked; // For checkboxes/radios input.disabled = true; // Disable input ``` ## Data Attributes ```javascript const element = document.querySelector(".item"); // Read data attribute element.dataset.userId; // "123" element.dataset["userId"]; // "123" // Write data attribute element.dataset.userId = "456"; element.dataset.loading = "true"; // data-user-id -> dataset.userId (camelCase) // data-user-id-string -> dataset.userIdString ``` ## Summary - Use `querySelector`/`querySelectorAll` for flexible element selection - `textContent` is safer than `innerHTML` for plain text - Always prefer `classList` over modifying `style` directly - Use `addEventListener` for attaching event handlers - Event delegation reduces the number of event listeners - `data-*` attributes store custom data on elements

Comments

Comments powered by Giscus

To enable comments, add your Giscus embed code here.

Learn more about Giscus →