How to position the bottom-most container in a grid layout [duplicate] - javascript

This question already has answers here:
Fill remaining vertical space with CSS using display:flex
(6 answers)
Closed 2 years ago.
Here's a quick demo of what I have:
https://codepen.io/brslv/pen/RwobvgP?editors=1100
So, there's a .container div, which is a grid with grid-template-rows: 100px auto auto.
I need to be able to:
the whole layout should be the height of the screen (100vh), and the middle div should be scrolling, if the content gets too high.
keep the top-most div fixed height
have the middle div span the whole height of the page minus those 100px for the top div and minus the bottom-most div (which should be "fluid" and expand, depending on the height of the contents in it)
as described above, have the bottom-most div expand, depending on the height of the contents in it (in this case an autosize-able text area), but always stay on the bottom of the grid as small as possible, with, let's say min-height: 100px.
So essentially:
|------------------------------------------
| Section A: 100px
|------------------------------------------
|
|
| Section B: 100% - A - C(variable height)
|
|
|------------------------------------------
| Section C: variable height, min: 100px
| (here is the autosizing text-area)
|------------------------------------------
In my demo It's working as expected (https://codepen.io/brslv/pen/RwobvgP?editors=1100). But, if there is only one or two items in the middle div, it breaks, because the middle div isn't high enough and the bottom most compensates it, which is what I want to avoid.
I want to do it css-only, but if it's not possible I'll have to write a small JS to resize the middle one "by hand"...
Any ideas how to approach the problem with css-only?

You can change your css code and make it:
.container {
height: 100vh;
display: grid;
grid-template-rows: 100px 1fr auto;
}
What do you want is the 1fr. In this way the middle div will fill all the available empty space. See here for details about the fr unit: https://developer.mozilla.org/en-US/docs/Web/CSS/CSS_Grid_Layout/Basic_Concepts_of_Grid_Layout#the_fr_unit

Related

How to fix text overflow from a flex box [duplicate]

This question already has answers here:
Can't scroll to top of flex item that is overflowing container
(12 answers)
Closed 2 years ago.
I am working with table. height of the row and width of column can be changed (configurable). every time If height/width changes , text within the cell should be vertically/horizontally centered every time .
I have a working code with css for a cell:
{
display: flex,
align-items: center // vertical alignment
justify-content: center // horizontal align
}
The problem here is ,for the cell value 90.45678423 now If i minimize column width. then its looking like that (pic)left part getting truncated
I don't want left part of the text truncate on column Resize..and even with minimun width it shouldleft part of value shpuld be there be like .
I have achive this behavior by using css with display block: but problem with this css is , I don't have line height access at this Js code and failed to achieve vertical alignment at middle if user change row height..
{
text-align : center // horizontal align
vertical-align : 'middle' // verical align
line-height : ?
}
If you want to center the text if it is smaller than the container and align it to the left and overflow it when the text is bigger than the container, you can use justify-content: safe center;
{
display : flex;
align-items : center;
justify-content : safe center;
}

How to use innerHeight for div on both window load & resize?

I am trying to determine the top/bottom padding of a div (.content) based on it's height, and to recalculate it based on load AND resize of the window. This is supposed to align nicely centered next to another div (.character) beside it.
I've tried using CSS calc, but in this case it doesn't do exactly what I want it to do since the syntax doesn't support operators and I have a few media queries that change the size of the font based on the viewfinder, so the height of the .content div is somewhat dynamic.
Below is the JS portion, but here is the JSFiddle of what I've done so far: https://jsfiddle.net/inochiishtal/a9z13fb2/62/
$(function(){
$.w = $(window);
$.w.on('load resize', res);
res();
});
function res() {
$('.content').css('height',($.w.innerHeight()/2)+'px');
}
Any help or suggestions are appreciated. I'm not 100% dedicated to using innerHTML if there is a better solution.
It's a little unclear exactly how you want the items aligned, but based on what you said it seems like you want the .content and the .character to be vertically center aligned with each other.
In your snippet you have both of them absolutely positioned. If that's the way you want to go, you can just ignore their margins and JavaScript in general with this little vertical centering trick applied to both:
top: 50%;
transform: translateY( -50% );
The first line says "Put the top of this element 50% of the way down the element that it's positioned based on." Since it goes by the top, the second line says "Scoot me back up 50% of my height." That's just the way those CSS properties work -- the "top" % is about its parent, and the translateY % is about itself.
Since both of your elements would be vertically centered in their parent, they'd be aligned.
https://jsfiddle.net/qowxezpy/
HOWEVER if you don't need the elements to overlap like they do in this example (which I think looks nice and modern) there's a much easier way, using flex.
The parent would get:
display: flex;
align-items: center;
And the two children get:
flex-basis: 50%; //just to give them some width, since one is empty

