ECMAScript是JavaScript的核心,但如果要在WEB中使用JavaScript,那么BOM则无疑才是真正的核心。
BOM提供了很多对象,用于访问浏览器的功能,这些功能与任意网页内容无关。
W3C为了把浏览器中JavaScript最基本的部分标准化,已经将BOM的主要方面纳入了HTML5的规范中。
8.1 window对象
BOM的核心对象是window。它表示浏览器的一个实例。在浏览器中,window对象有双重角色,它既是通过JavaScript访问浏览器窗口的一个接口,又是ECMAScript规定的Global对象,因此有权访问parseInt()等方法。
8.1.1 全局作用域
由于window对象同时扮演者ECMAScript中Global对象的角色,因此所有在全局作用域中声明的变量、函数都会变成window对象的属性和方法。来看下面的例子
var age=29; function sayAge(){ alert(this.age); } alert(window.age); //29 sayAge(); //29 window.sayAge(); //29
我们在全局作用域中定义了一个变量age和一个函数sayAge(),它们被自动归在了window对象名下。于是,可以通过window.age访问变量age,可以通过window.sayAge()访问函数sayAge()。由于sayAge()存在于全局作用域中,因此this.age被映射到window.age,最终显示的仍然是正确的结果。
抛开全局变量会变成为window对象的属性不谈,定义全局变量与在window对象上直接定义属性还是有一点差别:全局变量不能通过delete操作符删除,而直接在window对象上定义的属性可以。例如:
window.color="red"; //在IE<9时抛出错误,在其他浏览器返回false delete window.age; //在IE<9时抛出错误,在其他浏览器返回true delete window.color; alert(window.age); //29 alert(window.color); //undefined
使用var语句添加的window属性有一个名为[[Configurable]]的特性,这个特性的值被设置为false,因此这样定义的属性不可以通过delete操作符删除。
8.1.2 窗口关系及框架
如果页面中包含框架,则每个框架都拥有自己的window对象,并且保存在frames集合中。在frames集合中,可以通过数值索引(从0开始,从左至右,从上至下)或者框架名称来访问相应的window对象。每个window对象都有一个name属性,其中包含框架名称。下面是一个包含框架的页面:
frameset 元素可定义一个框架集。它被用来组织多个窗口(框架)。每个框架存有独立的文档。在其最简单的应用中,frameset 元素仅仅会规定在框架集中存在多少列或多少行。您必须使用 cols 或 rows 属性。
重要事项:您不能与 <frameset></frameset> 标签一起使用 <body></body> 标签。不过,如果您需要为不支持框架的浏览器添加一个 <noframes> 标签,请务必将此标签放置在 <body></body> 标签中!
以上代码创建了一个框架集,其中一个框架居上,两个框架居下。对于这个例子而言,可以通过window.frames[0]或者window.frames["topFrame"]来引用上方的框架。不过最好还是使用top而非winodw来引用这些框架(例如,通过top.frames[0])。
top对象始终指向(最外层)的框架,也就是浏览器窗口。使用它可以确保在一个框架中正确地访问另一个框架。因为对于在一个框架中编写的任何代码来说,其中的window对象指向的都是那个框架的特定实例,而非最外层框架。
与top相对的另一个window对象是parent。parent(父)对象始终指向当前框架的直接上层框架。在某些情况下,parent有可能等于top;但在没有框架的情况下,parent一定等于top(此时它们都等于window)。
注意,除非最高层窗口是通过window.open()打开的,否则其window对象的name属性不会包含任何值。
与框架有关的最后一个对象是self,它始终指向window;实际上,self和window对象可以互换使用。引入self对象的目的只是为了与top和parent对象对应起来,因此它不格外包含其他值。
所有这些对象都是window对象的属性,可以通过window.parent.parent.frames[0]。
8.1.3 窗口位置
用来确定和修改window对象位置的属性方法很多。
IE,Safari,Opera和Chrome都提供了screenLeft和screenTop属性,分别表示窗口相对于屏幕左边和上边的位置。
Firefox则在screenX和screenY属性提供相同的窗口位置信息。Safari和Chrome也支持这两个属性。
Opera虽然也支持screenX和screenY属性,但是具有的功能却是其他的,因此不建议在Opera使用这两个属性。
使用下列代码可以跨浏览器取得窗口左边和上边的位置
var leftPos=(typeof window.screenLeft=="number")?window.screenLeft:window.screenX; var topPos=(typeof window.screenTop=="number")?window.screenTop:window.screenY;
8.1.4 窗口大小
跨浏览器确认一个窗口的大小不是一件容易的事情。IE9+,Firefox,Safari,Opera和Chrome均为此提供了4个属性:
innerWidth,innerHeight,outerWidth和outerHeight。
在IE9+,Firefox和Safari中,outerWidth和outerHeight返回浏览器窗口本身尺寸(无论是从最外层的window对象还是从某个框架访问)
在Opera中,outerWidth和outerHeight表示页面视图容器的大小。而innerWidth和innerHeight则表示该容器中页面视图区的大小(减去边框宽度)。
在Chrome中,outerWidth、outerHeigh与innerWidth与innerHeight返回相同的值,即视图大小而非浏览器窗口大小。
在IE,Firefox,Safari,Opera和Chrome中,document.documentElement.clientWidth和document.documentElement.clientHeight中保存了页面视口的信息。在IE6中,这些属性必须在标准模式下才有效;如果是混杂模式,就必须通过document.body.clientWidth和document.body.clientHeight取得相同信息。而对于混杂模式下的Chrome,则无论通过document。documentElement还是document.body中的clientWidth和clientHeight属性,都可以取得视口的大小。
虽然最终无法确定浏览器窗口本身的大小,但却可以取得页面视口的大小,如下所示。
var pageWidth=window.innerWidth; var pageHeight=window.innerHeight; if(typeof pageWidth!="number"){ if(document.compatMode=="CSS1Compat") //标准模式 { pageWidth=document.documentElement.clientWidth; pageHeight=document.documentElement.clientHeight; }else{ pageWidth=document.body.clientWidth; onpagehide=document.body.clientHeight; } }
使用resizeTo()和resizeBy()方法可以调整浏览器窗口的大小。这两个方法都接收两个参数,其中resizeTo()接收浏览器窗口的新宽度和新高度。而resizeBy()接收新窗口与原窗口的宽度与高度之差。
8.1.5 导航和打开窗口
使用window.open()方法既可以导航到一个特定的URL,也可以打开一个新的浏览器窗口。
这个方法可以接收4个参数:
①要加载的URL
②窗口目标
③一个特性字符串
④一个表示新页面是否取代浏览器历史记录中当前加载页面的布尔值。
通常只须传递第一个参数,最后一个参数只在不打开新窗口的情况下使用。
如果为window.open()传递了第二个参数,而且该参数是已有窗口或框架的名称,那么就会在具有该名称的窗口或框架中加载第一个参数指定的URL。请看下面例子
window.open("http://www.wrox.com","topFrame"); //等价于<a href="http://www.wrox.com" target="topFrame"></a>
如果有一个名为“topFrame”的窗口或者框架,就会在该窗口或框架加载这个URL;否则,就会创建一个新窗口并将其命名为“topName”。此外,第二个参数也可以是下列任何一个特殊的窗口名称:_self,_parent,_top或_blank.
1.弹出窗口
如果给window.open()传递的第二个参数并不是一个已经存在的窗口或框架,那么该方法就会根据在第三个参数位置上传入的字符串创建一个新窗口或新标签页。如果没有传入第三个参数,那么就会打开一个带有全部默认设置(工具栏、地址栏、状态栏)的新浏览器窗口(或者打开一个新标签页---根据浏览器设置)。在不打开新窗口的情况下,会忽略第三个参数。
window.open("http://www.wrox.com/","wroxWindow","height=400,width=400,top=10,left=10,resizable=yes");
这行代码会打开一个新的可以调整大小的窗口。窗口初始大小为400*400像素,并且距屏幕上沿和左边各10像素。
window.open()会返回一个指向新窗口的引用。引用的对象与其他window对象大致相似。但我们可以对其进行更多控制。例如,有些浏览器在默认情况下可能不允许我们针对主浏览器窗口调整大小或移动位置,但却允许我们针对通过window.open()创建的窗口调整大小或移动位置。通过这个返回的对象,可以像操作其他窗口一样操作新打开的窗口,如下所示
var wroxWin=window.open("http://www.wrox.com/","wroxWindow","height=400,width=400,top=10,left=10,resizable=yes"); //调整大小 wroxWin.resizeTo(500,500); //移动位置 worxWin.moveTo(100,100); //关闭窗口 wroxWin.close();