DOM之parentNode与offsetParent
DOM中有两个属性parentNode和offsetParent,想必区别大家都是知道的,可用法上还是有一些需要注意的地方,尤其是后者,想知道吗?继续往下看咯。
parentNode指的是父节点,element.parentNode,获取某一个元素的父节点,这里的父节点呢,只有一个,就是指的是最临近的直接父节点。比如我们经常会有这样的需求:一个列表,点击删除删除一列,如下:
<ul id="list">
<li>我是沐晴<span>删除</span></li>
<li>我是沐晴<span>删除</span></li>
<li>我是沐晴<span>删除</span></li>
</ul>
var oList = document.getElementById("list");
var aSpan = oList.getElementsByTagName("span");
for(var i=0;i<aSpan.length;i++){
aSpan[i].onclick = function(){
this.parentNode.style.display = "none";
}
}
例子很简单,点击让对应的父元素隐藏即可。来看下一个属性.
offsetParent 这里的父节点,指的是相对于父节点,也就是说某个元素相对于谁定位,谁就是他的父亲。
和它很相似的属性还有offsetLeft \ offsetTop ,他们指的是前元素到offsetParent的距离。
不过不同的浏览器对于这个属性的解释也是有一些不同的:(什么时候元素会相对于别人定位呢,其实也就是有父元素设置相对定位,绝对定位的时候(relative,absolute),这个父元素就叫做定位父级,这个大家应该都懂。)
其他浏览器下:
当没有定位父级的时候: offsetParent 指的是body
有定位父级的时候:offsetParent 指的就是定位父级
IE7以下:
当没有定位父级的时候又分两种情况:
如果自己没有定位: offsetParent 指的是body
如果自己有定位:offsetLeft 指的是 html
如果有定位父级:
如果自己没有定位: offsetParent 指的是body
如果自己有定位:offsetLeft 指的是 定位父级
ie7以下,如果当前元素的某个父级触发了layout,那么offsetParent就会被指向到这个触发了layout特性的父节点上
所以我们在写代码的时候是需要注意这些细节的,我们在写代码的时候经常有这样的需求,获取一个元素到浏览器的距离,一般情况我们是会用到offsetLeft \ offsetTop ,但是这只适用于页面没有定位父级的时候,当我们的代码很多的时候,其中有些元素可能被设置了定位的时候,这个值很可能就不准了。那么如何能完全准确的获取到元素到文档的距离呢?
下面来看张图:
求diiv1到文档的距离,灰色的框是文档,其中又有相对定位父级2和3,这个时候我们怎么求div1到文档的距离呢?通过观察,我们可以知道到文档的距离,正好等于div1到它的定位父级div2的距离加上div2到它的定位父级div3的距离,再加上div3到文档的距离,也就是图中的1+2+3;所以我们可以先求出这个元素到自己的定位父级2的距离,然后再求出它的定位父级2到自己定位父级3的距离。依次到最后就会求得最终的到文档的距离。(body的offsetParent不存在)
我们可以总结出这样的代码
// obj是一个载体,用来放每个定位父级,是在改变的,比如上面的那张图来看,一开始它是div1,当计算出div1到div2的距离的时候,再把它变成div2,再求div2到定位父级div3的距离。依次循环到最后没有定位父级了,它就变成null了,然后停止了循环
var left = 0;
while (obj) { // 当这个元素节点存在的时候循环下面的代码
left += obj.offsetLeft; // 把每个元素定位父级的距离都累加起来
obj = obj.offsetParent; // 把当前的元素赋给obj
}
为了也能求出竖直方向上到文档的距离,也为了更方便,我们可以封装成一个函数:
    function getPos(obj) {
        var pos = {left:0, top:0};
        while (obj) {
            pos.left += obj.offsetLeft;
            pos.top += obj.offsetTop;
            obj = obj.offsetParent;
        }
        return pos;
    }
这个函数会经常用到,像我们的瀑布流中,也是需求的。
最后添加个笔记:
offsetWidth \ clientWidth
style.width : width(样式宽 带单位)
clientWidth : width+padding(不带单位 可视区宽)
offsetWidth:width+padding+border (占位置宽)
好啦,希望今天的分享能带给大家新的体会。
DOM之parentNode与offsetParent的更多相关文章
- javascrip中parentNode和offsetParent之间的区别
		首先是 parentNode 属性,这个属性好理解,就是在 DOM 层次结构定义的上下级关系,如果元素A包含元素B,那么元素B就可以通过 parentElement 属性来获取元素A. 要明白 off ... 
