DOM(document object model)
文档对象模型 (DOM) 是 HTML 和 XML 文档的编程接口。它提供了对文档的结构化的表述,并定义了一种方式可以结构化的方式进行访问,从而改变文档的内容。DOM 将文档解析为一个由节点和对象(包含属性和方法的对象)组成的结构集合。
一个 web 页面是一个文档。这个文档可以在浏览器窗口或作为 HTML 源码显示出来。但上述两个情况中都是同一份文档。文档对象模型(DOM)提供了对同一份文档的另一种表现,存储和操作的方式。DOM 是 web 页面的完全的面向对象表述,它能够使用如 JavaScript 等脚本语言进行修改。
DOM重要的数据类型
下面的表格简单则描述了这些数据类型。
document | 当一个成员返回 document 对象(例如,元素的 ownerDocument 属性返回它所属于 document ) ,这个对象就是 root document 对象本身。 DOM document Reference 一章对 document 对象进行了描述。 |
---|---|
element | element 是指由 DOM API 中成员返回的类型为 element 的一个元素或节点。例如, document.createElement() 方法会返回一个 node 的对象引用,也就是说这个方法返回了在 DOM 中创建的 element。 element 对象实现了 DOM Element 接口以及更基本的 Node 接口,参考文档将两者都包含在内。 |
text | element的文本内容,一定存储在element的子节点里 |
nodeList | nodeList 是一个元素的数组,如从 document.getElementsByTagName() 方法返回的就是这种类型。 nodeList 中的条目由通过下标有两种方式进行访问: |
• list.item(1) | |
• list[1]两种方式是等价的,第一种方式中 item() 是 nodeList 对象中的单独方法。 后面的方式则使用了经典的数组语法来获取列表中的第二个条目。 | |
attribute | 当 attribute 通过成员函数 (例如,通过 createAttribute()方法) 返回时,它是一个为属性暴露出专门接口的对象引用。DOM 中的属性也是节点,就像元素一样,只不过可能会很少使用它。 |
namedNodeMap | namedNodeMap 和数组类似,但是条目是由 name 或 index 访问的,虽然后一种方式仅仅是为了枚举方便,因为在 list 中本来就没有特定的顺序。出于这个目的, namedNodeMap 有一个 item() 方法,也可以从 namedNodeMap 添加或移除。 |
DOM 中核心接口
在 DOM 编程时,通常使用的最多的就是 Document
和 window
对象。简单的说, window
对象表示浏览器中的内容,而 document
对象是文档本身的根节点。Element
继承了通用的 Node
接口,将这两个接口结合后就提供了许多方法和属性可以供单个元素使用。在处理这些元素所对应的不同类型的数据时,这些元素可能会有专用的接口。
下面是在 web 和 XML 页面脚本中使用 DOM 时,一些常用的 API 简要列表。
-
document.getElementById(id)
document.getElementByIdvalue性质取值:JS允许我们通过
getElementById()
函数以id访问网页元素,但这个函数不会直接取值,需要以JS对象的形式提供HTML域内容,我们通过域的value性质访问数据document.getElementById("cakedonuts").value
-
document.getElementsByTagName(name)
document.getElementsByTagName返回一个包括所有给定标签名称的元素的 HTML 集合
HTMLCollection
。整个文件结构都会被搜索,包括根节点。返回的HTML 集合
是动态的,意味着它可以自动更新自己来保持和 DOM 树的同步而不用再次调用document.getElementsByTagName()
。document.getElementsByTagName(”img”)[3];//第4个<img>标签
-
createElement用于创建一个由标签名称 tagName指定的 HTML 元素。如果用户代理无法识别 tagName,则会生成一个未知 HTML 元素
document.body.onload = addElement; function addElement () { // 创建一个新的 div 元素 let newDiv = document.createElement("div"); // 给它一些内容 let newContent = document.createTextNode("Hi there and greetings!"); // 添加文本节点 到这个新的 div 元素 newDiv.appendChild(newContent); // 将这个新的元素和它的文本添加到 DOM 中 let currentDiv = document.getElementById("div1"); document.body.insertBefore(newDiv, currentDiv); }
-
Document.createTextNode()
创建一个文本节点。var text = document.createTextNode(data);//data 是一个字符串,包含了要放入文本节点的内容。
Node
**Node
**是一个接口,各种类型的 DOM API 对象会从这个接口继承。它允许我们使用相似的方式对待这些不同类型的对象;比如,继承同一组方法,或者用同样的方式测试。
Node属性
-
[Node.nodeValue]
返回或设置当前节点的值,只限文本与属性节点使用(不含元素)。document.getElementById("scenetext").nodeValue;
-
[Node.nodeType]
节点类型,返回与该节点类型对应的无符号短整型
的值,可能的值:Name Value ELEMENT_NODE 1 ATTRIBUTE_NODE 已弃用 2 TEXT_NODE 3 CDATA_SECTION_NODE 4 ENTITY_REFERENCE_NODE 已弃用 5 ENTITY_NODE 已弃用 6 PROCESSING_INSTRUCTION_NODE 7 COMMENT_NODE 8 DOCUMENT_NODE 9 DOCUMENT_TYPE_NODE 10 DOCUMENT_FRAGMENT_NODE 11 NOTATION_NODE 已弃用 12 -
Node.childNodes 包含节点下所有的子节点的数组,以出现在HTML代码中的顺序而排列,返回包含指定节点的子节点的集合,该集合为即时更新的集合(live collection)。
-
[Node.firstChild]
返回该节点第一个子节点[Node]
,如果该节点没有子节点则返回null
。 -
[Node.lastChild](
返回该节点最后一个子节点[Node]
,如果该节点没有子节点返回null
。
Node方法
-
[Node.removeChild()]
移除当前节点的一个子节点。这个子节点必须存在于当前节点中。// 移除一个元素节点的所有子节点 var element = document.getElementById("top"); while (element.firstChild) { element.removeChild(element.firstChild); }
-
[Node.appendChild()]
将指定的 childNode 参数作为最后一个子节点添加到当前节点。 如果参数引用了 DOM 树上的现有节点,则节点将从当前位置分离,并附加到新位置。// 创建一个新的段落元素 <p>,然后添加到 <body> 的最尾部 var p = document.createElement("p"); document.body.appendChild(p);
innerHTML
通过innerHTML 可以取得HTML内容类元素(div、span、p…)内存储的所有内容,包括HTML标签,如下面的案例所示,可以获取文字内容+strong标签及其内容,这与DOM方法不同。
<p id="story">
you are standing <strong>alone</strong> in the woods.
</p>
设置 innerHTML
的值可以让你轻松地将当前元素的内容替换为新的内容。举个例子来说,你可以通过文档 [body]
属性删除 body 的全部内容。
document.body.innerHTML = "";
只要把文字字符串指派给元素的innerHTML特性,元素内容即可设为HTML文本字符串。新内容将取代任何原本属于元素的内容。它本身没有附加功能,如果要实现附加的效果可以采用串联的方法将新内容加到旧内容上:
elem.innerHTML += "new content";
关键字this
this是Javascript语言的一个关键字,它代表函数运行时,自动生成的一个内部对象,只能在函数内部使用,随着函数使用场合的不同,this的值会发生变化,但是有一个总的原则,那就是this指的是调用函数的那个对象。
总结:谁调用了这个函数,this指向谁(对象)
this
在 类 中的表现与在函数中类似,因为类本质上也是函数,但也有一些区别和注意事项。
在类的构造函数中,this
是一个常规对象。类中所有非静态的方法都会被添加到 this
的原型中:
class Example {
constructor() {
const proto = Object.getPrototypeOf(this);
console.log(Object.getOwnPropertyNames(proto));
}
first(){}
second(){}
static third(){}
}
new Example(); // ['constructor', 'first', 'second']
// 对象可以作为 bind 或 apply 的第一个参数传递,并且该参数将绑定到该对象。
var obj = {a: 'Custom'};
// 声明一个变量,并将该变量作为全局对象 window 的属性。
var a = 'Global';
function whatsThis() {
return this.a; // this 的值取决于函数被调用的方式
}
whatsThis(); // 'Global' 因为在这个函数中 this 没有被设定,所以它默认为 全局/ window 对象
whatsThis.call(obj); // 'Custom' 因为函数中的 this 被设置为 obj
whatsThis.apply(obj); // 'Custom' 因为函数中的 this 被设置为 obj
function add(c, d) {
return this.a + this.b + c + d;
}
var o = {a: 1, b: 3};
// 第一个参数是用作“this”的对象
// 其余参数用作函数的参数
add.call(o, 5, 7); // 16
// 第一个参数是用作“this”的对象
// 第二个参数是一个数组,数组中的两个成员用作函数参数
add.apply(o, [10, 20]); // 34
原型链中的 this
对于在对象原型链上某处定义的方法,同样的概念也适用。如果该方法存在于一个对象的原型链上,那么 this
指向的是调用这个方法的对象,就像该方法就在这个对象上一样。
var o = {
f: function() {
return this.a + this.b;
}
};
var p = Object.create(o);
p.a = 1;
p.b = 4;
console.log(p.f()); // 5
这个例子中,对象 p
没有属于它自己的 f
属性,它的 f
属性继承自它的原型。虽然最终是在 o
中找到 f
属性的,这并没有关系;查找过程首先从 p.f
的引用开始,所以函数中的 this
指向p
。也就是说,因为f
是作为p
的方法调用的,所以它的this
指向了p
。这是 JavaScript 的原型继承中的一个有趣的特性。
getter 与 setter 中的 this
再次,相同的概念也适用于当函数在一个 getter
或者 setter
中被调用。用作 getter
或 setter
的函数都会把 this
绑定到设置或获取属性的对象。
function sum() {
return this.a + this.b + this.c;
}
var o = {
a: 1,
b: 2,
c: 3,
get average() {
return (this.a + this.b + this.c) / 3;
}
};
Object.defineProperty(o, 'sum', {
get: sum, enumerable: true, configurable: true});
console.log(o.average, o.sum); // logs 2, 6
作为构造函数
当一个函数用作构造函数时(使用new关键字),它的this
被绑定到正在构造的新对象。
虽然构造函数返回的默认值是 this
所指的那个对象,但它仍可以手动返回其他的对象(如果返回值不是一个对象,则返回 this
对象)。
/*
* 构造函数这样工作:
*
* function MyConstructor(){
* // 函数实体写在这里
* // 根据需要在 this 上创建属性,然后赋值给它们,比如:
* this.fum = "nom";
* // 等等...
*
* // 如果函数具有返回对象的 return 语句,
* // 则该对象将是 new 表达式的结果。
* // 否则,表达式的结果是当前绑定到 this 的对象。
* //(即通常看到的常见情况)。
* }
*/
function C(){
this.a = 37;
}
var o = new C();
console.log(o.a); // logs 37
function C2(){
this.a = 37;
return {a:38};
}
o = new C2();
console.log(o.a); // logs 38
在刚刚的例子中(C2
),因为在调用构造函数的过程中,手动的设置了返回对象,与this
绑定的默认对象被丢弃了。(这基本上使得语句“this.a = 37;
”成了“僵尸”代码,实际上并不是真正的“僵尸”,这条语句执行了,但是对于外部没有任何影响,因此完全可以忽略它)。
作为一个 DOM 事件处理函数
当函数被用作事件处理函数时,它的 this
指向触发事件的元素(一些浏览器在使用非 addEventListener
的函数动态地添加监听函数时不遵守这个约定)。
// 被调用时,将关联的元素变成蓝色
function bluify(e){
console.log(this === e.currentTarget); // 总是 true
// 当 currentTarget 和 target 是同一个对象时为 true
console.log(this === e.target);
this.style.backgroundColor = '#A5D9F3';
}
// 获取文档中的所有元素的列表
var elements = document.getElementsByTagName('*');
// 将 bluify 作为元素的点击监听函数,当元素被点击时,就会变成蓝色
for(var i=0 ; i<elements.length ; i++){
elements[i].addEventListener('click', bluify, false);
}
作为一个内联事件处理函数
当代码被内联 on-event 处理函数 (en-US) 调用时,它的this
指向监听器所在的 DOM 元素:
<button onclick="alert(this.tagName.toLowerCase());">
Show this
</button>
上面的 alert 会显示 button
。注意只有外层代码中的 this
是这样设置的:
<button onclick="alert((function(){return this})());">
Show inner this
</button>
在这种情况下,没有设置内部函数的 this
,所以它指向 global/window 对象(即非严格模式下调用的函数未设置 this
时指向的默认对象)。
类中的 this
和其他普通函数一样,方法中的 this
值取决于它们如何被调用。有时,改写这个行为,让类中的 this
值总是指向这个类实例会很有用。为了做到这一点,可在构造函数中绑定类方法:
class Car {
constructor() {
// Bind sayBye but not sayHi to show the difference
this.sayBye = this.sayBye.bind(this);
}
sayHi() {
console.log(`Hello from ${this.name}`);
}
sayBye() {
console.log(`Bye from ${this.name}`);
}
get name() {
return 'Ferrari';
}
}
class Bird {
get name() {
return 'Tweety';
}
}
const car = new Car();
const bird = new Bird();
// The value of 'this' in methods depends on their caller
car.sayHi(); // Hello from Ferrari
bird.sayHi = car.sayHi;
bird.sayHi(); // Hello from Tweety
// For bound methods, 'this' doesn't depend on the caller
bird.sayBye = car.sayBye;
bird.sayBye(); // Bye from Ferrari
涉及css样式要点
-
<style>包含文档的样式信息或者文档的部分内容。默认情况下,该标签的样式信息通常是CSS的格式。
type:该属性以 MIME 类型(不应该指定字符集)定义样式语言。如果该属性未指定,则默认为
text/css
。 -
字重 font-weightCSS属性指定了字体的粗细程度。一些字体只提供
normal
和bold
两种值。/* Keyword values */ font-weight: normal; font-weight: bold; /* Keyword values relative to the parent */ font-weight: lighter; font-weight: bolder; /* Numeric keyword values */ font-weight: 1 font-weight: 100; /* Global values */ font-weight: inherit; font-weight: initial; font-weight: unset;
-
边框 borderCSS的 **
border
**属性是一个用于设置各种单独的边界属性的简写属性。border
可以用于设置一个或多个以下属性的值:border-width、[border-style](<https://developer.mozilla.org/zh-CN/docs/Web/CSS/border-style>)
、[border-color](<https://developer.mozilla.org/zh-CN/docs/Web/CSS/border-color>)
。/* style */ border: solid; /* width | style */ border: 2px dotted; /* style | color */ border: outset #f33; /* width | style | color */ border: medium dashed green; /* Global values */ border: inherit; border: initial; border: unset;
-
间距
-
内间距 paddingCSS 简写属性控制元素所有四条边的内边距区域。
/* 应用于所有边 */ padding: 1em; /* 上边下边 | 左边右边 */ padding: 5% 10%; /* 上边 | 左边右边 | 下边 */ padding: 1em 2em 2em; /* 上边 | 右边 | 下边 | 左边 */ padding: 5px 1em 0 2em; /* 全局值 */ padding: inherit; padding: initial; padding: unset;
-
外间距 margin为给定元素设置所有四个(上下左右)方向的外边距属性
/* 应用于所有边 */ margin: 1em; margin: -3px; /* 上边下边 | 左边右边 */ margin: 5% auto; /* 上边 | 左边右边 | 下边 */ margin: 1em auto 2em; /* 上边 | 右边 | 下边 | 左边 */ margin: 2px 1em 0 auto; /* 全局值 */ margin: inherit; margin: initial; margin: unset; margin: 5%; /* 所有边:5% 的外边距 */ margin: 10px; /* 所有边:10px 的外边距 */ margin: 1.6em 20px; /* 上边和下边:1.6em 的外边距 */ /* 左边和右边:20px 的外边距 */ margin: 10px 3% -1em; /* 上边:10px 的外边距 */ /* 左边和右边:3% 的外边距 */ /* 下边: -1em 的外边距 */ margin: 10px 3px 30px 5px; /* 上边:10px 的外边距 */ /* 右边:3px 的外边距 */ /* 下边:30px 的外边距 */ /* 左边:5px 的外边距 */ margin: 2em auto; /* 上边和下边:2em 的外边距 */ /* 水平方向居中 */ margin: auto; /* 上边和下边:无外边距 */ /* 水平方向居中 */
-
注意事项
- 当只指定一个值时,该值会统一应用到全部四个边的边距上。
- 指定两个值时,第一个值会应用于上边和下边的边距,第二个值应用于左边和右边。
- 指定三个值时,第一个值应用于上边,第二个值应用于右边和左边,第三个则应用于下边的边距。
- 指定四个值时,依次(顺时针方向)作为上边,右边,下边,和左边的边距。
-
-
显示隐藏效果
-
visibility样式特性:显示或隐藏元素而不更改文档的布局。该属性还可以隐藏
[<table>]
中的行或列。/* Keyword values */ visibility: visible; visibility: hidden; visibility: collapse; /* Global values */ visibility: inherit; visibility: initial; visibility: unset;
visible
元素正常显示。hidden
隐藏元素,但是其他元素的布局不改变,相当于此元素变成透明。要注意若将其子元素设为visibility: visible
,则该子元素依然可见。collapse
关键字对于不同的元素有不同的效果: • 用于[<table>]
行、列、列组和行组,隐藏表格的行或列,并且不占用任何空间(与将[display]: none
用于表格的行/列上的效果相当)。但是,计算其他行和列的大小时,仍会像显示折叠行或列中的单元格一样进行计算。此值允许从表中快速删除行或列,而不强制重新计算整个表的宽度和高度。 • 折叠的弹性元素和 ruby 元素会被隐藏,它们本来将要占用的空间会被移除。 • 对于其他元素,折叠处理与隐藏相同。 -
display样式特性
CSS
display
属性设置元素是否被视为块或者内联元素以及用于子元素的布局,例如流式布局、网格布局或弹性布局。形式上,
display
属性设置元素的内部和外部的显示类型。外部类型设置元素参与流式布局;内部类型设置子元素的布局。一些display
值在它们自己的单独规范中完整定义;例如,在 CSS 弹性盒模型的规范中,定义了声明display: flex
时会发生的细节。/* precomposed values */ display: block; display: inline; display: inline-block; display: flex; display: inline-flex; display: grid; display: inline-grid; display: flow-root; /* box generation */ display: none; display: contents; /* two-value syntax */ display: block flow; display: inline flow; display: inline flow-root; display: block flex; display: inline flex; display: block grid; display: inline grid; display: block flow-root; /* other values */ display: table; display: table-row; /* all table elements have an equivalent CSS display value */ display: list-item; /* Global values */ display: inherit; display: initial; display: revert; display: revert-layer; display: unset;
-
其他知识点
-
id传参时,构造函数中不能加引号,但是要在调用函数中加引号,这是由于构造函数中的参数需要是一个变量,如果加了引号就变成字符串及固定的id文字了,那样不符合调用的逻辑
-
className 特性对元素样式进行访问,获取或设置指定元素的 class 属性的值。
let cName = elementNodeReference.className; elementNodeReference.className = cName;
-
鼠标事件
-
onmouseover当鼠标移动到一个元素上时,会在这个元素上触发 mouseover 事件。
element.onmouseover = event handling code
-
onmouseout当鼠标离开一个元素上时,会在这个元素上触发 onmouseout 事件。
<!doctype html> <html> <head> <title>onmouseover/onmouseout event example</title> <script type="text/javascript"> function initElement() { var p = document.getElementById("foo"); p.onmouseover = showMouseOver; p.onmouseout = showMouseOut; }; function showMouseOver() { var notice = document.getElementById("notice"); notice.innerHTML = '检测到鼠标移进'; } function showMouseOut() { var notice = document.getElementById("notice"); notice.innerHTML = '检测到鼠标移出'; } </script> <style type="text/css"> #foo { border: solid blue 2px; } </style> </head> <body onload="initElement()";> <span id="foo">移动鼠标,在该元素上移进移出</span> <div id="notice"></div> </body> </html>
-
-
switch评估一个表达式,将表达式的值与
case
子句匹配,并执行与该情况相关联的语句。switch (expression) { case value1: // 当 expression 的结果与 value1 匹配时,执行此处语句 [break;] case value2: // 当 expression 的结果与 value2 匹配时,执行此处语句 [break;] ... case valueN: // 当 expression 的结果与 valueN 匹配时,执行此处语句 [break;] [default: // 如果 expression 与上面的 value 值都不匹配,执行此处语句 [break;]] }
一个 switch 语句首先会计算其 expression。然后,它将从第一个 case 子句开始直到寻找到一个其表达式值与所输入的 expression 的值所相等的子句(使用 严格运算符 (en-US),
===
)并将控制权转给该子句,执行相关语句。(如果多个 case 与提供的值匹配,则选择匹配的第一个 case,即使这些 case 彼此间并不相等。)如果没有
case
子句相匹配,程序则会寻找那个可选的default
子句,如果找到了,将控制权交给它,执行相关语句。若没有default
子句,程序将继续执行直到switch
结束。按照惯例,default
子句是最后一个子句,不过也不需要这样做。可选的
[break]
语句确保程序立即从相关的 case 子句中跳出 switch 并接着执行 switch 之后的语句。若break
被省略,程序会继续执行switch
语句中的下一条语句。
案例:一个简单的场景选择小游戏
<html>
<head>
<title></title>
<style>
span.decision{
font-weight: bold;
background-color: aqua;
border: thin solid;
padding: 5px;
margin: 5px;
}
span.decisionhover{
font-weight: bold;
color: #ffffff;
background-color: #000000;
border: thin solid #dddddd;
padding: 5px;
margin: 5px;
}
</style>
<script type="text/javascript">
var curScene = 0;
/* 用DOM方法+函数实现动态替换文字 */
function replaceNodeText(id, newText){
var node = document.getElementById(id);
while (node.firstChild){
node.removeChild(node.firstChild);
}
node.appendChild(document.createTextNode(newText));
}
function changeScene(decision)
{
var message = "";
var decision1 = "", decision2 = "";
switch(curScene){
case 0:
curScene = 1;
message = "Your journey begins at a fork in the road.";
decision1 = "Take the Path";
decision2 = "Take the Bridge";
document.getElementById("decision2").style.visibility = "visible";
break;
case 1:
if (decision == 1) {
curScene = 2
message = "You have arrived at a cute little house in the woods.";
decision1 = "Walk around Back";
decision2 = "Knock on Door";
}
else {
curScene = 3;
message = "You are standing on the bridge overlooking a peaceful stream.";
decision1 = "Walk across Bridge";
decision2 = "Gaze into Stream";
}
break;
case 2:
if (decision == 1) {
curScene = 4
message = "Peeking through the window, you see a witch inside the house.";
decision1 = "Sneak by Window";
decision2 = "Wave at Witch";
}
else {
curScene = 5;
message = "Sorry, a witch lives in the house and you just became part of her stew.";
decision1 = "Start Over";
decision2 = "";
document.getElementById("decision2").style.visibility = "hidden";
}
break;
case 3:
if (decision == 1)
{
curScene = 6;
message = "Sorry, a troll lives on the other side of the bridge and you just became his lunch.";
decision1 = "Start Over";
decision2 = "";
document.getElementById("decision2").style.visibility = "hidden";
}
else
{
curScene = 7;
message = "Your stare is interrupted by the arrival of a huge troll.";
decision1 = "Say Hello to Troll";
decision2 = "Jump into Stream";
}
break;
case 4:
if (decision == 1)
{
curScene = 8;
decision1 = "?";
decision2 = "?";
}
else
{
curScene = 5;
message = "Sorry, you became part of the witch's stew.";
decision1 = "Start Over";
decision2 = "";
document.getElementById("decision2").style.visibility = "hidden";
}
break;
case 5:
curScene = 0;
decision1 = "Start Game";
decision2 = "";
document.getElementById("decision2").style.visibility = "hidden";
break;
case 6:
curScene = 0;
decision1 = "Start Game";
decision2 = "";
document.getElementById("decision2").style.visibility = "hidden";
break;
case 7:
if(decision == 1)
{
curScene = 6;
message = "Sorry,you became the troll's tasty lunch.";
decision1 = "Start Over";
decision2 = "";
document.getElementById("decision2").style.visibility = "hidden";
}
else
curScene = 9;
decision1 = "?";
decision2 = "?";
break;
case 8:
break;
case 9:
break;
}
document.getElementById("sceneimg").src = "scene" + curScene + ".png";
replaceNodeText("scenetext",message);
replaceNodeText("decision1",decision1);
replaceNodeText("decision2",decision2);
//显示决策路径历史
var history = document.getElementById("history");
if (curScene != 0){
var decisionElem = document.createElement("p");
decisionElem.appendChild(document.createTextNode("Decision" + decision + "-> Scene" + curScene + ":" + message));
history.appendChild(decisionElem);
}
else{
while(history.firstChild)
history.removeChild(history.firstChild);
}
/* 用DOM方法实现
var sceneText = document.getElementById("scenetext");
while (sceneText.firstChild){
sceneText.removeChild(sceneText.firstChild);
}
sceneText.appendChild(document.createTextNode(message));
*/
/* 用innerHTML方法实现在页面内显示场景描述信息
var sceneDesc;
if(message)
//alert(message);
sceneDesc = document.getElementById("scenetext").innerHTML = message;
*/
}
</script>
</head>
<body>
<div style="margin-top:100px; text-align:center">
<img id="sceneimg" src="scene0.png" alt="Stick Figure Adventure"/>
<br/>
<div id="scenetext"></div><br/>
Please choose:
<!-- 用span标签来实现同行显示的动态文字按钮 -->
<span id="decision1" class="decision" onclick="changeScene(1)" onmouseover=" this.className = 'decisionhover'" onmouseout=" this.className = 'decision'">Start Game!</span>
<span id="decision2" class="decision" onclick="changeScene(2)" onmouseover=" this.className = 'decisionhover'" onmouseout=" this.className = 'decision'" style="visibility:hidden"></span>
<!-- 用input实现按钮,但无法实现动态按钮上面的信息提示
<input type="button" id="decision1" value="1" onclick="changeScene(1)"/>
<input type="button" id="decision2" value="2" onclick="changeScene(2)"/>
-->
<div id="history"></div>
</div>
</body>
</html>