[JavaScript高级程序设计]BOM

目录

1 Window对象

1.1 全局作用域

1.2 窗口关系及框架

1.3 窗口位置

1.4 窗口大小

1.5 导航和打开窗口

1.5.1 弹出窗口

1.5.2弹出窗口屏蔽程序

1.6 间歇调用和超时调用

超时调用:

间歇调用:

1.7 系统对话框

2 location对象

位置方法

3 navigator对象

3.1 监测插件

3.2 注册处理程序

4 screen对象

5 history对象


1 Window对象

window对象具有双重角色,它既是JavaScript访问浏览器窗口的一个接口,又是ECMAScript规定的Global对象。

1.1 全局作用域

所有在全局作用域重声明的变量、函数都会变成window对象的属性和方法。但是定义全局变量和在window对象上直接定义属性十有一点区别的:全局变量不能通过delete删除,而直接在window对象上定义的属性可以。(IE8之后)。

常事访问未声明的变量会抛出错误,但通过window对象可以知道某个可能未声明的变量是否存在。

1.2 窗口关系及框架

每个框架都有自己的window对象,并且保存在frames集合中。在frames集合中可以通过数值索引(从0开始,从左到右,从上到下)或者是框架名称来访问相应的window随想。每个window对象都有一个name属性,其中包含框架的名称。

<html>
    <head>
        <title>Frameset Example</title>
        <frameset rows="160,*">
            <frame src="frame.htm" name="topFrame">
            <frameset cols="50%,50%">
                <frame src="leftFrame.htm" name="leftFrame">
                <frame src="rightFrame.htm" name="rightFrame">
            </frameset>
        </frameset>
    </head>
</html>

以上代码创建了一个框架集,其中一个框架居上,两个框架居下。可以通过window.frames[0]或window.frames["topFrame"]来引用上方框架。但最好使用top来引用。

top对象始终指向最高(最外)层的框架,也就是浏览器窗口,他可以确保在一个框架中正确的访问另一个框架。

与top相对应的另一个window对象是parent。parent(父)对象始终指向当前框架的直接上层框架。在某些情况下,parent有可能等于top,在没有框架的情况下,parent一定等于top。

/*rightFrame.htm*/
<html>
    <head>
        <title>RightFrame</title>
        <frameset cols="50%,50%">
            <frame src="red.htm" name='redFrame'>
            <frame src="blue.htm" name="blueFrame".>
        </frameset>
    </head>
</html>

浏览器在加载完第一个框架集之后,会继续将第二个框架集加载到rightFrame中。若代码位于redFrame中,则parent对象指向的就是rightFrame;若代码位于topFrame中,则parent对象指向的就是top。

注:除非窗口是通过window.open()打开的,否则window对象的name属性不会有任何值。

1.3 窗口位置

IE,Safari,Chrome,Opera中提供了screenLeft和screenTop属性,分别表示窗口相对于屏幕左边和上边的位置。Firefox则提供了screenX和screenY属性,提供相同的窗口位置信息。故可使用以下方法实现跨浏览器取得窗口左边和上边的位置。

var leftPos = (typeof window.screenLeft === 'number') ? window.screenLeft : window.screenX;
var topPos = (typeof window.screenTop === 'number') ? window.screenTop : window.screenY;

使用moveTo()和moveBy()方法可以将窗口精确地移动到一个新的位置。这两个方法都接收两个参数:其中moveTo()接受的是新位置的x和y坐标值,而moveBy()方法接受的是水平和垂直方向上移动的像素数。这两个方法都不是用于框架,只能对最外层window对象使用,且可能会被浏览器禁用。

1.4 窗口大小

IE9+,Firefox,Safari,Opera和Chrome都提供了4个属性:innerWidth,innerHeight,outerWidth,outerHeight。其中innerWidth和innerHeight表示页面视图区的大小。

在IE,Firefox,Safari,Opera和Chrome中,document.documentElement.clientWidth和document.documentElement.clientHeight中保存了页面视口的信息。在IE6中,这些属性必须在标准模式下才有效;如果是混杂模式,就必须通过document.body.clientWidth和document.body.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;
        pageHeight = document.body.clientHeight;
    }
}

