Responsive layout: stretched images on Safari - html

this is my layout.
The desired behavior is that when I resize the window vertically the image scales maintaining the original aspect ratio.
My code works very well in all browser except Safari (you can see it by trying the snippet in different browsers).
Do you have a solution? Thanks ;)
.wrap-container{
width: 100%;
display: flex;
justify-content: center;
background-color: yellow;
height: 55vh;
}
.wrap{
width: 700px;
background-color: aqua;
display: flex;
justify-content: flex-start;
align-items: flex-end;
padding-top: 64px;
}
.wrap img{
height: 100%;
width: auto;
max-width: 300px;
max-height: 300px;
}
<div class="wrap-container">
<div class="wrap">
<img src="https://via.placeholder.com/300"/>
</div>
</div>

Add flex: 0; on the image
.wrap-container{
width: 100%;
display: flex;
justify-content: center;
background-color: yellow;
height: 55vh;
}
.wrap{
width: 700px;
background-color: aqua;
display: flex;
justify-content: flex-start;
align-items: flex-end;
padding-top: 64px;
}
.wrap img{
height: 100%;
width: auto;
flex: 0;
max-width: 300px;
max-height: 300px;
}
<div class="wrap-container">
<div class="wrap">
<img src="https://via.placeholder.com/300"/>
</div>
</div>

Related

flexbox justify-content causes overflow: auto not work correctly

I have a container div that its content can grow vertically. I used overflow-y: auto for the container to make my page look good. But I need to place everything in the center when the content's height is smaller than the container's. So I used flexbox to do that. But the problem is that I can't scroll completely to see the top part of the contents.
Here is a simple example of the problematic code:
<html lang="en">
<head>
<style>
.container {
width: 20rem;
height: 20rem;
background-color: red;
display: flex;
justify-content: center;
flex-direction: column;
align-items: center;
overflow-y: auto;
}
.child {
width: 10rem;
height: 40rem;
background-color: blue;
flex-shrink: 0;
}
.top {
width: 1rem;
height: 1rem;
background-color: green;
}
</style>
</head>
<body>
<div class="container">
<div class="child">
<div class="top"></div>
</div>
</div>
</body>
</html>
One of the solutions to this problem is to use the reverse order of the elements in the flex-container, i.e. in your case, using flex-direction: column-reverse instead of flex-direction: column.
Example #1 below:
.container {
width: 20rem;
height: 20rem;
background-color: red;
display: flex;
justify-content: center;
flex-direction: column-reverse;
align-items: center;
overflow-y: auto;
}
.child {
width: 10rem;
min-height: 0;
height: 40rem;
background-color: blue;
flex-shrink: 0;
max-height: 150%;
}
.top {
width: 1rem;
height: 1rem;
background-color: green;
}
<div class="container">
<div class="child">
<div class="top">test</div>
</div>
</div>
The second solution is to consider using for center alignment, you can also use justify-content: space-between and pseudo-elements ::after and ::before.
Example #2 below:
.container {
width: 20rem;
height: 20rem;
background-color: red;
display: flex;
justify-content: space-between;
flex-direction: column;
align-items: center;
overflow-y: auto;
}
.container::before,
.container::after {
content: '';
}
.child {
width: 10rem;
min-height: 0;
height: 40rem;
background-color: blue;
flex-shrink: 0;
max-height: 150%;
}
.top {
width: 1rem;
height: 1rem;
background-color: green;
}
<div class="container">
<div class="child">
<div class="top">test222</div>
</div>
</div>

Scroll div with overflow y with image is distorting image in chrome and firefox but not safari

