我可以将元素相对于父元素定位吗?

时间:2011-03-06 09:58:13

标签: css dom

我发现当我将一个元素定位为固定时,如果父元素是否相对定位无关紧要,它将相对于窗口定位固定吗?

CSS

#wrapper { width: 300px; background: orange; margin: 0 auto; position: relative; }
#feedback { position: fixed; right: 0; top: 120px; }

HTML

<div id="wrapper">
    ...
    <a id="feedback" href="#">Feedback</a>
</div>

http://jsbin.com/ibesa3

10 个答案:

答案 0 :(得分:188)

CSS规范要求position:fixed锚定到视口,而不是包含定位元素。

如果必须指定相对于父级的坐标,则必须先使用JavaScript查找父级相对于视口的位置,然后相应地设置子级(固定)元素的位置。

ALTERNATIVE :某些浏览器具有sticky CSS支持,限制了元素在其容器和视口中的位置。根据提交消息:

  

sticky ...约束要在其容器框和视口的交叉点内定位的元素。

     

一个粘性定位的元素表现得像位置:相对(空间是   保留给它in-flow),但偏移量由   粘性位置。更改了isInFlowPositioned()来覆盖相对和   粘性

根据您的设计目标,此行为在某些情况下可能会有所帮助。它目前是一份工作草案,除了表格元素外,还有很好的支持。 position: sticky在Safari中仍然需要-webkit前缀。

有关浏览器支持的最新统计信息,请参阅caniuse

答案 1 :(得分:123)

让我提供两个可能问题的答案。请注意,您现有的标题(和原始帖子)提出的问题与您在编辑和后续评论中所寻求的问题不同。


要将元素定位为“固定”相对于父元素,您需要子元素上的position:absolute,以及父元素上除默认值或静态之外的任何位置模式。

例如:

#parentDiv { position:relative; }
#childDiv { position:absolute; left:50px; top:20px; }

这将使childDiv元素相对于parentDiv的位置向左50像素和向下20像素。


要将元素定位为“固定”相对于窗口,您需要position:fixed,并且可以使用top:left:right:bottom:按你认为合适的位置。

例如:

#yourDiv { position:fixed; bottom:40px; right:40px; }

这将使yourDiv相对于网络浏览器窗口固定,距底边40像素,右边40像素。

答案 2 :(得分:60)

首先设置position: fixedleft: 50%,然后设置第二个 - 现在您的开始是一个中心,您可以设置保证金的新头寸。

答案 3 :(得分:39)

2016年更新

现在可以在现代浏览器中定位相对于其容器固定的元素。具有transform属性的元素充当其任何固定位置子元素的视口。

&#13;
&#13;
.context {
  width: 300px;
  height: 250px;
  margin: 100px;
  transform: translateZ(0);
}
.viewport {
  width: 100%;
  height: 100%;
  border: 1px solid black;
  overflow: scroll;
}
.centered {
  position: fixed;
  left: 50%;
  bottom: 15px;
  transform: translateX(-50%);
}
&#13;
<div class="context">
  <div class="viewport">
    <div class="canvas">

      <table>
        <tr>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
        </tr>
        <tr>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
        </tr>

        <tr>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
        </tr>

        <tr>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
          <td>stuff</td>
        </tr>
      </table>

      <button class="centered">OK</button>

    </div>
  </div>
</div>
&#13;
&#13;
&#13;

答案 4 :(得分:11)

我知道这是超级老但是在找不到我想找的(纯CSS)答案之后我想出了这个解决方案(部分从medium.com中抽象出来)并认为它可能会帮助其他人做同样的事情事情。

如果你结合@ DuckMaestro的答案,你可以定位一个相对于父母(实际是祖父母)固定的元素。使用position: absolute;将一个元素放置在父级内position: relative;,然后position: fixed;放置在绝对定位元素内的元素上,如下所示:

HTML

<div class="relative">
  <div class="absolute">
    <a class="fixed-feedback">This element will be fixed</a>
  </div>
</div>

CSS

.relative {
  margin: 0 auto;
  position: relative;
  width: 300px;
}

.absolute {
  position: absolute;
  right: 0;
  top: 0;
  width: 50px;
}

.fixed-feedback {
  position: fixed;
  top: 120px;
  width: 50px;
}

EXAMPLE

就像@JonAdams所说的那样,position: fixed的定义要求元素相对于视口定位,但是你可以使用这个解决方案绕过它的水平方面。

