I am developing a forum theme at the moment, and am trying to figure out how to do the last bits, the posts. Example of what I'd like to make:
So the key things to keep in mind here is how User Info and Post Content have different colors, as well as the Post Description in the grid is in the same column as the Post Content.
Using a simple div setup doesn't work, as I need the User Info height to control the height of Post Content and vice versa. Having a wrapper element with the background color of User Info would work, but only if the Post Content is taller than User Info.
I am really just looking for brainstorming here. What would be the best way to go about doing this?
I created a draft of what the final result should look like here:
It should be fine with the code you have provided altered slightly, but I have some questions.
1) You commented the description has a set height? Does it need to? Worst case scenario I just adjust this height in media queries.
2) I probably need to have some columns within Post description too. As you see in my draft there's a left container with the timestamp (let's call that desc-meta) of the post, and to the right there's a permalink with ID (let's call that desc-ID). There's also a set of post options (Edit, report etc.) between the two (let's call that desc-edit), but aligned to the right side of the description. From my brief understanding of flex I can't figure out how to always keep the desc-meta and desc-ID on the same row, while desc-meta can be moved down if needed on smaller screens.
This layout can be achieved with CSS flexbox.
For both columns to have equal height we can use the align-items property, which controls space distribution among flex items on the cross-axis.
The default value is stretch, which enables items to extend the full length of the container.
.container-outer { align-items: stretch; }
We can also use the flex-grow property to control how free space is distributed among flex items in the main-axis.
.post-content { flex-grow: 1; }
The code below renders this (with borders only for demo purposes):
.container-outer {
display: flex;
align-items: stretch; /* tells boxes to stretch vertically (default value) */
width: 75%;
min-height: 250px;
border: 5px solid mistyrose;
}
.user-info {
display: flex; /* nested flexbox, to enable flex properties */
flex-direction: column;
justify-content: center;
align-items: center;
width: 25%;
border: 3px solid red;
font-family: verdana;
font-weight: bold;
font-size: 2em;
color: red;
box-sizing: border-box;
overflow: auto;
}
.container-inner {
display: flex; /* nested flexbox */
flex-direction: column;
width: 100%;
border: 3px dashed black;
overflow: auto;
}
.post-description {
display: flex; /* nested flexbox */
justify-content: center;
align-items: center;
height: 50px; /* fixed height */
border: 3px solid green;
font-family: verdana;
font-weight: bold;
font-size: 1.5em;
color: green;
box-sizing: border-box;
overflow: auto;
}
.post-content {
display: flex; /* nested flexbox */
justify-content: center;
align-items: center;
flex-grow: 1; /* box takes all available space (stretch, basically) */
border: 3px solid blue;
font-family: verdana;
font-weight: bold;
font-size: 2em;
color: blue;
box-sizing: border-box;
overflow: auto;
}
<article class="container-outer">
<section class="user-info">USER<br>INFO</section>
<div class="container-inner">
<section class="post-description">POST DESCRIPTION</section>
<section class="post-content">POST CONTENT</section>
</div><!-- end .container-inner -->
</article><!-- end .container-outer -->
jsFiddle
Regardless of how much or how little content is placed in USER INFO or POST CONTENT, both columns will remain equal height.
The container is given a minimum height (min-height: 250px;) to ensure it doesn't get too small if there is no content in either box.
flex-grow is only applied to POST CONTENT because USER INFO already expands full height by inheriting height from the container, and POST DESCRIPTION has a fixed height, so it won't expand.
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.
My initial thoughts would be to do something like this:
<div class="one">
</div>
<div class="container">
<div class="two">
</div>
<div class="three">
</div>
</div>
And then give the left div a display of inline-block and the right container of inline-block, and the inner divs remain block.
.one {
display: inline-block;
}
.container {
display: inline-block;
}
I would use display: table with the corresponding rows/cells. See this http://jsfiddle.net/ycsmo9vg/ it should be easy extend this for your needs
notice how in the second cell, I have 2 divs, 1 has class row and the second div is plain (no class needed). This is up to you. Since a div is a block level element it will automatically take a row. Though I'd say keep it consistent and have a class of row wherever you have a row
Related
I have the following header with items and am using flexbox
<header class="header">
<div class="row container header__items">
<h2 class="header__logo">Test</h2>
<input type="text" class="input input--outlined" placeholder="Serach">
<h5>Karim</h5>
<h5>Karim</h5>
<h5>Karim</h5>
</div>
</header>
And my scss code with flexbox classes i have
.header{
height: 50px;
background-color: white;
box-shadow: 0 10px 20px rgba(0,0,0,0.19), 0 6px 6px rgba(0,0,0,0.23);
display: flex;
align-items: center;
&__items{
display: inherit;
flex-direction: row;
align-items: center;
background-color: red;
}
&__logo{
font-size: 35px;
font-weight: 200;
color: inherit;
}
}
The following has the header__items overflowing on the y-axis. How can i stop this. See the attached screenshot on the red background. Also it doesn't center the red box even if i reduce its height.Am using materialize css. I have also created https://codepen.io/geowan/pen/gOpzOEm which shows this.
Yash - there are so many things wrong with your markup. Firstly, Materializecss have already created a navbar for you - why re-invent the wheel? They don't use flexbox, but you can adapt their example to create what you need.
https://materializecss.com/navbar.html
Secondly, you are using a row inside a div that is also a container - and there are no cols inside. Here's how it works:
.container
This restricts the width of content. Consider it the inner-wrapper.
.row
Rows sit inside containers - they add margin-bottom for spacing, and are a container for cols.
.col
cols sit inside rows and lay your content out in columns. Please refer to the grid system, you are not suing elements as per the documentation.
https://materializecss.com/grid.html
input {
width: auto !important;
}
.links {
display: flex;
}
In terms of fixing your code, I removed .row from the element, put justify-content:space-between on the header__items to force the three items away from each other, wrapped your right hand links in a new div (and display: flex on these) and then changed the input width to auto, because the materialize default is 100% (so it was spreading the available width of your div.
https://codepen.io/doughballs/pen/MWwGwme
You need to spend some time in the docs and use the provided examples until you know what you're doing.
I am building a website from an image given to me to practice (it comes from his employer as a test). I know he mainly used flexbox in the entire site, so im trying to stick with that (havent learned grid at all). On the top of the website is a sort of 'header' that includes some button links, a logo, and a search bar in the middle. The searchbar is located vertically about halfway down the entire header.
I am trying to do that without using a margin hack, but none of the typical align or justify commands seem to work. I also set a height, still nothing. Any thoughts?
Included a height property, also tried various commands like: align-item, align-items, align-self, justify-content, etc.
#searchbar {
height: 100px;
width: 15rem;
flex: 1;
/* margin-top: 15px; */
margin-right: -5px;
text-align: center;
}
I want to move the search bar down to the middle of its parent element, but nothing seems to work.
You need to apply align-self: center to the #searchbar - asyou can see - the display: flex is applied to the parent, then align-self to the div. This centeres it withing the parent. Then you will need to apply that same logic to the contents of the searchbar div itself - in order to center them within it. and adding justify-content: center to center the content horizontally within the parent div as well.
I have applied a yellow background on the parent div, a red border on the searchbar div to demonstrate the relationship and the centering of the inner div and a blue border on the text withon the searchbar div to show its centered..
#wrapper {
height : 200px;
display: flex;
background: yellow
}
#searchbar {
height: 100px;
width: 15rem;
flex: 1;
text-align: center;
align-self: center;
border: solid 1px red;
display: flex;
align-items: center;
justify-content: center
}
#searchbar-content {
border: solid 1px blue;
}
<div id="wrapper">
<div id="searchbar">
<span id="searchbar-content">Search bar content goes here</span>
</div>
I am currently designing a book website and on the right-hand side want to have a "Table of contents" which is in a fixed position and scrollable. I set the header for my website to "display: table-row" and similarly did so with the table of contents and its internal elements. (A header and a the scrollable list of chapters) As I understand it, display: table row should make a div element fill the remaining height and only the remaining height. [1] However, in this case, the content continues offscreen instead of allowing the user to scroll through it. (You can see the problem on this jsfiddle: https://jsfiddle.net/chrmon2/9wzjckvn/6/)
My css:
#container {
height: 300px;
border: 1px solid black;
}
#header {
background: blue;
display: table-row;
}
#toc h1 {
background: red;
display: table-row;
}
#toc #content {
background: yellow;
overflow-y: scroll;
display: table-row;
}
Is this not a capability of display: table-row or am I doing something wrong? Thanks
https://www.whitebyte.info/programming/css/how-to-make-a-div-take-the-remaining-height
As I understand it, the effect you want is as follows:
When there is remaining space, stretch the table of contents items;
When the space is too small, begin scrolling.
This is an ideal application of CSS Flexboxes. Flexboxes allow you to define how items stretch (or don't), how they align with each other, how they wrap etc.
In this case, we're going to use flexboxes for all the divs in this example.
.container, .toc, .content {
display: flex; /* begins flexbox layout */
flex-direction: column; /* Flexboxes can be aligned from left-to-right
or from top-to-bottom. In this case, we want
them to be top-to-bottom. */
flex-grow: 1; /* On .container, this does nothing. However, for
children of Flexboxes, this tells them to grow
if any space is still available. */
min-height: 0; /* For a more complicated reason, this is necessary
to make flexboxes scroll correctly. This needs
to be set on all the flexboxes in this example. */
}
.toc .content .item {
flex-grow: 1; /* Make items grow when there is room available */
}
.content {
overflow-y: scroll;
}
You can see the effects of this at this JSFiddle.
Just remove display: table-row from #toc #content and add this :
#content{
max-height:200px;
}
height can be as per your requirement.
In my bootstrap page, I want to force the <footer>...</footer> to be at the bottom of the page or the content, whichever is lower.
And there is a solution for that already which works great. However, that approach requires that I know ahead of time what the height of the footer will be.
How do I achieve the same thing, but the footer height is determined by its content?
You can use flexbox to achieve sticky footer.
Using flex: 1 0 auto; to section will make it flexible, it will acquire all available free space in flex-container.
flex: <positive-number>
Makes the flex item flexible and sets the flex basis to zero,
resulting in an item that receives the specified proportion of the
free space in the flex container. If all items in the flex container
use this pattern, their sizes will be proportional to the specified
flex factor.Equivalent to flex: 1 0.
html,
body {
margin: 0;
padding: 0;
}
html {
height: 100%;
}
body {
min-height: 100%;
display: flex;
flex-direction: column;
height: 1px; /* Height hack for IE */
}
header,
footer {
padding: 10px;
color: white;
background-color: #000;
}
section {
flex: 1 0 auto; /* This will make section flexible */
}
<header>Header</header>
<section></section>
<footer>Footer</footer>
I'm trying to create a flexbox horizontal scrollable div like this.
<div class="hz-panel">
<div class="list-holder">
<img src="abc.png" width="40"/>
<p>Deals</p>
</div>
</div>
Here's the CSS for the same
.hz-panel {
background: #ffffff;
overflow-x: scroll;
display: flex;
padding: 0 3%;
}
.hz-panel .list-holder {
padding: 15px 13px;
display: flex;
flex-direction: column;
justify-content: space-between;
align-items: center;
}
Works fine on my chrome browser and Android Marshmallow webview, the problem occurs on kitkat webview where the whole scrollable list gets collapsed on condensed (one over other) since the width of every list holder becomes Zero while the padding is there. How can I avoid this problem. The parent should grow based on its children divs content. One solution is to set the min-width of list-holder div to say 54px. But there has to be a good way to avoid this.
Please Help.