I have long image that I want to display in a container with a scroll bar. Perhaps I'm not going about this the right way, but at the moment I have a container(work-sample) with a project-container with the image inside. It displays fine in safari but for some reason when viewed in chrome and safari on macs, the long image is all scrunched together.
#work-sample {
flex: 1 3 auto;
flex-basis: 3;
display: flex;
flex-direction: column;
justify-content: flex-end;
width: 100%;
height: 400px;
position: relative;
overflow-y: scroll;
padding-right: 1rem;
padding-top: 1rem;
padding-bottom: 1rem;
}
.project-scroll {
overflow-x: hidden;
overflow-y: scroll;
object-fit: cover;
}
#project-long {
width: 100%;
height: 100%;
text-align: center;
}
<div id="work-sample" class="work-sample">
<div class="project-scroll">
<img id="project-long" src="../media/incompatible-image.png">
</div>
</div>
There is a height setting of 100% in the class for the img. This makes the img distorted as it's forced to fit that height. This snippet removes this so the height will default to auto and be shown in proportion to the overall image's aspect ratio.
#work-sample {
flex: 1 3 auto;
flex-basis: 3;
display: flex;
flex-direction: column;
justify-content: flex-end;
width: 100%;
height: 400px;
position: relative;
overflow-y: scroll;
padding-right: 1rem;
padding-top: 1rem;
padding-bottom: 1rem;
}
.project-scroll {
overflow-x: hidden;
overflow-y: scroll;
object-fit: cover;
}
#project-long {
width: 100%;
/* height: 100%; REMOVED */
text-align: center;
}
<div id="work-sample" class="work-sample">
<div class="project-scroll">
<img id="project-long" src="https://picsum.photos/id/1015/200/600">
</div>
</div>
I think the issue is because object-fit is on the parent to your img but should be on img itself.
#work-sample {
flex: 1 3 auto;
flex-basis: 3;
display: flex;
flex-direction: column;
justify-content: flex-end;
width: 100%;
height: 400px;
position: relative;
overflow-y: scroll;
padding-right: 1rem;
padding-top: 1rem;
padding-bottom: 1rem;
}
.project-scroll {
overflow-x: hidden;
overflow-y: scroll;
}
#project-long {
width: 100%;
height: 100%;
object-fit: cover; /* this property moved from .project-scroll */
text-align: center;
}
<div id="work-sample" class="work-sample">
<div class="project-scroll">
<img id="project-long" src="https://generative-placeholders.glitch.me/image?width=1200&height=500">
</div>
</div>

The Div's stack on top of each other

The second div stacks on top of the first div and the first div invisible
How can i position it below the first div
.shop {
width: 100%;
height: 1000px;
background-color: #ffffff;
position: relative;
justify-content: center;
display: flex;
}
.bell {
width: 100%;
height: 100%;
display: flex;
justify-content: center;
align-items: center;
position: relative;
}
<div class="shop"></div>
<div class="bell">
<img src="bell.png" alt="">
</div>
Is this what you are trying to do ? :)
.shop {
width: 100%;
height: 1000px;
background-color: #000;
justify-content: center;
display: flex;
}
.bell {
background-color: red;
width: 100%;
height: 100%;
display: flex;
justify-content: center;
align-items: center;
}
img{
width : 30%;
}
<div class="shop"></div>
<div class="bell">
<img src="https://images.pexels.com/photos/1289845/pexels-photo-1289845.jpeg?auto=compress&cs=tinysrgb&dpr=1&w=500" alt="">
</div>

Make a div as large as possible in flexLayout

#container {
display: flex;
flex-direction: column;
align-items: center;
height: 200px;
width: 100px;
background-color: red;
}
#stack{
display: flex;
flex-direction: column;
align-items: center;
max-height: 200px;
}
.item {
display: flex;
height: 30px;
width: 100px;
background-color: green;
flex-shrink: 0;
}
.spacer {
display: flex;
height: 200px;
flex-shrink: 1000;
}
<div id="container">
<div class="stack">
<div class="item">a</div>
<div class="spacer"></div>
<div class="item">b</div>
</div>
</div>
As the code shows above, parent had a max-height as the height of it is undefined.
I want the height of spacer was as large as possible. And what I expect is 160px in this situation.
I had tried flex-grow, but it doesn't work as the container has no height.
I had tried flex-shrink and a large height like the code in snippet either. But I found that sometime flex-shrink not work, or sometimes it looks scary with a very large height.
it does not work because you use a wrong selector for "stack" - it is a class, not id!
This should work: https://jsfiddle.net/bL5w81d4/1/
#container {
display: flex;
flex-direction: column;
align-items: center;
height: 200px;
width: 100px;
background-color: red;
}
.stack{
display: flex;
flex-direction: column;
align-items: center;
max-height: 200px;
}
.item {
display: flex;
height: 30px;
width: 100px;
background-color: green;
flex-shrink: 0;
}
.spacer {
display: flex;
height: 200px;
flex-shrink: 1000;
}

`position:absolute` with `bottom:0` is not working with parent having display:flex?