注意:这与仅在固定元素上设置rightleft值不同,因为这会导致在调整窗口大小时水平移动。

答案 5 :(得分:9)

以上是Jon Adams建议的示例,以便使用jQuery将div(工具栏)修复到页面元素的右侧。我们的想法是找到从视口右侧到页面元素右侧的距离,并保持工具栏的右侧!

HTML

<div id="pageElement"></div>
<div id="toolbar"></div>

CSS

#toolbar {
    position: fixed;
}
....

的jQuery

function placeOnRightHandEdgeOfElement(toolbar, pageElement) {
    $(toolbar).css("right", $(window).scrollLeft() + $(window).width()
    - $(pageElement).offset().left
    - parseInt($(pageElement).css("borderLeftWidth"),10)
    - $(pageElement).width() + "px");
}
$(document).ready(function() {
    $(window).resize(function() {
        placeOnRightHandEdgeOfElement("#toolbar", "#pageElement");
    });
    $(window).scroll(function () { 
        placeOnRightHandEdgeOfElement("#toolbar", "#pageElement");
    });
    $("#toolbar").resize();
});

答案 6 :(得分:2)

我知道这是一篇较老的帖子,但我认为Jiew Meng试图做的一个很好的例子已经在这个网站上找到了。查看位于此处的旁边菜单:https://stackoverflow.com/faq#questions。看一下它没有太深入,我可以告诉javascript附加一个固定的位置一旦滚动点击锚标签下方,并删除固定的定位,如果滚动超过相同的锚标签。希望这会让某人开始朝着正确的方向前进。

答案 7 :(得分:2)

这是一个老帖子,但我会留下我的javascript解决方案,万一有人需要它。

@BasePathAwareController
@RequestMapping("/buergers/search/")
public class BuergerSearchController {

    @Autowired
    QueryService service;

    @RequestMapping(value = "/findBuergerFuzzy", method = RequestMethod.GET)
    public
    @ResponseBody
    ResponseEntity<?> findBuergerFuzzy(PersistentEntityResourceAssembler assembler, @Param("searchString") String searchString) {
        if (searchString.length() < 3)
            throw new IllegalArgumentException("Search String must be at least 3 chars long.");
        List<Buerger> list = service.query(searchString, Buerger.class, new String[]{"vorname", "nachname", "geburtsdatum", "augenfarbe"});
        final List<PersistentEntityResource> collect = list.stream().map(assembler::toResource).collect(Collectors.toList());
        return new ResponseEntity<Object>(new Resources<>(collect), HttpStatus.OK);
    }
}
// you only need this function
function sticky( _el ){
  _el.parentElement.addEventListener("scroll", function(){
    _el.style.transform = "translateY("+this.scrollTop+"px)";
  });
}


// how to make it work:
// get the element you want to be sticky
var el = document.querySelector("#blbl > div");
// give the element as argument, done.
sticky(el);
#blbl{
  position:relative;
  height:200px;  
  overflow: auto;
  background: #eee;
}

#blbl > div{
  position:absolute; 
  padding:50px; 
  top:10px; 
  left:10px; 
  background: #f00
}

备注

  1. 我使用 transform:translateY(@px),因为它应该是轻量级的,high-performance-animations

  2. 我只使用现代浏览器尝试此功能,它不适用于需要供应商的旧浏览器(当然还有IE)

答案 8 :(得分:2)

此解决方案适合我!参考原始详细答案:https://stackoverflow.com/a/11833892/5385623

的CSS:

.level1 {
    position: relative;
}


.level2 {
    position: absolute;
}


.level3 {
    position: fixed;
    /* Do not set top / left! */
}

HTML:

<div class='level1'>
    <div class='level2'>
        <div class='level3'>
            Content
        </div>
    </div>
</div>

答案 9 :(得分:1)

有了多个div,我设法得到一个固定的y和绝对-x div。 在我的情况下,我需要在左侧和右侧使用div,与中心的1180px宽度div对齐。

    <div class="parentdiv" style="
        background: transparent;
        margin: auto;
        width: 100%;
        max-width: 1220px;
        height: 10px;
        text-align: center;">
        <div style="
            position: fixed;
            width: 100%;
            max-width: 1220px;">
            <div style="
                position: absolute;
                background: black;
                height: 20px;
                width: 20px;
                left: 0;">
            </div>
            <div style="
                width: 20px;
                height: 20px;
                background: blue;
                position: absolute;                                           
                right: 0;">
            </div>
        </div>
    </div>