Home > Software engineering >  How can I have one large image over several smaller adjoining divs
How can I have one large image over several smaller adjoining divs

Time:11-11

I have a table-like bunch of divs exposed as follow:

enter image description here

This is the HTML:

<div id='container'>
  
  <div class='row'>
    <div class='smaller'>1</div><div class='smaller image'>2</div><div class='smaller image'>3</div><div class='smaller image'>4</div>
  </div>
  
  <div class='row'>
    <div  class='smaller'>5</div><div class='smaller image'>6</div><div class='smaller image'>7</div><div class='smaller image'>8</div>
  </div>
  
  <div class='row'>
    <div  class='smaller'>9</div><div class='smaller image'>10</div><div class='smaller image'>11</div><div class='smaller image'>12</div>
  </div>      
  
  <div class='row'>
    <div  class='smaller'>13</div><div class='smaller'>14</div><div class='smaller '>15</div><div class='smaller '>16</div>
  </div>            
  
</div>

The image layout above was produced by the following css:

#container {
  background-color:yellow;
  text-align: center;
}

#container .row .smaller {
  background: white;
  border:  1px solid grey;        
  display: inline-block;
  width: 20%;      
}

#container .row .smaller.image {
  background: lightgrey;
}

which can be easily replaced as needed.

I need to place an image over greyed divs (2, 3, 4, 6, 7, 8, 10, 11, 12) keeping the whole thing responsive

As read somewhere, I tried the "background-attachment: fixed;" approach which is not working when scrolling down the page

How to achieve this?

CodePudding user response:

It looks as though you have a grid, with the right hand upper items as one larger item.

If the image is to cover the items you have shown grayed out then there is no need to have them as separate cells and you can use CSS grid's template-area system to create the grid, with the image set as a background to the second cell.

Here's a simple snippet showing that. Note that the grayed out divs have been removed from the HTML as have the row divs as CSS grid will take care of that:

#container {
  width: min(600px, 100vmin);
  height: min(300px, 50vmin);
  display: grid;
  grid-template-areas: "A B B B" "C B B B" "D B B B" "E F G H";
}

#container>div {
  display: flex;
  justify-content: center;
  align-items: center;
  border-style: solid;
}

#container :nth-child(1) {
  grid-area: A;
}

#container :nth-child(2) {
  grid-area: B;
  background-image: url(https://picsum.photos/id/1016/200/300);
  background-size: cover;
  background-position: center center;
}

#container :nth-child(3) {
  grid-area: C;
}

#container :nth-child(4) {
  grid-area: D;
}

#container :nth-child(5) {
  grid-area: E;
}

#container :nth-child(6) {
  grid-area: F;
}

#container :nth-child(7) {
  grid-area: G;
}

#container :nth-child(8) {
  grid-area: H;
}
<div id='container'>
  <div>1</div>
  <div>2</div>
  <div>5</div>
  <div>9</div>
  <div>13</div>
  <div>14</div>
  <div>15</div>
  <div>16</div>
</div>
<iframe name="sif1" sandbox="allow-forms allow-modals allow-scripts" frameborder="0"></iframe>

Obviously you will want to alter the sizes/aspect ratio of the container to suit your application.

CodePudding user response:

If you're looking into another option other than Javascript this can be achieved with CSS Grid layout using Column and Row spans. Quick example, I have only 8 grid items because where the image resides, it takes up all those cells.

.grid {
  display: grid;
  grid-template-columns: repeat(4, [col] 1fr);
  grid-template-rows: repeat(4, [row] auto );
}
.grid-item-image {
  background-color: #ddd;
  z-index: 20;
  grid-column: col 2 / span 3;
  grid-row: row 1 / span 3;
}
.responsive-img {
  width: 100%;
}  
<div class="grid">
  <div class="grid-item item-1">1</div>
  <div class="grid-item item-2">2</div>
  <div class="grid-item item-3">3</div>
  <div class="grid-item item-4">4</div>
  <div class="grid-item item-5">5</div>
  <div class="grid-item item-6">6</div>
  <div class="grid-item item-7">7</div>
  <div class="grid-item-image"><img class="responsive-img" src="https://via.placeholder.com/1000x500"></div>
</div>
<iframe name="sif2" sandbox="allow-forms allow-modals allow-scripts" frameborder="0"></iframe>

  • Related