I am using reactjs and i am currently unable to expand the horizontal line that i have created below to 100% width.
This is due to the div on top of it that occupy 80% of the screen, therefore my element also has 80%.
Is there anyway that I can expand my element "the horizontal line" to 100% width WITHOUT MODIFYING it parent element?
const HorizontalLine = () => {
return <section className="line"></section>;
};
export default HorizontalLine;
css
.line {
display: flex;
flex-wrap: nowrap;
flex-grow: 1;
width: 100%;
border-top: 1px solid grey;
}
Below is the structure of the page that I am dealing with. As mentioned above I am not allowed to modify the structure of the parent page.
<div class="main-content">
<div>
<div class="page">
<div class="page-header">
<div class="page-title">
</div>
<section className="line"</section> # My element is located here
</div>
</div>
</div>
page.css
.page {
display: flex;
justify-content: space-between;
align-items: center;
flex-direction: row;
margin-bottom: 30px;
}
Ron
Please take a look here i want the line not to be on top of the blue background on the left side. So i am trying to limit as far it can go from the left.
Any help would be much appreciated.
To get the line to break out from the current section, and be fill-page-width, add these to the .line class:
.line{
position:absolute;
left:0;
}
You can additionally add width:100vw; to ensure that the line covers 100 virtual width of the page.
You can try this on .line:
flex-grow: 0;
flex-shrink: 0;
flex-basis: 100%;
but that will have an impact on the other children of .page, they will shrink
Related
I hava a page with two columns. I would like to textarea height mimic left column height. Left column is short when webpage loads, but when user starts expanding various properties (checkboxes + dropdownmenus) it grows based on hidden divs. But my textarea is still small in right column and making it staticly bigger does not look good.
I want it to grow per left column height. Not sure how to achieve that.
EDIT:
Once height: 100%; was added to textarea it solved the issue with columns growth.
But I ran into another two issues.
Textarea in right column overlaps that column on page load. When I try to resize, it suddenly jumps to the column properly. Weird behavior.
here is the pic - textarea overlaps column
Left column context is not aligned properly with right. How I am going to align or justify context of both columns so they end up like this:
here is the pic - final look
My CSS:
body {
height: 100%;
position: relative;
background: #000000;
color: #66adff;
font-size: 105%;
font-family: serif, Arial, Helvetica
}
.column {
border: 5px solid #333;
}
.container{
display: flex;
}
.columnleft {
width: 45%;
padding: 10px;
display: table-cell;
}
.columnright {
width: 45%;
padding: 10px;
display: table-cell;
}
textarea.out {width: 100%; height: 100%; box-sizing: border-box;}
EDIT 2:
Issue 1 - I had text inside the column which pushed area down
Issue 2 - all was fixed with proper padding
Thanks all for replies.
I think you could do this without js, but use CSS Grid instead.
Example:
.grid-container {
display: grid;
grid-template-columns: 1fr 1fr; // the width of each column
grid-template-rows: auto; // row height will auto-adjust to contents
}
<div class="grid-container">
<div class="column-left">
...some dynamic content
gets bigger and bigger and bigger and bigger and bigger
</div>
<div class="column-right">
might be empty or small or large
</div>
</div>
The grid row height will always adjust to the height of the largest content which will make both columns the same height.
Since you're using flex, the right column should be automatically adjusting to match the left column. It sounds like your issue is that the textarea is not expanding automatically to match its container (right column.)
If that's the case, try this simple fix - in your CSS, set textarea height to 100% to automatically fill its parent:
textarea {
height: 100%;
};
Here's an example answer:
Textarea to fill a parent container exactly, with padding
The reason your code wasn't working was because you didn't set the height to your textarea settting the height to 100% will always make it fit the maximum size of it's container (<div>) also i have added box-sizing: border-box; so that you can add padding to your columnright.
A better explanation about box-sizing can be found here (just won't explain here because i couldn't do better then this): https://css-tricks.com/box-sizing/
function f_anyEvent(){
var leftcolumnHeight = document.getElementById('columnleft').style.height.value;
if (document.getElementById('columnleft').style.height != document.getElementById('columnright').style.height)
document.getElementById('columnright').style.height = leftcolumnHeight.value;
}
document.getElementById('add').addEventListener('click', function() {
let columnleft = document.getElementById('columnleft');
columnleft.innerHTML += '<h1>a</h1>';
});
.row{
display: flex;
}
.column {
border: 1px solid #333;
}
.columnleft {
float: left;
width: 45%;
padding: 10px;
display: table-cell;
}
.columnright {
float: left;
width: 45%;
padding: 10px;
display: table-cell;
}
textarea {
width: 100%;
height: 100%;
box-sizing: border-box;
}
<div class="row">
<div id="columnleft" class="column columnleft">
</div>
<div id="columnright" class="column columnright">
<textarea></textarea>
</div>
</div>
<button id="add">
add
</button>
Every time you click add it will add an <h1> to your left column and your textarea will get the same height as columnleft.
Here's a basic demo of an interface similar to yours that uses display: grid on the parent container to automagically keep the two inner divs the same height. (Click on the blue details element to trigger a height change.)
It's wonderfully simple. (Thanks for inspiring me to finally learn how grid works.)
// The JavaScript isn't needed for the dynamic styling. (It just copies the text.)
const
left = document.getElementById("left"),
right = document.getElementById("right");
left.addEventListener("change", showOutput);
function showOutput(event){
right.innerHTML = this.querySelector("#reasons").value
}
div { max-width: 400px; border: 1px solid grey; }
details{ margin: 10px 5px; color: #0000DD; text-decoration: underline; }
/* This is where the magic happens */
#container { display: grid; grid-template-columns: 1fr 1fr; }
#left{ padding: 10px; }
#right { white-space: pre-wrap; }
<div id="container">
<div id="left">
<label> <input type="checkbox"/> I like pie </label>
<details>
<summary>Type your reasons here</summary> <textarea id="reasons"></textarea>
</details>
</div>
<div id="right"></div>
</div>
.wrapper {
border: 5px solid pink;
display: flex;
flex-wrap: wrap;
justify-content: center;
}
.a-fc {
background-color: purple;
width: 300px;
/*height: 100px;*/
}
.b-fc {
background-color: orange;
display: flex;
flex-direction: column;
/*flex-wrap: wrap;*/
flex-basis:70px;
flex-grow:1;
}
.b-fc > * {
flex-grow: 1;
flex-basis: 100px;
}
.b-fc > *:nth-child(1) {
background-color: red;
}
.b-fc > *:nth-child(2) {
background-color: blue;
}
.b-fc > *:nth-child(3) {
background-color: green;
}
<div class="wrapper">
<div class="a-fc">
<div>a1</div>
</div>
<div class="b-fc">
<div>b1</div><div>b2</div><div>b3</div>
</div>
</div>
FC = flex-container.
FI = flex-item.
I am able to place .b-fc onto a new row when the space left for it to exist on the original row goes below 70px.
My task: I want b-fc's FIs to stack vertically when no new row is created/they don't wrap. I want b-fc's FIs to align horizontally when b-fc wraps.
Current solution
In the code-snippet above, I've tried to achieve my task by writing one set of properties that work for both scenarios by setting a `flex-basis` on `.b-fc`'s FIs. If the space left for `.b-fc`'s FIs is less than this flex-basis (100px), the FIs will stack vertically. The weakness: i) if `.b-fc`'s `width`'s larger than 300px, its FIs align horizontally ii) When `.b-fc` wraps, its FIs wrap when `.bf-c` is less than 300px.
Therefore, I'm figuring it'd be more powerful to be able to apply CSS when .b-fc wraps. Is this possible?
*Idea 1: CSS variables & JS*
Perhaps using CSS variables/SASS I could continually assess whether FC - .a-fc <= than 70px. If true, apply stylings to .b-fc.
Idea 2: media-queries
Another option is to test when row2 is made, use media queries to capture this and apply CSS to .b-fc with media queries.
P.S. Similar question has been asked here before in 2015. Maybe new techniques have transpired since.
For this particular case you can consider the use of max() combined with flex-basis. The trick is to either have 0px (horizontal item) or a very big value (vertical items).
You will note that this is not a generic solution and the value is based on your html structure:
395px = 300px (width of a-fx) + 70px (flex-basis of b-fc) + 10px (border of wrapper) + 16px (default body margin) - 1px
.wrapper {
border: 5px solid pink;
display: flex;
flex-wrap: wrap;
justify-content: center;
}
.a-fc {
background-color: purple;
width: 300px;
}
.b-fc {
background-color: orange;
display: flex;
flex-wrap: wrap;
flex-basis: 70px;
flex-grow: 1;
}
.b-fc>* {
flex-grow: 1;
flex-basis: max(0px, (100vw - 395px)*100);
height: 100px;
}
.b-fc>*:nth-child(1) {
background-color: red;
}
.b-fc>*:nth-child(2) {
background-color: blue;
}
.b-fc>*:nth-child(3) {
background-color: green;
}
<div class="wrapper">
<div class="a-fc">
<div>a1</div>
</div>
<div class="b-fc">
<div>b1</div>
<div>b2</div>
<div>b3</div>
</div>
</div>
So to answer your question: No, we cannot apply CSS on wrapping (CSS cannot detect wrapping) but we can always find workaround of each case.
Similar questions:
Without media queries how to achieve 3 column desktop to 1 column mobile layout
CSS grid maximum number of columns without media queries
I'm having difficulty aligning some images inside of bootstrap 4 columns. I have tried using the CSS property text-align: center, and this will center the image horizontal. My columns take up a large amount of the view port though, so I also need the images to be centered vertical.
Here is what my react component is returning. class="img13" is what i am attempting to center.
<div id="border">
<div class="container">
<div class="row tower">
<div class="col-sm-3 towers" id="tower1">
<div class="tower-icon"><img class="img13" src={character}></img></div>
</div>
</div>
</div>
</div>
Here is the CSS that I currently have. It hard codes an image to be centered in one column, but if i change the display size for the site, or use a different image, it is no longer centered.
.row{
display: flex;}
.towers {
color: white;
height: 100%;
position: relative;
}
.tower-icon{
margin-top: 52%;
margin-bottom: 48%;
}
.img13{
height: auto;
width: 100%;
}
Start Menu here is an attached picture of what the component looks like. The background is the column, and the 'start' picture is the class="img13"
You can take advantage of flexbox and auto center align everything within the .tower-icon div like so:
.tower-icon {
display: flex;
align-items: center;
justify-content: center;
}
Just please note that the logo will horizontally and vertically center within the constraints of the column with the .col-sm-3 class.
Test link:
https://jsbin.com/sekosibizo/edit?css,output
Set the div containing the image to be the height of the viewport, then set its display property to flex. Then give the image a margin: auto.
.tower-icon {
height: 100vh;
display: flex;
}
.img13 {
margin: auto;
height: auto;
width: 100%;
}
I have catalog of 6 picture. I am showing them in 1 row. On larger screens all 6 photos shows correctly, but when i change screen width to tablet size of mobile size, picture cuts in half.
The behaviour i want is that, show all 6 pictures on larger screen, but as soon as user window size, only picture which can be shown completely in that particular screen size show show, and other should get hide. Right now, I am using overflow: hidden and container of fixed size.
Below are some screenshots to show the issue,
The question is too general but I think this would be a sample for it.
add below styles to the div wraps images.
.wrapper {
display: flex;
flex-wrap: wrap;
overflow: hidden;
// the following styles are optional but you must specify width and height
width: 100%;
height: 320px;
padding: 20px;
}
and add these styles to images.
img {
height: 100%;
width: auto;
// optional
margin-right: 50px;
margin-top: 50px;
}
The wrapper styles make that images wrap in multiple lines if they expand the wrapper width and overflow: hidden makes that only single line shows
Use width:100% on img tag in html
OR
You can use it n your style-sheet like
img{
width:100%;
}
also try to use objectfit:contain if you img has some fixed height width
here is amir mahdi digbari expanded solution in action.
You can achieve the same with css grid but flexbox is good enough for this.
.img {
height: 200px;
width: 200px;
border: 1px solid red;
}
.wrapper {
display: flex;
overflow: hidden;
width: 100%;
height: 200px;
flex-wrap: wrap;
justify-content: space-around;
border: 2px solid blue;
}
.container {
width: 1250px;
max-width: 100%;
margin: auto;
}
<div class="container">
<div class="wrapper">
<div class="img">Img1</div>
<div class="img">Img2</div>
<div class="img">Img3</div>
<div class="img">Img4</div>
<div class="img">Img5</div>
<div class="img">Img6</div>
</div>
</div>
Happy coding!
I'm pretty new to web development and I'm working on something which requires two divs to always take up 100% of the viewport.
I have div A which is an interactive image that should be as big as possible and should take up the top part of the screen.
Then div B which contains either 1 or 2 buttons depending on what action is done on the interactive div A. Div B is at the bottom of the view.
Is there a clean way to make the size of A depend on the size that div B takes up dynamically? Like just the "remainder" of the viewport should be div A. I put an image below of what I'm attempting to achieve. The second image shows what would happen if some action is done in div A - for simplicity, we could say if some method potato() is called, we want div B to now contain two buttons.
I have tried doing a solution with:
position: fixed;
bottom: 0;
and Div B looks 90% right that way, but it doesn't resize Div A and I also don't want Div B "covering" anything in this way. I just want it to be the same level as Div A and sharing the space to get 100% of the viewport.
Any help would be greatly appreciated! I'd prefer to use plain CSS if possible. I'm doing some away team work and can't add much in the way of libraries or new dependencies to the project.
check on this fiddle https://jsfiddle.net/kt931frp/1/ the trick is using flex as suggested by the below answer.
<div class="wrapper">
<div class="part1"></div>
<div class="part2">
<div contenteditable="true"class="contenteditable">continue typing...</div>
</div>
</div>
body {
margin: 0;
}
.wrapper {
height: 100vh;
display: flex;
flex-direction: column;
}
.part1 {
background:#ffff00;
flex: 1 0 auto;
}
.part2 {
padding: 2em;
color: white;
background:#ff0000;
}
.contenteditable{
width:100%;
min-height:50px;
}
Actually, this is pretty easy using Flexbox and the flex property.
You can change the padding value to see how the top block reacts.
body {
margin: 0;
}
main {
height: 100vh;
display: flex;
flex-direction: column;
}
.top-part {
flex: 1 0 auto; /* This tells `top-part` to take the remaining place. */
background: violet;
}
.bottom-part {
padding: 2em;
color: white;
background: lightblue;
}
<main>
<section class="top-part"></section>
<section class="bottom-part">
Some text here
</section>
</main>
Bringing my 2 cents, you can also take advantage of display: table|table-row|table-cell to create this layout (see the MDN documentation on display property to know more).
The trick when using these properties, unless display: flex, is to tell the "actions" cell to measure 0.1px, which will force the cell to be the minimum possible. However, it does not crushes its inner content, allowing to dynamically adjust depending the content inside.
As cells are by default sharing spaces, this does the job for this kind of layout because the "Div A" is using the rest of the available space.
Check this JSFiddle or use the snippet code below to play with it. I annoted the properties you can tweak.
body {
margin: 0px;
}
.app {
width: 100vw;
height: 100vh;
display: table;
}
.main,
.actions {
display: table-row;
}
.main > div,
.actions > div {
display: table-cell;
vertical-align: middle;
text-align: center;
border-width: 10px; /* tweak this */
border-style: solid; /* tweak this */
}
.main > div {
border-color: purple; /* tweak this */
background-color: violet; /* tweak this */
}
.actions > div {
padding: 20px; /* tweak this */
border-color: blue; /* tweak this */
background-color: lightblue; /* tweak this */
height: 0.1px;
}
.button {
width: 200px; /* tweak this */
padding: 10px; /* tweak this */
}
<div class="app">
<main class="main">
<div>
Div A
</div>
</main>
<footer class="actions">
<div>
<div>
Div B - some text and 2 buttons
</div>
<div>
<button class="button">
Button 1
</button>
</div>
<div>
<button class="button">
Button 2
</button>
</div>
</div>
</footer>
</div>
Hope it help you getting inspiration.