Flex only for two out of three elements - javascript

I have 3 seperate elements all in one container/wrapper.
I have flex applied so the image and Text are side by side. However i want the "Scroll Down" div to be placed underneath the other two elements while still using Flex.
Is there any flex property to somehow only apply Flex on the two first elements?
Image:
https://gyazo.com/a391508e26aff2486103579134c051e1
<section class="home-section">
<div class="home-wrapper">
<div class="home-column">
<div class="home-row">
<h1>Centuries Gaming</h1>
<h2>Roleplay on a different level</h2>
<p>From the aspirations and dreams of others, we stand tall, proud, and loyal
to our visions and project. We provide the best and most immersive...</p>
<div class="home-buttons">
<div class="home-button home-button-left">
Apply
</div>
<div class="home-button home-button-right">
Read More <i class="fas fa-arrow-right"></i>
</div>
</div>
</div>
<div class="home-row">
<div class="home-image">
<img src="images/home-image.png" alt="Vehicle Drifting">
</div>
</div>
</div>
</div>
<div class="home-scroll">
<button>
<span>Scroll Down</span>
<img src="icons/mouse.svg" alt="Mouse Scroll Icon">
</button>
</div>
</section>
/* Home Section */
.home-section {
height: 100vh;
display: flex;
align-items: center;
}
.home-column {
display: flex;
}
.home-row h1 {
font-size: 60px;
color: white;
font-weight: 700;
margin-bottom: 7x;
}
.home-row h2 {
font-weight: 500;
color: #ffffff80;
margin-bottom: 20px;
}
.home-row p {
color: #ffffff80;
font-size: 14px;
max-width:600px;
}
.home-row .home-buttons {
display: flex;
margin-top: 50px;
}

If you add flex-direction: column; to .home-section then the parent element will display its children vertically. And the scroll element will be below the order elements.

You can use flex-direction:column
.home-section {
height: 100vh;
display: flex;
align-items: center;
flex-direction: column;
}
The default is row, but you can change that property to stack the elements vertically. https://developer.mozilla.org/en-US/docs/Web/CSS/flex-direction

Related

Add space and keep elements on the right side

I have these 2 children elements and I want them on the right side(I have that working just fine), but now I want to add more space between them and having a hard time to get that to work. Can someone tell me what I'm missing, please? thanks
section {
background: yellow;
display: flex;
justify-content: flex-end;
}
<section>
<button>Cancel</button>
<button>Confirm</button>
</section>
gap property can help you
section {
background: yellow;
display: flex;
justify-content: flex-end;
gap: 5px;
}
dont create more containers if you can avoid this. This is my principle
You can assign a default class to your buttons, or set a new class to your elements, and specify (for example) a margin that will be applied.
consider the following example:
section {
background: yellow;
display: flex;
justify-content: flex-end;
}
.elementContainer{
margin: 5px;
}
<section>
<div class='elementContainer'>
<Button variant="secondary">Cancel</Button>
</div>
<div class='elementContainer'>
<Button variant="primary">Confirm</Button>
</div>
</section>
This will add a 5px margin around each item with the element class.
you may change this style according to your needs.
You can use column-gap
So try this:
HTML:
<section>
<Button variant="secondary">Cancel</Button>
<Button variant="primary">Confirm</Button>
</section>
CSS:
section {
background: yellow;
display: flex;
justify-content: flex-end;
column-gap: 10px;
}

Flexbox: how to wrap a flex item once the width of another flex item is 0?