在不考虑IE6及之前的IE浏览器兼容问题时,使用

var pageWidth = window.innerWidth || document.documentElement.cliengWidth;
var pageHeight = window.innerHeight || document.documentElement.clientHeight;

使用resizeTo()和resizeBy()可以调整浏览器窗口大小。这两个方法都接收两个参数。其中,resizeTo()接收浏览器窗口的新宽度和新高度,resizeBy()方法接收新窗口与元窗口的宽度和高度之差。这两个方法不适用于框架,仅适用于最外层的window对象,且有可能被浏览器屏蔽。

1.5 导航和打开窗口

使用window.open()方法既可以导航到一个特定的url,也可以打开一个新的窗口。这个方法接受4个参数:要加载的url,窗口目标,一个特性字符串,一个表示新页面是否取代浏览器中当前加载页面的布尔值。通常只需传递第一个参数,最后一个参数仅在不大开心窗口的条件下有效。

1.5.1 弹出窗口

如果给window.open()传入的第二个参数不是一个已经存在的窗口或框架,那个该方法会根据第三个位置桑德字符串创建一个新的窗口或标签页。在不打开新窗口的情况下,第三个参数无效。

window.open()会返回一个指向新窗口的引用。

close()方法,仅适用于通过window.open()打开的弹出窗口。

1.5.2弹出窗口屏蔽程序

大多数浏览器都内只有弹出窗口屏蔽程序,没有内置此类程序的浏览器也可以安装带有内置屏蔽程序的实用工具。如果是浏览器内置的屏蔽程序阻止了窗口的弹出,则window.open()很可能会返回null;如果是浏览器拓展或其他程序组织了弹出窗口,那么window.open()会抛出错误。股监测弹出窗口是否被屏蔽,使用以下代码

var newWindow = window.open("http://www.wrox.com","_blank"),
    blocked = false;
try{
    if(newWindow === 'null'){
        blocked = true;
    }
}catch(ex){
    blocked = true;
}

if(blocked){
    alert("The popup was blocked!");
}

1.6 间歇调用和超时调用

JavaScript是单线程的语言,但它允许通过设置超时值和间歇时间值来调度代码在特定时刻执行。超时值是在指定的时间过后执行代码,间歇时间值是每隔指定的时间就调用一个代码。

超时调用:

window的setTimeout()方法,接收两个参数:要执行的代码,以毫秒表示的时间。

第二个参数表示等待多长时间的毫秒数,但经过该时间后指定的代码不一定会执行。JavaScript是一个单线程的解释器,因此在一定的时间内只能执行一段代码,为了控制要执行的代码,就有一个JavaScript任务队列,这些任务会按照将它们添加到队列中的顺序执行。setTimeout()的第二个参数告诉JavaScript过多长时间后把当前任务添加到任务队列中。若队列为空,则添加的代码会立刻执行;若队列不为空,则要等到前面的代码执行完毕后,新添加的代码才会执行。

调用setTimeout()方法后会返回一个数值ID,表示超时调用,可以通过他来取消超时调用

间歇调用:

window的setInterval()方法,接收两个参数:要执行的代码,每次执行之前需要等待的毫秒数。它会按照指定的时间间隔重复执行代码,知道间歇调用被取消或者页面被卸载。

调用setInterval()方法也会返回一个数值ID,用于在将来某个时刻取消间歇调用

1.7 系统对话框

浏览器通过alert(),confirm()和prompt()方法可以调用系统对话框向用户显示消息。通过这几个方法打开的对话框都是同步和模态的,即显示这些对话框的时候代码会停止执行,而关掉这些对话框后又恢复执行。

2 location对象

是最有用的BOM对象之一,提供了与当前窗口中加载的文档有关的信息,还提供了一些导航功能。事实上,location对象是一个特殊的对象,因为它既是window对象的属性,也是document对象的属性。以下是location对象的所有属性:

