Reputation: 317
It's hard to explain what I want so i drew a picture.
So basically the first div (the outer div) has fixed height. The third div - blue - contains some text that I don't know the height of so the div should wrap around the text which means it has variable height. And the second div - green - (that should fill the rest of the height) contains an image which should either shrink to fit the div or simply align to the bottom if it's smaller. The problem I encounter is that the image simply doesn't want to shrink. It will always try to be full size and will push the text out of the div #1.
I tried solving it with a table approach but somehow table ignores the outer div fixed height. I'm fine with a flexbox solution althought I would like to avoid it to also support older browsers.
I would really like to solve this with css cause javascript will only complicate things and make it more laggy.
.outer{
width: 100%;
height: 200px;
background-color: lightgray;
padding: 20px;
}
<div class="outer">
<div class="top">
<img src="http://themeflush.com/minimalix/demo4/wp-content/uploads/2014/08/wallpapers-for-christian-background-tumblr-photography-vintage-images-tumblr-wallpapers.jpg">
</div>
<div class="bottom">
<span>Title of the description<span>
<p>This is a long description.</p>
</div>
</div>
Upvotes: 3
Views: 1286
Reputation: 2373
Here is a solution that uses display: table
to maximise your browser support with no polyfills needed. However it uses a background image as opposed to an image..
.outer {
box-sizing: border-box;
display: table;
width: 100%;
height: 200px;
background-color: lightgray;
padding: 20px;
}
.top {
background-size: contain;
background-repeat: no-repeat;
display: table-cell;
height: 100%;
}
.bottom {
display: table-row;
}
<div class="outer">
<div class="top" style="background-image: url(http://themeflush.com/minimalix/demo4/wp-content/uploads/2014/08/wallpapers-for-christian-background-tumblr-photography-vintage-images-tumblr-wallpapers.jpg)">
</div>
<div class="bottom">
<span>Title of the description</span>
<p>This is a long description.</p>
</div>
</div>
Upvotes: 1
Reputation: 371143
Here's a solution in pure CSS.
.outer {
display: flex;
flex-direction: column;
height: 200px;
background-color: lightgray;
padding: 20px;
}
.top {
flex: 1;
display: flex;
}
.top > img {
width: 100%;
object-fit: contain;
object-position: left;
}
<div class="outer">
<div class="top">
<img src="http://themeflush.com/minimalix/demo4/wp-content/uploads/2014/08/wallpapers-for-christian-background-tumblr-photography-vintage-images-tumblr-wallpapers.jpg">
</div>
<div class="bottom">
<span>Title of the description</span>
<p>This is a long description.</p>
</div>
</div>
Browser support: Flexbox is supported by all major browsers, except IE < 10. Some recent browser versions, such as Safari 8 and IE10, require vendor prefixes. For a quick way to add prefixes use Autoprefixer. More details in this answer.
References:
Upvotes: 1
Reputation: 2676
If I'm not mistaken, a pure css solution is unlikely although could look into css grid layout, which also has some compatibility issues. I don't understand why you say js is laggy. All modern browsers are extremely efficient at interpreting and processing the language and most websites and web-apps use javascript. So here is a solution using js calculations.
var img = document.getElementById("myImage");
var bottom = document.getElementById("bottom");
var myTop = document.getElementById("myTop");
var outerHeight = 200;
var remainingHeight = 200 - bottom.offsetHeight;
myTop.style.height = remainingHeight + "px";
if (img.offsetHeight >= remainingHeight)
img.style.height = remainingHeight + "px";
.outer{
width: 100%;
height: 200px;
background-color: lightgray;
padding: 20px;
}
.top {
position:relative;
}
.top img {
position:absolute;
display:block;
bottom:0px;
}
<div class="outer">
<div id="myTop" class="top">
<img id="myImage" src="http://themeflush.com/minimalix/demo4/wp-content/uploads/2014/08/wallpapers-for-christian-background-tumblr-photography-vintage-images-tumblr-wallpapers.jpg"/>
</div>
<div id="bottom" class="bottom">
<span>Title of the description<span>
<p>This is a long description.</p>
</div>
</div>
Upvotes: 0