I got a flex container that contains 2 elements. Here is a JSFiddle Demo. The first one is a dynamic header with text. The second one is a wrapper for multiple dynamic buttons. Dynamic meaning the text is generated with javascript and does not have a specific width and there can be 2-4 buttons depending on the user (so I cannot set flex-basis or width to a specific amount of px on these flex-items).
I have set the overflow of the text to hidden and the text-overflow property to ellipsis.
Now I would like for the buttons to wrap to a new line only when the text has completely dissapeared. This is what I mean:
This article has led me to believe it has something to do with the flex-basis property.
The first gotcha with flex-wrap is that flex items will only begin to wrap if their sum total flex-basis is greater than the size of the flex container.
However, whatever properties I try, I cannot seem to get it to work how I want to.
.wrapper {
display: flex;
justify-content: space-between;
border: 1px solid red;
max-width: 600px;
}
.flex-wrapper {
display: flex;
min-width: 0;
}
.header {
overflow: hidden;
display: inline-block;
text-overflow: ellipsis;
white-space: nowrap;
line-height: 24px;
}
.actions {
display: flex;
/* Only wrap once the text is fully gone and not visible anymore. */
/* flex-wrap: wrap; */
}
.actions button:not(:last-child) {
margin-right: 10px;
}
<div class="wrapper">
<div class="flex-wrapper">
<div class="header">
Lorem ipsum dolar sit amet constructeur
</div>
</div>
<div class="actions">
<button>
button1
</button>
<button>
button2
</button>
<button>
button3
</button>
<button>
button4
</button>
</div>
</div>
You can approximate this by using a big flex-shrink on the first container. This will give more priority to the first container for the shrink effect.
.wrapper {
display: flex;
justify-content: space-between;
border: 1px solid red;
max-width: 600px;
}
.flex-wrapper {
display: flex;
min-width: 0;
flex-shrink:99999;
}
.header {
overflow: hidden;
display: inline-block;
text-overflow: ellipsis;
white-space: nowrap;
line-height: 24px;
}
.actions {
display: flex;
flex-wrap: wrap;
column-gap:10px; /* you can use gap with flexbox*/
}
<div class="wrapper">
<div class="flex-wrapper">
<div class="header">
Lorem ipsum dolar sit amet constructeur
</div>
</div>
<div class="actions">
<button>
button1
</button>
<button>
button2
</button>
<button>
button3
</button>
<button>
button4
</button>
</div>
</div>
You can also simplify all the code like below:
.wrapper {
display: flex;
border: 1px solid red;
max-width: 600px;
}
.flex-wrapper {
flex-basis:0;
flex-grow:1;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
line-height: 24px;
}
.actions {
display: flex;
flex-wrap: wrap;
column-gap:10px; /* you can use gap with flexbox*/
}
<div class="wrapper">
<div class="flex-wrapper">
Lorem ipsum dolar sit amet constructeur
</div>
<div class="actions">
<button>
button1
</button>
<button>
button2
</button>
<button>
button3
</button>
<button>
button4
</button>
</div>
</div>

Create a Mosiac image gallary inside a set Div

I am trying to create a pinterest style board for mobile my web application which is going to be just html, css and javascript/jquery (at the moment i'm just coding them as static pages) No frameworks such as bootstrap. It needs to work on different screen dimensions therefore need to be responsive, to achieve this I tried to use flexbox however this didnt work either
I have made an initial attempt however i'm relatively new to web development and cannot get the images stay within the "board-inner" div. As the images will be different sizes, I need them to fit
/* CSS for Login-image-holder */
.main-column-holder {
display: grid;
grid-template-columns: repeat( auto-fit, minmax(350px, 1fr));
justify-items: center;
align-items: center;
}
.column-holder {
display: flex;
flex-direction: column;
width: calc(100% - 50px);
align-items: center;
justify-content: center;
}
/* CSS for collection-holder */
.board-holder {
display: flex;
width: 100%;
border: #b2b2b2 1px solid;
height: 310px;
flex-direction: column;
}
.board {
height: 100%;
}
.board-inner {
height: 100%;
display: flex;
flex-flow: column wrap;
align-items: center;
}
.board-image {
width: 32%;
height: auto;
}
.detailer {
display: flex;
flex-direction: column;
background: white;
}
.board-inline {
display: flex;
flex-direction: row;
justify-content: space-evenly;
}
.counter {
align-self: flex-start;
}
.board-author {
align-self: flex-end;
}
}
<div class="main">
<div class="main-column-holder">
<div class="column-holder">
<div class="board-holder">
<!-- Board -->
<div class="board">
<div class="board-inner">
<img class="board-image" src="https://source.unsplash.com/HtHrjExpddA" alt="">
<img class="board-image" src="https://source.unsplash.com/Y--zr3CPaPs" alt="">
<img class="board-image" src="https://source.unsplash.com/W7QkaUbYEmg" alt="">
<img class="board-image" src="https://source.unsplash.com/4dhlFpZ0dDw" alt="">
<img class="board-image" src="https://source.unsplash.com/QMRN_GX7p4I" alt="">
</div>
</div>
<!-- detail Holder-->
<div class="detailer">
<div class="board-header">
<h3 class="header">Animals</h3>
</div>
<div class="board-inline">
<div class="counter">
<p class="count_text"><span class="counter">73</span> Photos</p>
</div>
<div class="board-author">
<p class="author_text"><span class="author">Jon Bucket</span></p>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
inside the board-inner div and resize if required.
https://codepen.io/humzaysf/pen/WNvrjGJ