- parentNode,offsetParent
		元素.parentNode : 父节点 只读 属性 当前节点的父级节点 没有兼容性问题 可放心使用 <!DOCTYPE HTML> <html> <head> ... 
- offsetParent和parentNode区别
		offsetParent用的最普遍的就是来计算元素在页面中的位置,前面的日志理讲了 通过getBoundingClientRect() 来获取页面中元素的位置,不过这只支持最新的浏览器,如果要兼容像O ... 
- 我所理解的ECMAScript、DOM、BOM---写给新手们
		像很多新手一样,我知道js有三部分组成,即ECMAScript.DOM.BOM三部分组成,ECMAScript是核心解释器.DOM(Document Object Model)是文档对象模型.BOM( ... 
- JavaScript中的DOM及相关操作
		一.什么是DOM JavaScript由ECMAScript.DOM和BOM三部分组成,其中DOM代表描述网页内容的方法和接口,即文档对象模型(Document Object Model).在网页上, ... 
- day29—JavaScript中DOM的基础知识应用
		转行学开发,代码100天——2018-04-14 JavaScript中DOM操作基础知识即对DOM元素进行增删改操作.主要表现与HTML元素的操作,以及对CSS样式的操作.其主要应用知识如下图: 通 ... 
- JS操作DOM节点查找
		JS中常用的DOM操作事件,包括有节点查找,键盘鼠标事件等等,本文内容介绍DOM的节点查找. <script> window.onload = function(){ //children ... 
- salesforce 零基础学习(三十二)通过Streams和DOM方式读写XML
		有的时候我们需要对XML进行读写操作,常用的XML操作主要有Streams和DOM方式. 一.Streams方式 Streams常用到的类主要有两个XmlStreamReader 以及XmlStrea ... 
- 1.offsetParent,offsetLeft,offsetTop
		offsetParent <!doctype html> <html> <head> <meta charset="utf-8"> ... 
随机推荐
- ORACLE TO_CHAR函数格式化数字的出现空格的原因
			在这篇博客SQL挑战--如何高效生成编码里面我由于需要将数字格式化为字符,像12需要格式化0012这样的字符,所以使用了TO_CHAR(数字,'0000')这样的写法,后面0000表示缺省补零,测试过 ... 
- Android海康监控视频调用demo
			一. 开发环境 1. 操作系统:windows7(X64) 2. 开发工具:eclipse adt Build: v22.2.1-833290 JDK7 android SDK 3. 客户端设备版本: ... 
- Sql Server之旅——第四站 你必须知道的非聚集索引扫描
			非聚集索引,这个是大家都非常熟悉的一个东西,有时候我们由于业务原因,sql写的非常复杂,需要join很多张表,然后就泪流满面了...这时候就 有DBA或者资深的开发给你看这个猥琐的sql,通过执行计划 ... 
- SSIS技巧--优化数据流缓存
			问题 我们经常遇到一种情况,在SSMS中运行很慢的一个查询,当把查询转化成从源到目的数据库的SSIS数据流以后,需要花费几倍的时间!源和数据源都没有任何软硬件瓶颈,并且没有大量的格式转换.之前看了很多 ... 
- Hessian 二进制RPC协议框架
			Hessian是一个由Caucho Technology开发的轻量级二进制RPC协议. 和其他Web服务的实现框架不同的是,Hessian是一个使用二进制轻量级的Web服务协议的框架,免除了许多附加的 ... 
- php框架laravel:数据库建立:artisan
			aravel 迁移是一种数据库的版本控制.迁移通常和 结构生成器 配对使用来管理您应用程序的数据库结构. 配置数据库 我们安装wamp,并且使用mysql方式.用wamp自带的phpMyAdmin添加 ... 
- 使用C/C++,赋值运算时发生的转换
			使用C/C++,赋值运算时发生的转换主要有以下四种情况 一: 两边类型不同: 结果: 自动完成类型转换! 二: 长数赋给短数: 结果: 截取长数的低位送给短数! 三: 短数赋给长数: 结果: 原来是什 ... 
- [转]Shell中read的常用方式
			原文:Linux Shell Scripting Tutorial V2.0 read命令的语法: read -p "Prompt" variable1 variable2 var ... 
- Java 代码的基本知识(摘)
			(摘自:Java经典入门教程) http://wenku.baidu.com/link?url=IoWI58cD5vzeHN-NL4pN7Gren-RfzydrhjDlETAByC9L-9ANinyL ... 
- ELF Format 笔记(三)—— Section Types
			ilocker:关注 Android 安全(新入行,0基础) QQ: 2597294287 ELF 文件中会包含很多 section,所有的 section 都在 section header tab ... 
