轻松弄清 JavaScript 中的 offset、scroll、client(转载)

初次见到这张图,觉得好乱额,所以下面我们来慢慢理顺这个东西。

一、理顺 offset

在这里我们可以看到,关于offset共有 5 个东西需要弄清楚:

  1. offsetParent
  2. offsetTop
  3. offsetLeft
  4. offsetWidth
  5. offsetHeight

我们根据难易程度把以上 5 点分为三类来讲解。

第一类:offsetWidthoffsetHeight

obj.offsetWidthobj 控件自身的绝对宽度,不包括因 overflow 而未显示的部分,也就是其实际占据的宽度,整型,单位像素。
obj.offsetHeightobj 控件自身的绝对高度,不包括因 overflow 而未显示的部分,也就是其实际占据的高度,整型,单位像素。

offsetWidth=(border-width)*2+(padding-left)+(width)+(padding-right)
offsetHeight=(border-width)*2+(padding-top)+(height)+(padding-bottom)
  
第二类:offsetLeftoffsetTop

obj.offsetTopobj 相对于版面或由 offsetParent 属性指定的父坐标的计算上侧位置,整型,单位像素。
obj.offsetLeftobj 相对于版面或由 offsetParent 属性指定的父坐标的计算左侧位置,整型,单位像素

offsetLeft=(offsetParent的padding-left)+(中间元素的offsetWidth)+(当前元素的margin-left)。
offsetTop=(offsetParent的padding-top)+(中间元素的offsetHeight)+(当前元素的margin-top)。
  
第三类:offsetParent

offsetParent属性返回一个对象的引用,这个对象是距离调用offsetParent的元素最近的(在包含层次中最靠近的),并且是已进行过CSS定位的容器元素。如果这个容器元素未进行CSS定位, 则offsetParent属性的取值为根元素的引用。

总的来说两条规则:
  1. 如果当前元素的父级元素没有进行CSS定位(positionabsoluterelative),offsetParentbody

  2. 如果当前元素的父级元素中有CSS定位(positionabsoluterelative),offsetParent取最近的那个父级元素。

二、理顺 scroll

  • scrollHeight: 获取对象的滚动高度,对象的实际高度;
  • scrollLeft:设置或获取位于对象左边界和窗口中目前可见内容的最左端之间的距离
  • scrollTop:设置或获取位于对象最顶端和窗口中可见内容的最顶端之间的距离
  • scrollWidth:获取对象的滚动宽度

三、理顺 client

  1. clientHeight, clientWidth
    这两个属性大体上显示了元素内容的象素高度和宽度.理论上说这些测量不考虑任何通过样式表加入元素中的页边距,边框等.                                                                                                         
    clientWidth 是对象可见的宽度,不包滚动条等边线,会随窗口的显示大小改变

  2. clientLeft,clientTop
    这两个返回的是元素周围边框的厚度,如果不指定一个边框或者不定位改元素,他的值就是 0. 
    clientLeft 返回对象的offsetLeft属性值和到当前窗口左边的真实值之间的距离。

四、常见的区别

  1. offsetTopstyle.top 的区别

    我们知道 offsetTop 可以获得 HTML 元素距离上方或外层元素的位置,style.top 也是可以的,二者的区别是:
    一、offsetTop 返回的是数字,而 style.top 返回的是字符串,除了数字外还带有单位:px。 二、offsetTop只读,而style.top可读写。 三、如果没有给HTML元素指定过top样式,则style.top` 返回的是空字符串。

    offsetLeftstyle.leftoffsetWidthstyle.widthoffsetHeightstyle.height 也是同样道理。

  2. clientHeightoffsetHeightscrollHeight

    我们这里说说四种浏览器对 document.bodyclientHeightoffsetHeightscrollHeight 的解释。
    这四种浏览器分别为 IE(Internet Explorer)、NS(Netscape)、Opera、FF(FireFox)。

    • clientHeight
      是内容可视区域的高度,也就是说页面浏览器中可以看到内容的这个区域的高度,一般是最后一个工具条以下到状态栏以上的这个区域,与页面内容无关。
    • offsetHeight
      IE、Opera 认为 offsetHeight = clientHeight + 滚动条 + 边框。
      NS、FF 认为 offsetHeight 是网页内容实际高度,可以小于 clientHeight
    • scrollHeight
      IE、Opera 认为 scrollHeight 是网页内容实际高度,可以小于 clientHeight
      NS、FF 认为 scrollHeight 是网页内容高度,不过最小值是 clientHeight

    简单地说
    clientHeight 就是透过浏览器看内容的这个区域高度。
    NS、FF 认为 offsetHeightscrollHeight 都是网页内容高度,只不过当网页内容高度小于等于 clientHeight 时,scrollHeight 的值是 clientHeight,而 offsetHeight 可以小于 clientHeight
    IE、Opera 认为 offsetHeight 是可视区域 clientHeight 滚动条加边框。scrollHeight 则是网页内容实际高度。

    同理
    clientWidthoffsetWidthscrollWidth 的解释与上面相同,只是把高度换成宽度即可。

    但是
    FF 在不同的 DOCTYPE 中对 clientHeight 的解释不同, xhtml 1 trasitional 中则不是如上解释的。其它浏览器则不存在此问题。
    标题:scrollTopscrollLeftscrollWidthscrollHeight

    scrollTop 是“卷”起来的高度值,示例:

    <div style="width:100px;height:100px;background-color:#FF0000;overflow:hidden;" id="p">
        <div style="width:50px;height:300px;background-color:#0000FF;" id="t">如果为 p 设置了 scrollTop,这些内容可能不会完全显示。</div>
    </div>
    <script type="text/javascript">
        var p = document.getElementById("p");
        p.scrollTop = 10;
    </script>
      

    由于为外层元素 p 设置了 scrollTop,所以内层元素会向上卷。

    scrollLeft 也是类似道理。

    我们已经知道 offsetHeight 是自身元素的宽度。
    scrollHeight 是内部元素的绝对宽度,包含内部元素的隐藏的部分。

    上述中 pscrollHeight 为 300,而 poffsetHeight 为 100。

    scrollWidth 也是类似道理。

    IEFireFox 全面支持,而 NetscapeOpera 不支持 scrollTopscrollLeftdocument.body 除外)。

  3. offsetTopoffsetLeftoffsetWidthoffsetHeight

    1. offsetTop :
      当前对象到其上级层顶部的距离.
      不能对其进行赋值.设置对象到页面顶部的距离请用style.top属性.

    2. offsetLeft :
      当前对象到其上级层左边的距离.
      不能对其进行赋值.设置对象到页面左部的距离请用style.left属性.

    3. offsetWidth :
      当前对象的宽度.
      style.width属性的区别在于:如对象的宽度设定值为百分比宽度,则无论页面变大还是变小,style.width都返回此百分比,而offsetWidth则返回在不同页面中对象的宽度值而不是百分比值

    4. offsetHeight :
      style.height属性的区别在于:如对象的宽度设定值为百分比高度,则无论页面变大还是变小,style.height都返回此百分比,而offsetHeight则返回在不同页面中对象的高度值而不是百分比值


转载自:http://my.oschina.net/longteng2013/blog/167023