属性名 例子 说明
hash "#content" 返回URL中的hash
host "www.wrox.com:8080" 返回服务器名称和端口号
hostname "www.wrox.com" 返回不带端口号的服务器名称
port "8080" 返回URL中指定的端口号
href "http://www.wrox.com" 返回当前加载页面的URL
pathname "/WileyCDA" 返回URL中的目录和(或)文件名
protocal "http:" 返回页面使用的协议
search "?q=javascript" 返回URL的查询字符串

位置方法

使用location对象可以通过很多方式来改变浏览器的位置。

使用assign()方法并为其传递一个URL。这样就可以立即打开新URL并在浏览器的历史记录中生成一条新的历史记录,如果将location.href或者window.location设置为一个URL,则在后台调用location.assign()方法。

每次修改location的属性(除hash外),页面都会以新URL重新加载。任何一种方式修改URL后,都会在历史记录中生成一条新的记录。若想不生成记录,则使用replace()方法。这个方法接收一个参数,既要导航到的URL,结果虽然会导致浏览器的位置改变,但不会在历史记录中生成新的记录。在使用replace()方法后,用户无法回到前一页面。

最后一个方法是reload(),作用是重新加载当前显示的页面。如果调用reload()是不传入参数,则页面会以最有效的方式加载。要想从服务器中加载页面,则需向reload()方法中传入参数true。

3 navigator对象

识别客服端浏览器。

3.1 监测插件

检测浏览器中是否安装了特定的插件是一种最常见的检测例程。对非IE浏览器,可以使用plugins数组达到这个目的。该数组包含以下几项

  • name:插件的名称
  • description:插件的描述
  • filename:插件的文件名
  • length:插件所处理的MIME类型数量

检测插件方法(非IE中)

function hasPlugins(name){
    name = name.toLowerCase();
    for(let i=0;i<navigator.plugins.length;i++){
        if(navigator.plugins[i].name.toLowerCase().indexOf(name) > -1){
            return true;
        }
    }
    return false;
}

在 IE中检测插件的唯一方式就是使用专有的ActiveXObject类型,并尝试创建一个特定插件的实例。IE是以COM对象的方式实现插件的,而COM对象使用唯一的表述符来标识。因此,想要检测特定的插件,就必须知道其COM标识符。例如,Flash的标识符就是ShockWaveFlash.ShockWaveFlash。

检测方法(IE)

function hasIEPlugin(name){
    try{
        new ActiveXObject(name);
        return true;
    }catch(ex){
        return false;
    }
}

鉴于以上两种检测插件的方式差别较大,故典型做法是:针对每个插件分别创建检测函数。

//检测所有浏览器中的Flash
function hasFlash(){
    var result = hasPlugin("Flash");
    if(!result){
        result = hasIEPlugin("ShockWaveFlash.ShockWaveFlash");
    }
    return result;
}

//检测所有浏览器中的QuickTime
function hasQuickTime(){
    var result = hasPlugin("QuickTime");
    if(!result){
        result = hasIEPlugin("QuickTime.QuickTime");
    }
    return result;
}

3.2 注册处理程序

Firefox2为navigator对象新增了registerContentHandler()和registerProtocolHandler()方法。这两个方法可以让一站点知名他可以处理特定类型的信息。

registerContentHandler()方法接收3个参数:要处理的MIME类型,可以处理该MIME类型的页面的URL已经应用程序的名字。

registerProtocolHandler()方法也接受3个参数:要处理掉的协议,处理该协议的页面的URL,应用程序的名字。

4 screen对象

screen对象基本上只用来表明客户端的能力,其中包含浏览器窗口外部的显示器信息。

5 history对象

history对象保存着用户上网的历史记录,从窗口被打开的那一刻算起。

使用go()方法可以再用户的的历史记录中随意跳转,可以向前也可以向后。方法接收一个参数,表示向前或向后跳转的一个整数值。负数表示向后跳转,正数表示向前跳转。野结衣给go()方法传入一个字符串,此时浏览器会跳转到历史记录中包含该字符串的第一个位置。

使用back()方法和forward()来代替go()方法,模仿浏览器的“向后”和“向前”操作。

history对象还有一个length属性,保存着历史记录的数量。对于加载到窗口,标签页或框架中的第一个页面而言,history的length等于0.

猜你喜欢

转载自blog.csdn.net/Liwen_Ye/article/details/81477242