I have a flexbox in a side navigation that is overflowing it's granparent's height. The basic structure is:
<div class="holder">
<div class="block-item">content</div>
<div class="flex-nav">
<div class="flex-row"><img src="#"><img src="#"></div>
<div class="flex-row"><img src="#"><img src="#"></div>
<div class="flex-row"><img src="#"><img src="#"></div>
<div class="block-item">content</div>
<div>
.holder { height: 100vh;}
.block-item { display: block;}
.flex-nav { display: flex; flex-flow: column;}
.flex-row { flex: 1 1 0; display: flex;}
img { max-width: 100%;}
Somehow the flex-rows are not shrinking to fit their grandparent's 100vh. Instead, the images are going outside of the view port. From the articles I've read, I'm not sure if a grandchild takes into consideration it's grandparent's height restrictions, though I'm assuming it would. The actual code is slightly different and can be seen in the following codepen:
http://codepen.io/strasbal/pen/zNEMpj?editors=1100
However I'm not sure the exact specifications of Codepen's viewport, it may not show when changes are put into place, so the site url is http://www.webhosting-issues.com
I forked your pen.
Comments are included in the new pen that say /* NEW! */ to help you keep track of what changed, but, basically, since you had already set the height of the overall container at 100vh, I simply assigned a height in vh units to the header and footer that let them maintain the heights they already were, and then did the math to fill in the heights of other child elements.
Overall container is 100vh
Header logo and contact footer are 19vh each
That leaves 62vh for the middle section, made up of three rows
That's 20.666vh per row in the middle section
From there, just set explicit heights for the images and their wrapper links for the inner rows, and you’re was good to go.
One problem you run into is that the text in the links by the images can run out of their container on smaller screens. You could fix that by putting them inside spans and positioning them on top of the images, perhaps with a semi-transparent background.
Hope that works for you.
Related
I've created a codepen to demonstrate the effect and what I want to achieve. It's not that complicated a problem, but I'm not sure how to be more concise and direct.
http://codepen.io/anon/pen/KwoeqR
What I want is to have a variable-width block of text that, when flowing normally, is below a block of content. But, through breakpoints and media queries, becomes stuck to the top right corner of the content, and allows the content to flow around it.
It's very easy to achieve one-half of the equation, or the other. I can achieve a floating top-right aligned block with this:
CSS:
.floater {
float: right;
}
HTML:
<div class="floater"></div>
<p>A bunch of content text.</p>
But when, through a media query, the floater no longer floats, it sits above the content. It needs to sit below.
To make it sit below, I can just do this:
HTML:
<p>A bunch of content text.</p>
<div class="floater"></div>
But now it won't float properly - it does not stick to the top right corner.
Solutions I have tried:
Absolute positioning:
This might work if the block were a fixed width. Instead it is a variable width so I can't simply set margins on the content.
Flexbox:
A flex column reserves the space below it, instead of allowing other columns/content to flow into it. If there is a way to get a flex column to flow or float, that would work, but I have not found one.
I hope this makes sense. It sounds very particular and precise but it really is not. It's a simple layout problem that does not seem to have a simple answer, unless I am missing it!
You can use a combination of float, flex and media queries as below:
.floater{
float: right;
}
#media (max-width: 500px) {
.wrapper{
display: flex;
flex-direction: column;
}
.main{
order: 0;
}
.floater{
order: 1;
}
}
http://jsfiddle.net/og8s0rvr/
Here you can see that the floater is floated right until the window gets smaller than 500px. At that point it switches to a flex layout where the order of elements is changed via order.
I'm using Kube CSS framework to create a demo site at www.dreametry.nl/ddfleurs . It was going well until I came across a problem with the main content background color. On the desktop the white background grows with the content, but not on a mobile device. The problems is the white background stops half way the content.
I tried using several styles, the only changes was with
.content { min-height: 650px; }
But then the background height is too much on mobiles.
Including height: 60%; to the previous code doesn't work.
This can be solved in two ways.
by giving
overflow: hidden
to class="unit-75 content"
or by clearing the div
<div class="unit-75 content" >
<!--All you HTML-->
<div style="clear: both"></div>
</div>
You can use overflow:hidden on the wrapper element (body tag, a particular div etc) to force it to adapt to the height of elements contained IF your layout uses floats.
I've attached a screenshot with this question. There are three columns and I want to keep the height of all the three columns exactly same. I managed to keep the width same with width css property now i wanted to adjust to height. Can anyone help me out in this regard. Thanks in advance.
I would use the following CSS to achieve this:
.wrapper {
display: table;
table-layout: fixed;
width: 100%;
}
.column {
display: table-cell;
}
With table-layout: fixed you're telling every child elements with display: table-cell to have same width, equally distributed based on wrapper's width, as well equal height.
Demo
In pure CSS you can use CSS3 columns: for a 3-column layout just try with
<div style="columns:3">...</div>
(with both -moz- and -webkit- prefixes)
See https://developer.mozilla.org/en-US/docs/CSS/Using_CSS_multi-column_layouts for the reference, in particular about the height balancing:
Height Balancing
The CSS3 Column specification requires that the column heights must be balanced: that is, the browser automatically sets the maximum column height so that the heights of the content in each column are approximately equal.
There is actually no right, cross browser way to do this, but rather you have to resort to some hacks.
A method I have used previously is to wrap the three columns inside a container and set a custom background to the hole container. Basically you create an image, having the same width of the website, having the two vertical lines, and you set it as the background of the container.
<div class="wrapper">
<div class="column">....</div>
<div class="column">....</div>
<div class="column">....</div>
</div>
<style> .wrapper { background-image: url(wrapper-bg.png); } </style>
You could use a javascript library like http://www.cssnewbie.com/equalheights-jquery-plugin/#.UVwCaZAW200 to achive this. This method however does not work if, the hight of the columns is dinamically changing in height (e.g. you have a collapsable item in it). Of course you can handle this cases by handling those events and recalculating the hight.
Finally you could use height: 100%. It's not as simple as it seems however! This solution does only work for block elements and the size of the parent has to be known. So, if you know the size of the website in advance you can do something like the following:
<div class="wrapper">
<div class="column">....</div>
<div class="column">....</div>
<div class="column">....</div>
</div>
<style>
.wrapper { height: 1000px; width:900px; }
.column { width:300px; float:left; height: 100%; }
</style>
Hopefully this will become simpler in future....
Lets say I have this
<div class="sectionContainer">
<div class="itemsContainer">
<div class="items"></div>
<div class="items"></div>
<div class="items"></div>
</div>
</div>
The css:
.itemsContainer
{
/* width:3000px works, however this is what I want to avoid saying explicitly.*/
}
.sectionContainer
{
width: 1000px;
overflow: auto;
}
.items
{
width: 1000px;
float: left;
}
The sectionContainer has some set width.
The items has some set width.
The items container does not have a set width; it will scale to the size of its contents.
The items container's overflow is set to hidden, so that one can scroll through the items within the div. The items within the div are horizontally displayed IE they are side-by-side, I'm currently doing this with a float.
How can I do this with CSS only? Is it possible? I'm not looking for a JavaScript solution right away but can resort to that if needed.
to be more specific, this would work if I specified the itemsContainer to have a width of 3000. But I'm guessing that since it is the child of its parent div, its width gets sized to 1000. I do not want to explicitly set the size of the itemsContainer because this should be based upon the number of items. If I add more items, I want the itemsContainer to change its width to contain all of those items without having to alter the CSS.
Thanks!
It's not possible for CSS to guess what you want to happen -- meaning that it wants to cascade elements downward as opposed to horizontally, which is what you want.
http://jsfiddle.net/9NHFa/
Set the itemsContainer width to a 100% X the number of elements.
.itemsContainer
{
width:300%; /* since you have 3 elements
}
Alright, I understand that the purpose of a DIV is to contain its inner elements - I didn't want to upset anyone by saying otherwise. However, please consider the following scenario:
My web page (which only takes up a width of 70% of the entire page) is surrounded by a container (a div). However, under my navigation bar which is at the top of the page, I would like to create w banner that takes up 100% of the width of the entire page (which means it will have to extend outside the bounds of its container as the container is only taking up 70% of the page's width).
This is the basic idea that I am trying to accomplish: http://www.petersonassociates.biz/
Does anyone have any suggestions for how I could accomplish this? I'd appreciate any help.
Evan
If you just want the background of the element to extend across the whole page this can also be achieved with negative margins.
In a nutshell (correction from comment):
.bleed {
padding-left: 3000px;
margin-left: -3000px;
padding-right: 3000px;
margin-right: -3000px;
}
That gives you horizontal scroll bars which you remove with:
body {overflow-x: hidden; }
There is a guide at http://www.sitepoint.com/css-extend-full-width-bars/.
It might be more semantic to do this with psuedo elements: http://css-tricks.com/full-browser-width-bars/
EDIT (2019):
There is a new trick to get a full bleed using this CSS utility:
width: 100vw;
margin-left: 50%;
transform: translateX(-50%);
I guess all solutions are kind of outdated.
The easiest way to escape the bounds of an element is by adding:
margin-left: calc(~"-50vw + 50%");
margin-right: calc(~"-50vw + 50%");
discussion can be found here and here. There is also a nice solution for the upcoming grid-layouts.
If I understood correctly,
style="width: 100%; position:absolute;"
should achieve what you're going for.
There are a couple of ways you could do this.
Absolute Positioning
Like others have suggested, if you give the element that you want to stretch across the page CSS properties of 100% width and absolute position, it will span the entire width of the page.
However, it will also be situated at the top of the page, probably obscuring your other content, which won't make room for your now 100% content. Absolute positioning removes the element from the document flow, so it will act as though your newly positioned content doesn't exist. Unless you're prepared to calculate exactly where your new element should be and make room for it, this is probably not the best way.
Images: you can also use a collection of images to get at what you want, but good luck updating it or making changes to the height of any part of your page, etc. Again, not great for maintainability.
Nested DIVs
This is how I would suggest you do it. Before we worry about any of the 100% width stuff, I'll first show you how to set up the 70% centered look.
<div class="header">
<div class="center">
// Header content
</div>
</div>
<div class="mainContent">
<div class="center">
// Main content
</div>
</div>
<div class="footer">
<div class="center">
// Footer content
</div>
</div>
With CSS like this:
.center {
width: 70%;
margin: 0 auto;
}
Now you have what appears to be a container around your centered content, when in reality each row of content moving down the page is made up of a containing div, with a semantic and descriptive class (like header, mainContent, etc.), with a "center" class inside of it.
With that set up, making the header appear to "break out of the container div" is as easy as:
.header {
background-color: navy;
}
And the color reaches to the edges of the page. If for some reason you want the content itself to stretch across the page, you could do:
.header .center {
width: auto;
}
And that style would override the .center style, and make the header's content extend to the edges of the page.
Good luck!
The more semantically correct way of doing this is to put your header outside of your main container, avoiding the position:absolute.
Example:
<html>
<head>
<title>A title</title>
<style type="text/css">
.main-content {
width: 70%;
margin: 0 auto;
}
</style>
</head>
<body>
<header><!-- Some header stuff --></header>
<section class="main-content"><!-- Content you already have that takes up 70% --></section>
<body>
</html>
The other method (keeping it in <section class="main-content">) is as you said, incorrect, as a div (or section) is supposed to contain elements, not have them extend out of bounds of their parent div/section. You'll also face problems in IE (I believe anything 7 or below, this might just be IE6 or less though) if your child div extends outside the parent div.