Itay Gal
Itay Gal

Reputation: 10834

Fixed div inside a scrollable div - CSS only

I'm trying to make a div stay at a fixed location inside another div. The containing div is scrollable and his location is not fixed in the screen.

This is what I got so far JSFiddle

The text "fixed text" should stay at the top right corner of the container when scrolling. I made 2 copies of the div and kept the same class in order to simulate 2 different locations of the div.

Can it be done with CSS only?

HTML

<div class="cont">
  <div class="items">
    <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 class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
  </div>
  <div class="txt">
    fixed text
  </div>
</div>

<div class="cont">
  <div class="items">
    <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 class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
  </div>
  <div class="txt">
    fixed text
  </div>
</div>

CSS

.cont{
  width: 400px;
  height: 130px;
  border: 1px solid black;
  margin: 10px;
  overflow-x: auto;
  overflow-y: hidden;
  position: relative;
}

.items{
  width: 600px;
}

.item{
  width: 80px;
  height: 80px;
  background-color: blue;
  margin-top: 22px;
  margin-left: 3px;
  display: inline-block;
}

.txt{
  position: absolute;
  top: 2px;
  right: 10px;
}

Upvotes: 3

Views: 5210

Answers (3)

Nenad Vracar
Nenad Vracar

Reputation: 122027

You can use overflow: auto on items instead of cont element.

.cont {
  width: 400px;
  height: 130px;
  border: 1px solid black;
  margin: 10px;
  overflow-x: hidden;
  position: relative;
}
.items {
  overflow-x: auto;
  overflow-y: hidden;
  white-space: nowrap;
}
.item {
  width: 80px;
  height: 80px;
  background-color: blue;
  margin-top: 22px;
  margin-left: 3px;
  display: inline-block;
}
.txt {
  position: absolute;
  top: 2px;
  right: 10px;
}
<div class="cont">
  <div class="items">
    <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 class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
  </div>
  <div class="txt">
    fixed text
  </div>
</div>

Upvotes: 2

kukkuz
kukkuz

Reputation: 42352

Create an extra wrapper and apply height and overflow to that - I have added a div inner wrapping all the contents of cont and applied this to it:

.inner {
  overflow-x: scroll;
  overflow-y: hidden;
  height: inherit;
}

See demo below to see what I mean:

.cont {
  width: 400px;
  height: 130px;
  border: 1px solid black;
  margin: 10px;
  /*overflow-x: auto;*/
  /*overflow-y: hidden;*/
  position: relative;
}
.items {
  width: 600px;
}
.item {
  width: 80px;
  height: 80px;
  background-color: blue;
  margin-top: 22px;
  margin-left: 3px;
  display: inline-block;
}
.txt {
  position: absolute;
  top: 2px;
  right: 10px;
}
.inner {
  overflow-x: scroll;
  overflow-y: hidden;
  height: inherit;
}
<div class="cont">
  <div class="inner">
    <div class="items">
      <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 class="item"></div>
      <div class="item"></div>
      <div class="item"></div>
    </div>
    <div class="txt">
      fixed text
    </div>
  </div>
</div>

Upvotes: 1

Michael Coker
Michael Coker

Reputation: 53664

Add the fixed height and overflow to .items instead, so that .items scrolls instead of .cont, and .txt will stay where it is since it is positioned relative to .cont and .cont isn't scrolling.

.cont{
  width: 400px;
  border: 1px solid black;
  margin: 10px;
  overflow-x: auto;
  overflow-y: hidden;
  position: relative;
}

.items{
  width: 600px;
  height: 130px;
  overflow: scroll;
}

.item{
  width: 80px;
  height: 80px;
  background-color: blue;
  margin-top: 22px;
  margin-left: 3px;
  display: inline-block;
}

.txt{
  position: absolute;
  top: 2px;
  right: 10px;
}
<div class="cont">
  <div class="items">
    <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 class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
  </div>
  <div class="txt">
    fixed text
  </div>
</div>

<div class="cont">
  <div class="items">
    <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 class="item"></div>
    <div class="item"></div>
    <div class="item"></div>
  </div>
  <div class="txt">
    fixed text
  </div>
</div>

Upvotes: 0

Related Questions