I want to fix div with class sidebar to the bottom of the container, but position: absolute with bottom:0 is not working with a container having display: flex.
how to solve that problem?
code: https://jsfiddle.net/zgmg48z1/1/
/*******************page layout**************************/
.container{
width: 100%;
background-color: #d5d5d5;
display: flex;
align-items: flex-start;
}
.sidebarcontainer{
width: 250PX;
/*height: 6000px;*/
display: inline-block;
box-sizing: border-box;
padding: 5px;
padding-right: 2px;
}
.innersidebarcontainer{
position: relative;
width: 100%;
height: 100%;
}
.sidebar{
width: 243px;
background-color: white;
height: 500px;
/*top: 1px;*/
/*bottom: 0;*/
/*position: absolute;*/
}
.mainpage{
width: calc(100% - 250px);
padding: 5px;
padding-left: 2px;
height: 600px;
display: inline-block;
box-sizing: border-box;
}
.page{
width: 100%;
height: 100%;
background-color: white;
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: center;
align-items: baseline;
align-content: flex-start;
}
.footer{
height: 500px;
width: 100%;
margin: 0 auto;
background-color: #031003;
}
/***************end of pagelayout******************/
.card{
width: 250px;
/*height: 400px;*/
align-self: flex-start;
margin: 10px;
display: inline-block;
}
.image{
width: 200px;
margin: 0 auto;
height: 250px;
}
.image img{
width: 100%;
height: 100%;
}
<div class="container">
<div class="sidebarcontainer">
<div class="innersidebarcontainer">
<div class="sidebar">
</div>
</div>
</div><!--
--><div class="mainpage">
<div class="page">
<h1>something in the page</h1>
</div>
</div>
</div>
<div class="footer"></div>
Try this:
.sidebarcontainer{
/*OTHER STUFF*/
align-self: flex-end;
}
Explanation here: https://css-tricks.com/snippets/css/a-guide-to-flexbox/#article-header-id-14
"This allows the default alignment (or the one specified by align-items) to be overridden for individual flex items."
If you want the sidebar to be at the bottom of the container, you can use align-self: flex-end on the sidebar container.
In this case you don't have to use an absolute position on your sidebar. But i'm not sure that's what your trying to do, maybe you need to have a 100% height (of the container) sidebar container and to align bottom the content of the sidebar. If you need that you can set an height on your sidebar container and a relative position. Then use position: absolute and bottom: 0 on the sidebar child.
/*******************page layout**************************/
.container{
width: 100%;
background-color: #d5d5d5;
display: flex;
align-items: flex-start;
}
.sidebarcontainer{
width: 250PX;
/*height: 6000px;*/
display: inline-block;
box-sizing: border-box;
/* Add align-self: flex-end to the sidebar-container */
align-self: flex-end;
padding: 5px;
padding-right: 2px;
}
.innersidebarcontainer{
position: relative;
width: 100%;
height: 100%;
}
.sidebar{
width: 243px;
background-color: white;
height: 500px;
/*top: 1px;*/
/*bottom: 0;*/
/*position: absolute;*/
}
.mainpage{
width: calc(100% - 250px);
padding: 5px;
padding-left: 2px;
height: 600px;
display: inline-block;
box-sizing: border-box;
}
.page{
width: 100%;
height: 100%;
background-color: white;
display: flex;
flex-direction: row;
flex-wrap: wrap;
justify-content: center;
align-items: baseline;
align-content: flex-start;
}
.footer{
height: 500px;
width: 100%;
margin: 0 auto;
background-color: #031003;
}
/***************end of pagelayout******************/
.card{
width: 250px;
/*height: 400px;*/
align-self: flex-start;
margin: 10px;
display: inline-block;
}
.image{
width: 200px;
margin: 0 auto;
height: 250px;
}
.image img{
width: 100%;
height: 100%;
}
<div class="container">
<div class="sidebarcontainer">
<div class="innersidebarcontainer">
<div class="sidebar">
</div>
</div>
</div><!--
--><div class="mainpage">
<div class="page">
<h1>something in the page</h1>
</div>
</div>
</div>
<div class="footer"></div>
This exact same problem happened to me recently. In my case it wasn't the fault of flex or even the positioning at all in the end, turns out I had another class that was cascading down and also effecting the element's absolute position making it look like my new values weren't working.