Will
Will

Reputation: 408

Keep element fixed while absolutely positioned in a scrolling element

I have written a code snippet so you understand what I mean better. I have a scrollable area in a grid. I would like to have an element in the bottom left corner to add a new item to the list.

I would like it to be positioned relative to the scrollable element as it will have a dynamic width which is why I cant just use position fixed, I dont want to be positioning it from the edge of the screen.

I dont want it to scroll with the background either. Is there any way thats not hacky to get around this?

.page {
  display: grid;
  grid-template-rows: auto 1fr auto;
  height: 100vh;
  width: 100%;
}

.scrollable {
  background-color: red;
  overflow-y: scroll;
  width: 300px;
  margin: 0 auto;
  position: relative;
}

.item {
  width: 100%;
  border-bottom: 1px solid black;
  height: 90px;
  background-color: blue;
}

.header {
  background-color: yellow;
  width: 100%;
  height: 40px;
}

.footer {
  background-color: yellow;
  width: 100%;
  height: 40px;
}

.add {
  width: 30px;
  height: 30px;
  border-radius: 50%;
  position: absolute;
  bottom: 16px;
  right: 16px;
  background-color: green;
  display: flex;
  justify-content: center;
  align-items: center;
}
<div class="page">

  <div class="header"></div>

  <div class="scrollable">
    <div class="add">+</div>
    
    <div class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
  </div>
  
  <div class="footer"></div>

</div>

Upvotes: 1

Views: 2023

Answers (1)

Krokodil
Krokodil

Reputation: 1470

You can use position sticky to "stick" an element to a scrollable element. Position sticky fluctuates the position of an element between static and fixed depending on the scroll position.

Since you cannot use bottom with position: sticky, you have to use top instead, and calc() the margin from the top using the known height of your button, in this case 30px.

.add {
  height: 30px;
  position: sticky;
  float: right; /* go to the right */
  right: 16px;
  top: calc(100% - 30px - 16px);
}

Upvotes: 1

Related Questions