CSS - how to force text input fill remaining space of container

I have div and inside that div are floated child divs and one text input. I need force that text input to fill remaning horizontal space and stay on same line unless some min-width condition places that input to next line. Is it possible? I don't wanna use javascript for that.
here is example (write tag and hit enter)
EDIT EXAMPLE: I have div with 300px width. It contains 3 left floated divs with various width (for instance 30, 60, 100) and one text input. I want to have that text input on same vertical position like that floated divs, so it must automatically shrink to fit remaining space (300-(30+60+100) = 110px). That text input has some min-width, so it prevents it from getting to small and in that case it jumps to next line).
http://plnkr.co/edit/sulxnvR58LnQqyI7ddFK?p=preview
You could try adding something like this:
style="width: 100%; min-width=2000px;"
http://plnkr.co/edit/uuL91pnUBkBRHMziaGBs?p=preview
Can't you just use percentage width for the input and overflow hidden?
Add this CSS
div.tag-wrapper input[type=text] {
width: 100%;
}
div.tag-wrapper {
padding: 5%;
overflow: hidden;
}

How can I have vertically fixed div element?

I would like to have vertically but not horizontally fixed div element. Currently, I am using jQuery to update the position top every time scroll occurs, but I don't want it seeing moving. I would like it to be fixed without moving. Is there a way to do this?
-----------------
| | |
| | |
| div A | div B |
| | |
| | |
| | |
-----------------
Scrolling down
-----------------
| div A | |
| | |
| | div B |
| | |
| | |
| | |
-----------------
I would like to be able keep Div B vertically fixed while Div A scrolls down and up. But when I scroll to the right and left, I wand Div A and Div B to move.
I noticed that Twitter uses something similar. Once you click on a tweet, the element on the right that display the tweet detail, is veridically fixed. I am not sure how they are doing it. See the second image, when scrolling down the right panel stays fixed.
Second image:
Twitter uses a css property: position: fixed; which sure is the best way to go.
This does exactly what it says it does, it fixes the position. By using the top, right, bottom and left properties you can set the exact position of your div.
Edit 13-12-11 (awesome date!)
The property position: fixed; can not influence a positioning property over one axis only. This means, that you can not scroll left or right, like you want to.
I highly suggest you should either avoid surpassing the screen width, using percentages for your element's width. You can also just stick to your javascript.
You could however go for the method I suggested at first, but change the left property using a scroll event listener so that when you scroll, the left offset is increased or decreased. Because jQuery's bad-ass cross-browser support I'd go for jQuery. I think you can do practically the same with the prototype library, but I'm not familiar with that library.
jQuery (worked in google chrome):
var offset = 400; // left offset of the fixed div (without scrolling)
$(document).scroll(function(e) {
// b is the fixed div
$('.b').css({
'left': offset - $(document).scrollLeft()
});
});
Have a look at the live demo
You might need to change the document object to another object or selector of your choice.
A whole lot of people want this, but unfortunately pure CSS does not offer a way to accomplish this very simple, very useful task. The only way that I have found is to give the div position:fixed. However, as you have found, this fixes the div on both the x and y axes.
This is a big failing in CSS, in my opinion. We really need something like CSS position:fixed-x and position:fixed-y. The only way I have found to do this is to have a piece of JavaScript code that's entered on a SetInterval( ) timeout (I use .10 second) that repositions the div on the axis that needs to change.
In your case (if I read your question correctly) you'd change the top: of DivB at each SetInterval( ) tick, moving DivB down to the position you want it in the viewport. Easy to do and it works, just a needless pain.
You might ask, and rightly, why you (and I) can't do this manipulation when the scroll event fires. The answer is that the scroll event doesn't fire in some versions of IE.
If you can make this depend upon scroll event cross-browserly, that would be a huge advance.
HTH.
This is easily done with the correct markup and CSS. You need a container (div, section, etc.) to contain your two content areas. In the following example, I exploit the way JSFiddle renders the fiddle's content, but the technique is the same outside of JSFiddle.
Live example.
First, we need the markup:
<div id="container">
<div id="divA">
<p>This div will scroll.</p>
</div>
<div id="divB">
<p>This div will not scroll.</p>
</div>
</div>
Next, the CSS:
#container {
height: 100%;
postition: relative;
width: 100%;
}
#divA {
background: #ccc;
height: 300%; /* So we can see scrolling in action */
left: 0;
position: absolute;
top: 0;
width: 25%;
}
#divB {
background: #c55;
height: 100%;
position: fixed;
right: 0;
width: 75%;
}
In this example, I take advantage of the fact that JSFiddle will create a view port of limited size. Thus, I can specify all of my sizes in percentages.
Notice that I set the container's position to relative. This is so that I can set the position model of divA and divB to "absolute" and "fixed" such that they will be positioned according to the box generated by "container". This is the key part of solving your problem.
use position:fixed as style and set a fixed width for div. also set top and left or right in pixel.

