Modifying the document
JavaScript Modifying the document (JavaScript修改文档)
The key to creating so-called “live” pages is DOM modification. In this chapter, we are going to show you how to create new elements on the fly, as well as modify the existing page content. (创建所谓的“实时”页面的关键是DOM修改。 在本章中,我们将向您展示如何动态创建新元素,以及如何修改现有页面内容。)
When writing apps or web pages, the first thing you will want to do is manipulating the document structure. Normally, it can be done by using the DOM. (在编写应用或网页时,您首先要做的是操作文档结构。通常,可以通过使用DOM来完成。)
Example: Show a Message
Example: Show a Message
Let’s add a message on the page that looks better than alert. It will look like this:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
<style>
.alert {
padding: 20px;
font-size: 20px;
border-radius: 5px;
color: red;
background-color: yellow;
}
</style>
</head>
<body>
<div class="alert">
Welcome to <strong>w3cdoc</strong>.
</div>
</body>
</html>
And the same thing in javascript:
let div = document.createElement("div");
div.id = 'main';
div.style.padding = "20px";
div.style.fontSize = "20px";
div.style.background = "yellow";
div.style.color = "red";
div.innerHTML = "Welcome to";
document.body.appendChild(div);
let strong = document.createElement("strong");
strong.innerHTML = "w3cdoc";
document.getElementById("main").appendChild(strong);
Above was demonstrated an HTML example. Now, let’s try creating the same div using JavaScript. (上面演示了一个HTML示例。现在,让我们尝试使用JavaScript创建相同的div。)
Creating an Element
Creating an Element (创建元素)
There are two methods of creating DOM nodes. The first one is document.createElement(tag). It helps to create a new element node with the given tag, like here:
let input = document.createElement('input');
The second method is document.createTextNode(text), targeted at creating a new text node with the given text, like this:
let txtNode = document.createTextNode('Welcome to w3cdoc');
Creating the Message
Creating the Message (创建消息)
In the case below, it is a div with alert class and HTML inside:
let div = document.createElement('div');
div.className = "alert";
div.innerHTML = "Welcome to <strong>w3cdoc</strong> ";
document.body.appendChild(div);
So, the element is created. Yet, it’s only in the variable. You can’t see it on the page, as it’s not a part of the document yet. (因此,创建了元素。然而,它只在变量中。您无法在页面上看到它,因为它还不是文档的一部分。)
Methods of Insertion
Methods of Insertion (插入方法)
For making the div show up, it is necessary to insert it into the document. For example, in the document.body. (为了使div显示,有必要将其插入到文档中。例如,在document.body中。)
A special method, such as document.body.append(div), can be used for it. The full code will look like this:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
<style>
#alert {
padding: 20px;
font-size: 20px;
border-radius: 5px;
color: red;
background-color: yellow;
}
</style>
</head>
<body>
<script>
let div = document.createElement('div');
div.id = "alert";
div.innerHTML = "Welcome to <strong>w3cdoc</strong> ";
document.body.append(div);
</script>
</body>
</html>
And the same thing in javascript:
let div = document.createElement("div");
div.id = 'alert';
div.style.padding = "20px";
div.style.fontSize = "20px";
div.style.background = "yellow";
div.style.color = "red";
div.innerHTML = "Welcome to <strong>w3cdoc</strong> ";
document.body.appendChild(div);
Below is a set of methods, allowing to add items to a list and the text before/after it:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
</head>
<body>
<ol id="ol">
<li>One</li>
<li>Two</li>
<li>Three</li>
</ol>
<script>
ol.before('before'); // insert string "before" before <ol>
ol.after('after'); // insert string "after" after <ol>
let li1 = document.createElement('li');
li1.innerHTML = 'prepend';
ol.prepend(li1); // insert li1 at the beginning of <ol>
let liLast = document.createElement('li');
liLast.innerHTML = 'append';
ol.append(liLast); // insert liLast at the end of <ol>
</script>
</body>
</html>
before 1. prepend 2. One 3. Two 4. Three 5. append after
And, the final list will look like this:
before
<ol id="ol">
<li>prepend</li>
<li>One</li>
<li>Two</li>
<li>Three</li>
<li>append</li>
</ol>
after
The mentioned methods are capable of inserting multiple lists of nodes and text pieces in one call. (上述方法能够在一次调用中插入多个节点列表和文本片段。)
In the following example, a string and an element are inserted:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
</head>
<body>
<div id="div"></div>
<script>
div.before('<p>Welcome to w3cdoc</p>', document.createElement('hr'));
</script>
</body>
</html>
The whole text is inserted as text. And, the final HTML will look as follows:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
</head>
<body>
<p>Welcome to w3cdoc</p>
<hr>
<div id="div"></div>
</body>
</html>
In brief, strings are inserted safely, like elem.textContent does it. So, such kinds of methods may be used to insert text pieces or nodes. And you may ask, what will happen if you insert HTML “as html”, including all tags and stuff working, like elem.innerHTML? (简而言之,字符串是安全插入的,就像elem.textContent那样。因此,此类方法可用于插入文本片段或节点。您可能会问,如果将HTML “作为html”插入,包括所有标签和工作内容(如elem.innerHTML ) ,会发生什么?)
Let’s find it out. (跟随记者一探究竟。)
insertAdjacentHTML/Text/Element
insertAdjacentHTML/Text/Element (insertAdjacentHTML/文本/元素)
Another, more flexible method can be used for that is elem.insertAdjacentHTML(where, html). The initial parameter is a code word, indicating where to insert relative to elem. One of the following may be used:
“beforebegin” – inserting html at once before elem, (- “beforebegin” –在elem之前立即插入html ,)
“afterbegin”– inserting html into elem, at the beginning, (- “afterbegin” –在开始时将html插入elem ,)
“beforeend” – inserting html into elem, at the end, (- “beforeend” –在末尾将html插入elem ,)
“afterend” – inserting html at once after elem. (- “afterend” –在elem之后立即插入html。)
The second parameter will be an HTML string, inserted “as HTML”, like this:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
</head>
<body>
<div id="div"></div>
<script>
div.insertAdjacentHTML('beforebegin', '<p>Welcome</p>');
div.insertAdjacentHTML('afterend', '<p>Bye</p>');
</script>
</body>
</html>
The result will be the following:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
</head>
<body>
<p>Welcome</p>
<div id="div"></div>
<p>w3cdoc</p>
</body>
</html>
Let’s check out the picture of insertion variants, in which you can notice similarities between it and the previous picture. The insertion points are similar, yet this method inserts HTML. (让我们来看看插入变体的图片,在这张图片中,您可以注意到它与前一张图片之间的相似之处。插入点相似,但此方法插入HTML。)
Node Removal
Node Removal (节点移除)
The method of node.remove() is used for removing a node. In the case below, you can see how to make your message disappear after a second:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
<style>
#alert {
padding: 20px;
font-size: 20px;
border-radius: 5px;
color: red;
background-color: yellow;
}
</style>
</head>
<body>
<script>
let div = document.createElement('div');
div.id = "alert";
div.innerHTML = "Welcome to <strong>w3cdoc</strong>";
document.body.append(div);
setTimeout(() => div.remove(), 1000);
</script>
</body>
</html>
And the same thing in javascript:
let div = document.createElement('div');
div.id = "alert";
div.style.padding = "20px";
div.style.fontSize = "20px";
div.style.background = "yellow";
div.style.color = "red";
div.innerHTML = "Welcome to <strong>w3cdoc</strong> ";
document.body.append(div);
setTimeout(() => div.remove(), 1000);
Please, take into account that for moving an element to another place, you don’t have to remove it from the old one. All the insertion methods can automatically remove the node from the old place. (请注意,要将元素移动到另一个地方,您不必将其从旧元素中删除。所有插入方法都可以自动从旧位置删除节点。)
In the example below, the swapping of elements is demonstrated:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
</head>
<body>
<div id="first">First</div>
<div id="second">Second</div>
<script>
// no need to call remove
(//无需调用REMOVE)
second.after(first); // take #second and after it insert #first
</script>
</body>
</html>
Cloning nodes: cloneNode
Cloning nodes: cloneNode
Now, let’s see how to insert another similar message. (现在,让我们看看如何插入另一条类似的消息。)
For that, you can make a function and put the code there. There is also an alternative way: cloning the existing div and modifying the text inside it. Sometimes, having a big element can make it faster and simpler.
- The elem.cloneNode(true) call will create a deep clone of the element along with all subelements and attributes. In the case of calling elem.cloneNode(false), the clone will be made without any child elements. (- elem.cloneNode (true)调用将创建元素的深层克隆以及所有子元素和属性。在调用elem.cloneNode (false)的情况下,将生成没有任何子元素的克隆。)
Here is an example of copying the message:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
<style>
#div {
padding: 20px;
font-size: 20px;
border-radius: 5px;
color: red;
background-color: yellow;
}
</style>
</head>
<body>
<div class="alert" id="div">
Welcome to <strong>w3cdoc.</strong>
</div>
<script>
let div2 = div.cloneNode(true); // clone the message
div2.querySelector('strong').innerHTML = 'Javascript book.'; // change the clone
div.after(div2); // show the clone after the existing div
</script>
</body>
</html>
DocumentFragment
DocumentFragment
DocumentFragment is a special DOM node, which serves as a wrapper for passing around lists of nodes. You can also append other nodes to it. But when you insert it somewhere, its content will be inserted instead. For instance, getListContent creates a fragment with <li> items that are later inserted into <ul>, like in the example below:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
</head>
<body>
<ul id="ul"></ul>
<script>
function getListContent() {
let fragment = new DocumentFragment();
for(let i = 1; i <= 5; i++) {
let li = document.createElement('li');
li.append(i);
fragment.append(li);
}
return fragment;
}
ul.append(getListContent()); // (*)
</script>
</body>
</html>
At the last line (*), DocumentFragment is inserted, and its resulting structure will look like this:
<ul>
<li>1</li>
<li>2</li>
<li>3</li>
<li>4</li>
<li>5</li>
</ul>
As a rule, DocumentFragment is rarely used in an explicit way. So, you can return an array of nodes instead, like this:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
</head>
<body>
<ul id="ul"></ul>
<script>
function getListContent() {
let result = [];
for(let i = 1; i <= 5; i++) {
let li = document.createElement('li');
li.append(i);
result.push(li);
}
return result;
}
ul.append(...getListContent()); // append + "..." operator = friends!
</script>
</body>
</html>
About “Document.write”
About “Document.write” (关于“Document.write”)
The document.write is an ancient method of adding something to a web page. (Document.write是一种向网页添加内容的古老方法。)
The syntax of document.write is the following:
<!DOCTYPE html>
<html>
<head>
<title>Title of the Document</title>
</head>
<body>
<p>Hello</p>
<script>
document.write('<b>Welcome to JS book</b>');
</script>
<p>The end</p>
</body>
</html>
By calling document.write(html), you can write the html into the page “right here and now”. The string of html is flexible; it can be dynamically generated. So, you can use JavaScript for creating a full fledged webpage.
This method was created in ancient times but is still alive, as there are scripts that use it. But, document.write works only when the page is loading. (该方法是在古代创建的,但仍然有效,因为有脚本使用它。但是, document.write仅在加载页面时有效。)