Is there any other way to change styles than to override each of them?

There is really many panels on my site. Each of them has a div with items-container class and inside of it there is a few item divs (all you can see in example code below). To style them all I created "global" styles (let's call them global) which work on all panels, but there are a few I want to have different styles.
To change the styles of top-container panel, I need to copy all global styles and override every single one of them under new selector (top-container).
Is there any other way to change the styles of my top-container panel than to override each of it separately?
JS solutions are also welcome (if there are any...).
Here is a demo: LINK
And here is the code:
<div class="top-container">
<div class="top panel">
<div class="items-container">
<div class="item">Item1</div>
<div class="item">Item2</div>
<div class="item">Item3</div>
<div class="item">Item4</div>
</div>
</div>
</div>
<div class="middle">
<div class="left panel">
<div class="items-container">
<div class="item">Item1</div>
<div class="item">Item2</div>
<div class="item">Item3</div>
<div class="item">Item4</div>
<div class="item">Item5</div>
<div class="item">Item6</div>
<div class="item">Item7</div>
<div class="item">Item8</div>
</div>
</div>
<div class="right panel">
<div class="items-container">
<div class="item">Item1</div>
<div class="item">Item2</div>
<div class="item">Item3</div>
<div class="item">Item4</div>
<div class="item">Item5</div>
<div class="item">Item6</div>
<div class="item">Item7</div>
<div class="item">Item8</div>
</div>
</div>
</div>
CSS:
.top-container {
width: calc(100% - 4px);
height: 50px;
}
.panel {
border: 2px solid black;
width: 100%;
height: 100%;
display: flex;
align-items: center;
justify-content: center;
}
.middle {
width: 100%;
height: 250px;
display: flex;
flex-direction: row;
margin-top: 10px;
}
.items-container {
display: flex;
flex-direction: column;
text-align: center;
}
.item {
font-weight: bold;
}
.top-container .items-container {
display: block;
}
.top-container .items-container .item {
display: inline-block;
}
I write the styles in SASS, but jsfiddle somehow didn't work even when I changed the language.
This is a simple example. I know it's not much work to change two lines of code (in this case), but my real project is much more complicated and overriding styles = hundreds of additional lines of code...
As you mentioned !
To change the styles of top-container panel, I need to copy all global
styles and override every single one of them under new selector
(top-container).
The easiest way is to make a global class which you already did .panel. Now if you want to give any of panels a different style, either add a new class <div class="top panel panel1"> or select by child selector .middle > .left or select by nth-Child().
Here is your updated Fiddle with my example.
Hope it will answer your question.

CSS: Align children elements like 'filling up columns'

I have a div-container, which has one main image and optional multiple smaller images: http://jsfiddle.net/h5kc8ybm/
The multiple smaller images are generated dynamically, so there can be just 1 or 10 of them. On my JFiddle you can see, that the images are just displayed in one single row.
What I want to achieve is, that there are filled up 'by colomns':
First image on top next to the main image (like shown in this example)
Second image below that (not right of it, like in the example)
Third image right of first image (top)
Fourth image below third image
...and so on.
Is it possible to do that just with CSS?
Update
To avoid misunderstanding: All smaller images should be positioned right of the main image. But these small images should be displayed in two rows, filled up from first row to second row.
The main div-element will never change its height, but only its width.
Example
HTML
<div class="tnwrapper">
<div class="tn">
<img src="http://placehold.it/96x96" alt="" class="thumbnail">
</div>
<div class="tn">
<img src="http://placehold.it/96x96" alt="" class="thumbnail child">
</div>
<div class="tn">
<img src="http://placehold.it/96x96" alt="" class="thumbnail child">
</div>
</div>
LESS
.tnwrapper {
background-color: #f5f5f5;
padding: 5px 5px 5px 9px;
border-radius: 4px;
display: inline-block;
.tn {
display: inline-block;
vertical-align:top;
position: relative;
margin-right: 5px;
.thumbnail {
display: block;
padding: 4px;
margin-bottom: 20px;
line-height: 1.42857143;
background-color: #fff;
border: 1px solid #ddd;
border-radius: 4px;
}
.thumbnail.child {
width: 40px;
}
}
}
I was able to do this with the following steps:
wrap the smaller children in a div and make it position:relative
apply position:absolute on even items and reposition them
float them left
http://jsfiddle.net/0neukb08/
The downside of this approach is that it hardcodes the image's size in the "reposition" step
Additionally, the reason I chose not to use flex-box here was this issue with growing its width (I also didn't like the highest voted answer), but flexbox is a good option if you know the container's width in advance.
You probably can do this by
Rotate the container -90deg and reflect it:
.tnwrapper {
...
transform: rotate(-90deg) scaleX(-1);
}
then apply the reverse transformation for the thumbnails:
.tnwrapper .tn {
...
transform: rotate(90deg) scaleX(-1);
}
JSFiddle: http://jsfiddle.net/h5kc8ybm/1/
Note though that the height limit of the container is now width, not height (because it was rotated -90deg.
CSS flexbox styling should do the trick:
.tnwrapper {
display: flex;
flex-direction: column;
flex-wrap: wrap;
height: 200px;
}
.tn:first-child {
height: 192px;
width: 192px;
}
<div class="tnwrapper">
<div class="tn">
<img src="http://placehold.it/96x96" alt="" class="thumbnail">
</div>
<div class="tn">
<img src="http://placehold.it/96x96" alt="" class="thumbnail child">
</div>
<div class="tn">
<img src="http://placehold.it/96x96" alt="" class="thumbnail child">
</div>
<div class="tn">
<img src="http://placehold.it/96x96" alt="" class="thumbnail child">
</div>
<div class="tn">
<img src="http://placehold.it/96x96" alt="" class="thumbnail child">
</div>
<div class="tn">
<img src="http://placehold.it/96x96" alt="" class="thumbnail child">
</div>
</div>
EDIT: Sorry, the above snippet doesn't quite answer the question after all. This snippet places each subsequent image in left-to-right then top-to-bottom order, rather than top-to-bottom then left-to-right order as the question asked. I think adding a div around the first image would be the cleanest way to accomplish what you want.
I'm not quite clear on the order of the thumbnails but I think you wanta column format for those.
I that case wrap the main image and the thumbnails in separate divs and then flexbox can do the rest.
.wrap {
display: flex;
margin: 1em auto;
height: 280px;
}
.hero {
padding: 10px;
}
.sidekicks {
flex: 1;
padding: 10px;
display: flex;
flex-direction: column;
flex-wrap: wrap;
align-content: flex-start;
}
.sidekicks .item {
width: 96px;
height: 96px;
margin: 10px;
background: lightblue;
line-height: 96px;
text-align: center;
}
<div class="wrap">
<div class="hero">
<img src="http://lorempixel.com/image_output/city-h-c-240-250-5.jpg" alt="" />
</div>
<div class="sidekicks">
<div class="item">Item1</div>
<div class="item">Item2</div>
<div class="item">Item3</div>
<div class="item">Item4</div>
<div class="item">Item5</div>
<div class="item">Item6</div>
<div class="item">Item7</div>
<div class="item">Item8</div>
</div>
</div>
Codepen Demo
This is solution with flexbox and since you said that height of main-div wont change this should work http://jsfiddle.net/h5kc8ybm/13/
CSS
.tnwrapper {
background-color: #000;
padding: 5px 5px 5px 9px;
border-radius: 4px;
display: -webkit-flex;
display: flex;
}
.child-images {
display: -webkit-flex;
display: flex;
-webkit-flex-direction: column;
flex-direction: column;
-webkit-flex-wrap: wrap;
flex-wrap: wrap;
margin: 0 10px;
height: 170px;
}
.tnwrapper .tn .thumbnail {
padding: 4px;
margin: 10px;
line-height: 1.42857143;
background-color: #fff;
border: 1px solid #ddd;
border-radius: 4px;
}
.child-images .tn img {
width: 40px;
}

Categories