Side border and dynamic content help

I have two side borders on my website, left and right side... small image about 15x15 which repeats itself down the website... When setting 100% like below, the border only goes "one screen" down (which is 100%). But my website is dynamic and the content changes... I want the border to change along with the total height of the page...
How can I do this?
Here is the css:
.bgr_right {
background-image: url(../Graphics/bgr_right.jpg);
background-repeat: repeat-y;
background-position: right;
position: absolute;
top: 0px;
height: 100%;
width: 30px;
right: 0px;
background-color: #E7F5F0;
}
Here is the HTML DIV:
<div class="bgr_right"></div>
Also, is position: absolute the right thing to have?
UPDATE:
After reading the responses, I thought there has to be a better way...
How about using javascipt...
Does anybody know if there is a way to, with javascript, get the height of the body?
then:
<div height="javascript_function()" or something...
???
Thanks again
Alternativly I'd suggest to wrap another two divs around content container and repeat the background aligning it in one div to the left and in the other to the right. I.e.:
<div id="left_wrapper" style="background: url(my_leftimage.png) y-repeat top left;">
<div id="right_wrapper" style="background: url(my_rightimage.png) y-repeat top right;">
<div id="content">hello world</div>
</div>
</div>
Then if you want it to go height 100% set the html, body and the content containers to 100% height like this in the CSS:
html, body, #content { height: 100%; }
Hope this helps :)
At the risk of angry comments and loss of reputation - use a table to contain your layout. You get the full-height borders free - they will automatically adjust to the same height as your content.
<table>
<tr>
<td class="bgr_left"></td>
<td class="content"></td>
<td class="bgr_right"></td>
</tr>
</table>
If you have a fixed-width design, you could just use one background image, either on the body or on your content container, depending on the effect you want. This image would be something like:
(left bar)-> | ([x]px space here) | <-(right bar)
With repeat-y, this would give you:
| |
| |
| |
| content here |
| |
| |
| |
Then the bars will be as high as your content. If you apply this to <body>, then it will have the height of the body.
Hope this helps.
There doesn´t seem to be a reason to use a separate div for the background as it´s empty, but it depends if the column width is fixed.
You should apply the background image to the div you want to have a background, that way you can be sure that it will continue below as the div grows.
If your column width is fixed, you
can just combine the left and right
image in a very wide image that will
only repeat vertically.
If your column width is variable,
you can have for example the left
background in the growing div and
the right one on a wrapper div that
contains the growing div.
Using the right padding you will get the effect you want.

Categories