Yes, this has been asked before, and I have seen it work numerous times in online examples, but I must be missing something in my attempt:
main.wrap {
display: flex;
flex-wrap: wrap;
/*flex-direction: row; the default */
gap: 10%;
}
<main class="wrap">
<div class="column">
<h3>Wrap with gap</h3>
<p>Lorem ipsum dolor sit amet, consectetur adipiscing elit. Praesent tincidunt imperdiet justo, ac rhoncus urna sollicitudin vitae. Duis eu dolor eu dui tempor cursus. </p>
</div>
<div class="sidebar">
<h3>Sidebar</h3>
<p>Nullam posuere commodo quam eget ultricies. Duis luctus, mauris at iaculis tempor. </p>
</div>
</main>
Works fine with the default of no-wrap
See it here: https://codepen.io/breadwild/pen/abWMQPB
Thoughts?
Look, If you put flex on the parent element, it will be applied on only its children elements, not on their grand children elements. The marked two portion are the children here. flex-gap has been created in between them.
If you want to add gaps between h3, p tags- you need either to add padding/margin or to add flex on its parent element. Hopefully it helps. Feel free to ask further questions.
You're trying to apply a % gap, and that unit is relative to its parent. In this case, the parent has no defined height, so this is happening:
You can define a height or use the viewport unit for height vh, like this:
Sorry for not understanding your question perfectly. Please replace your CSS file with the given code. I guess you are asking for it. If not, please keep asking questions-
.wrap {
display: flex;
flex-wrap: wrap;
flex-direction: row;
gap: 6%;
}
.column{
flex-basis: 47%;
}
.sidebar{
flex-basis: 47%;
}
In your wrap case your column and sidebar are wrapping into 2 rows, so there isn't a column-gap appearing as each occupies the whole width. (And there isn't a row-gap either between the 2 rows because - as mentioned in another answer - you're using a % value of a parent which doesn't have any height).
With wrap you're allowing the elements to wrap into new rows. So the browser looks at the each element, sees that there's enough text to occupy the whole line, so it allows that and places the elements on 2 rows.
With nowrap you're telling the browser to fit these 2 elements onto the same line. So the browser will do that, choosing a width for each element which makes them of a similar height, and allows the 10% gap in between.
So to get the same effect for wrap you need to constrain both elements so that they don't occupy the whole line, and don't then result in the wrap into 2 rows being applied.
You can do this by adding this CSS, for example:
.column {
max-width: 60%;
}
.sidebar {
max-width: 30%;
}
Related
According to css specification on min/max-height, if I don't provide a fixed height for the containing block any percentage min-height value will be treated as 0. I have the following example showing that this is either implemented with some quirks or I'm missing something very obvious.
What I want to achieve with this layout
A 2 column layout with the container having dynamic height depending on the columns height
The left column should float above the right column
Both the left and the right column should get the height of the largest column (align-items: stretch)
p {
/*Comment out to display more content*/
display: none;
}
.floating-panel-content {
position: relative;
z-index: 1;
background: rgba(0, 100, 0, 0.9);
float: left;
width: 100px;
/*Why does this work? I didn't provide any explicit height.*/
min-height: 100%;
}
.container {
display: flex;
width: 300px;
outline: 1px solid red;
align-items: stretch;
}
.main-panel {
background: blue;
}
img {
display: block;
}
.floating-panel {
flex: 0 0 0;
width: 0;
}
<div class="container">
<div class="floating-panel">
<div class="floating-panel-content">
Floating content
<p>
Lorem ipsum dolor, sit amet consectetur adipisicing elit. Atque maxime aperiam saepe, quia error reiciendis dolorem! Natus facere aliquam sit quisquam, mollitia debitis ullam assumenda atque beatae saepe labore ab.
</p>
</div>
</div>
<div class="main-panel">
<img src="http://placehold.it/300x300">
</div>
</div>
Some content after .container
You wrote:
According to css specification on min/max-height, if I don't provide a fixed height for the containing block any percentage min-height value will be treated as 0.
That's 100% correct. That's what the spec says.
<percentage>
Specifies a percentage for determining the used value. The percentage
is calculated with respect to the height of the generated box's
containing block. If the height of the containing block is not
specified explicitly (i.e., it depends on content height), and this
element is not absolutely positioned, the percentage value is treated
as 0 (for min-height) or none (for max-height).
https://www.w3.org/TR/CSS22/visudet.html#min-max-heights
You wrote:
I have the following example showing that this is either implemented with some quirks or I'm missing something very obvious.
Also correct. You're not missing anything, but you're on the right track with "some quirks".
For many years, major browsers adhered to a strict interpretation of spec language with regard to percentage heights. In other words, without an explicitly defined height on the parent, a percentage height on the child wouldn't work as intended. It would resolve to auto or 0 or none, per the respective rule for height, min-height or max-height.
In recent years, however, most major browsers have loosened their interpretation and now accept other forms of height – such as flex heights – as an acceptable parent reference.
The only browser that appears to continue with the strict interpretation is Safari. Without a defined height (using the height property) on the parent, percentage heights on the children will fail.
It doesn't help matters that the height property definition hasn't been updated since 1998 (CSS2). With the advent of multiple new ways to establish box height, this definition is thoroughly obsolete. It appears that browser makers aren't waiting around for an update from the W3C.
For more details and examples see: Chrome / Safari not filling 100% height of flex parent
Is there any way I can make an image div scale it's height to the text beside it?
I'm designing a blog post element which has some text to the left and an image to the right, however the text and image go out of kilter at certain resolutions which doesn't look great. The best thing I can think of right now is just giving the image a static height but that doesn't really solve the issue and I'd have to put in different heights for different breakpoints which would look quite janky when resizing.
I am trying to emulate the look of this: https://www.lonelyplanet.com/france/paris#survival-guide
(Scroll to the 'Recent Articles' section)
HTML
<div class="recent-petra">
<div class="petra-content">
<h4>Petra</h4>
<cite>Oct. 4</cite>
<p class="recent-desc">Enim vitae pellentesque nec phasellus, quis in vitae, leo in eros donec, pede volutpat. Donec nunc mi vel, quis malesuada, sed proin curabitur orci ipsum volutpat, eu eu id blandit ultricies sodales</p>
</div> <!-- petra-content -->
<div class="petra-img"></div>
</div>
CSS
.recent-petra {
display: flex; }
.petra-content {
width: 60%;
margin: 0 5%; }
.petra-img {
width: 20%;
background-image: url('http://4.bp.blogspot.com/_qWovdGs59MY/RykS9HDQGMI/AAAAAAAAAJo/s79SRNqRNok/s400/Petra+1.jpg');
height: 300px;
margin: 0 5%; }
The codepen is here: http://codepen.io/reskk/pen/ozPwAw - probably a lot better to look there so you get a visual example of what I'm talking about.
I mean.. is this something that is even doable with CSS? Am I trying to do something that is just a massive pain i.e. do I have to find appropriately-sized images etc. or can I achieve this using CSS?
I essentially want the image height to scale according to the height of the text beside it so that it's nice and responsive.
Thanks,
Reskk
You're on the right track with flexbox and background-image here. A couple of things are throwing you off. First is that you've got the image div set to a pixel height. That'll throw the equal height columns in Flexbox off. Second is that margins on divs inside the container count towards its height. So on CodePen, your paragraph has a native margin of 1em 0em, and since it's the last item in that column, the height of the column on the right is matching it.
The site you mention uses a fixed height at various breakpoints for images. It really is the standard way to do images (other way involves making height responsive, which in my experience makes the picture way too small at certain breakpoints. It scales diagonally, instead of by horizontally (width responsive)).
In order to scale your images with your text, you will have to use breakpoints using media queries, which will at various breakpoints change the height of the images and text of the content.
#media (min-width: 0px) and max-width(400px){
img{
width:40%
height:200px;
}
#divcontainingtext{
font-size:14px;
}
}
#media (min-width: 401px) {
/* insert new fixed height and new font-size here */
}
For more information on media queries see: http://www.w3schools.com/css/css_rwd_mediaqueries.asp
Given the following HTML:
<p>
Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore
</p>
And the following CSS:
p {
border: 1px solid red;
width: 200px;
text-align: right;
white-space: nowrap;
}
What would the expected rendering be? I was expecting the text to butt up against the right hand side of the para and overflow off to the left. Observed results in Fx/Safari/Opera butt the text to the left and overflow to the right though. The same problem is observed with text-align:center; I’d expect the text to overflow equally to both sides.
CSS2.1 and CSS3 Text don’t seem to specify the rendering.
Test link: http://www.webdevout.net/test?0e&raw
I was able to get the result you were after using the direction property, e.g.
p {
direction: rtl;
border: 1px solid red;
width: 200px;
text-align: right;
white-space: nowrap;
}
That worked in current versions of Firefox, Safari and IE.
The "Inline Formatting Context" section of the CSS 2.1 spec says:
When the total width of the inline
boxes on a line is less than the width
of the line box containing them, their
horizontal distribution within the
line box is determined by the
'text-align' property. If that
property has the value 'justify', the
user agent may stretch spaces and
words in inline boxes (except for
inline-table and inline-block boxes)
as well.
When an inline box exceeds the width
of a line box, it is split into
several boxes and these boxes are
distributed across several line boxes.
If an inline box cannot be split
(e.g., if the inline box contains a
single character, or language specific
word breaking rules disallow a break
within the inline box, or if the
inline box is affected by a
white-space value of nowrap or pre),
then the inline box overflows the line
box.
So, the text-align property is only used in cases where the line box length is less than the block width. If the line box is wider than its containing element then the text-align property isn't considered.
You can create outside envelope container limiting size
and inner element showing content floated to right, like:
HTML:
<div>
<p>Lorem ipsum dolor sit amet, consectetur adipisicing elit, sed do eiusmod tempor incididunt ut labore.</p>
</div>
CSS:
DIV {
width: 200px;
overflow: hidden;
border: 1px solid red;
}
P {
float: right;
white-space: nowrap;
}
In react to Olly Hodgson's idea:
direction: rtl;
is throwing interpunction from end of sentence (from right) as first char (to left) (Google Chrome v. 38)
Oh, I have encountered this before.
The align:right only affects the content within the box, any overflow is ALWAYS left aligned, only reversing the direction of the text with "direction" can change that.
I have a div with a width of 250px. When the innertext is wider than that i want it to break down. The div is float: left and now has an overflow. I want the scrollbar to go away by using word-wrapping. How can i achieve this?
<div id="Treeview">
<div id="HandboekBox">
<div id="HandboekTitel">
<asp:Label ID="lblManual" runat="server"></asp:Label>
</div>
<div id="HandboekClose">
<asp:ImageButton ID="btnCloseManual" runat="server"
ImageUrl="Graphics/close.png" onclick="btnCloseManual_Click"
BorderWidth="0" ToolTip="Sluit handboek" />
</div>
</div>
<asp:TreeView ID="tvManual" runat="server" RootNodeStyle-CssClass="RootNode">
<Nodes>
</Nodes>
</asp:TreeView>
</div>
CSS:
#Treeview
{
padding-right: 5px;
width: 250px;
height: 100%;
float: left;
border-right: solid 1px black;
overflow-x: scroll;
}
As Andrew said, your text should be doing just that.
There is one instance that I can think of that will behave in the manner you suggest, and that is if you have the whitespace property set.
See if you don't have the following in your CSS somewhere:
white-space: nowrap
That will cause text to continue on the same line until interrupted by a line break.
OK, my apologies, not sure if edited or added the mark-up afterwards (didn't see it at first).
The overflow-x property is what's causing the scroll bar to appear. Remove that and the div will adjust to as high as it needs to be to contain all your text.
Or simply use
word-wrap: break-word;
supported in IE 5.5+, Firefox 3.5+, and WebKit browsers such as Chrome and Safari.
try white-space:normal; This will override inheriting white-space:nowrap;
It's pretty hard to say definitively without seeing what the rendered html looks like and what styles are being applied to the elements within the treeview div, but the thing that jumps out at me right away is the
overflow-x: scroll;
What happens if you remove that?
you can use:
overflow-x: auto;
If you set 'auto' in overflow-x, scroll will appear only when inner size is biggest that DIV area
I'm a little surprised it doesn't just do that. Could there another element inside the div that has a width set to something greater than 250?
Setting just the width and float css properties would get a wrapping panel.
The folowing example work just fine:
<div style="float:left; width: 250px">
Pellentesque feugiat tempor elit. Ut mollis lacinia quam.
Sed pharetra, augue aliquam ornare vestibulum, metus massa
laoreet tellus, eget iaculis lacus ipsum et diam.
</div>
Maybe there are other styles in place that modify the appearance?
I found that word-wrap: anywhere worked (as opposed to word-wrap: break-word mentioned in another answer).
See also:
What does "anywhere" mean in "word-wrap" css property?
I have a row of divs that must all be the same height, but I have no way of knowing what that height might be ahead of time (the content comes from an external source). I initially tried placing the divs in an enclosing div and floated them left. I then set their height to be "100%", but this had no perceptible effect. By setting the height on the enclosing div to a fixed-height I could then get the floated divs to expand, but only up to the fixed height of the container. When the content in one of the divs exceeded the fixed height, it spilled over; the floated divs refused to expand.
I Googled this floated-divs-of-the-same-height problem and apparently there's no way to do it using CSS. So now I am trying to use a combination of relative and absolute positioning instead of floats. This is the CSS:
<style type="text/css">
div.container {
background: #ccc;
position: relative;
min-height: 10em;
}
div.a {
background-color: #aaa;
position: absolute;
top: 0px;
left: 0px;
bottom: 0px;
width: 40%;
}
div.b {
background-color: #bbb;
position: absolute;
top: 0px;
left: 41%;
bottom: 0px;
width: 40%;
}
</style>
This is a simplified version of the HTML:
<div class="container">
<div class="a">Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Integer pretium dui sit amet felis. Integer sit amet diam. Phasellus ultrices viverra velit.</div>
<div class="b">Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Integer pretium dui sit amet felis. Integer sit amet diam. Phasellus ultrices viverra velit. Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Integer pretium dui sit amet felis. Integer sit amet diam. Phasellus ultrices viverra velit.</div>
</div>
This works, unless you change the min-height to something like 5em (demonstranting what happens when the content exceeds the minimum height), and you can see that while the text doesn't get cutoff, the divs still refuse to expand. Now I am at a lose. Is there any way to do this using CSS?
Here is one of those moments where you can get stuck between being idealistic or realistic. I understand that there is no semantic value to placing non-tabular data in a table strictly for formatting reasons but I don't want to see you bending over backwards to create a non-tabular solution to this problem simply for its own sake.
I am the first to shoot down non-semantic designs, trust me, but sometimes you need to face the fact that CSS + semantic markup does not work for all design scenarios. I don't know the accessibility needs of this site but I would recommend that you look to a more practical solution to this problem.
Cheers to you for approaching this the right way and looking for the proper way to solve it! Unfortunately this is one of the dark corners of CSS (along with vertical positioning within a block) that is just plain impossible to do without faux columns, javascript, or table cells.
Whichever you choose, please don't adhere to a standard for its own sake.
Making them exactly the same height can be a tricky thing, but if they just have to appear to be the same height, you may want to look at the faux columns technique.
I have tried a few other methods, but this is the most reliable way I have found of getting the effect, apart from using tables of course.
OK, the table thing turned out to be a little trickier than I thought it would be. It turns out the Javascript solution is actually the simplest (for my situation), since my app is an AJAX app and the framework uses Prototype.js. All it takes is a few lines of JS:
$$('div.container').each(function (element) {
var longest = 0;
element.descendants().each(function (child) {
if (child.getHeight() > longest)
longest = child.getHeight();
});
element.descendants().each(function (child) {
child.style.height = longest + 'px';
});
});
Thanks again for the help.
You can use JavaScript, but of course it will break without JavaScript enabled. Then there's tables, but this ruins the point of CSS. Perhaps seanb's answer could work, place a background image that creates the illusion that all columns go to the bottom. This is known as the faux background technique.
Or sit tight and wait for display: table-cell to be supported for all/most browsers.
Thanks for the answers, guys. I don't think the background image will work because the widths of the columns can also vary depending on how many columns there are (the user can change it). I guess I'll use tables :(
if your looking for a purely css option, and you can seperate the background of the block from the content then the answer is two have two bits of code for each block, one for the content, one for the background. this is how it's done:
<div id="wrapper">
<div class="content" id='one>
<div class="content" id="two>
<div class="content" id="three>
<div class="background" id="back-one">
<div class="background" id="back-two">
<div class="background" id="back-three">
</div>
Position the content divs using floats. Then position the backgrounds using absolute positioning (and a z-index to put them behind)
This works because the floats can set the height, and the absolutely positioned elements can have 100% height. It's a little bit messy, but does the job.