Best practice way to handle variable content margin? - html

Ok, so a quick site that I am throwing together for a friend has about 20 static pages. Each one with a small amount of content. the div Container contains, well, the div Content, and the div Content contains, obviously, the content that changes on each page.
Now, depending on the length of the content, I want a different margin at the top. The less content, then the larger the margin. Simply an aesthetic choice. For example, if the content almost fills the static sized container, there is less padding, but a 1 line page of content might be 1/3 of the way down the static container. Centering the content in the div wont do, as that creates too large of a margin.
Whats the best way to handle this? A new class for each content with a different margin? A new Id, so that it is in its own special div positioned or margined differently? Inline css on each page to override the standard css for div Content? A differnt spacer div inside Container before Content on each page? Some sort of scripting along the lines of margin of Content = (ContainerHeight - ContentHeight) / 3?
Whats the acceptable way of doing this? I don't want to get into bad habits.

If javascript is an option, you can calculate the height of your content box and set a top margin according to the formula you prefer.
In jquery it would be something like:
c_height = $("#Content").height();
c_margin = Math.floor( /* your formula */ );
$("#Content").css("margin-top", c_margin + "px");
(not sure about the "px" part...)

I would go the simple route, and define a single upper margin globally, with inline CSS to override it in pages that need it. Suppose you wind up editing one of the one-line pages to add more content - in that case you'd presumably would want to change the layout for that page and no other, so that change might as well be right there in the page itself.
On the other hand, the pages might feel more usable and consistent if you pick, say, three margin sizes and assign each page one of them based on how much content it has. Then, when you expanded a one-liner you might simply change its class from the small margin to the medium, so putting classes like div.smallVMargin into a central style sheet would make sense. What you want to avoid is an external CSS file with classes like div.page16 or div.margin25px.

Related

Elements in CSS Grid Column, top margin behaves as position top

Difficult to come up with a good title - by all means, change if you can.
Traditionally, a margin on an element can be used to move elements around a page relative to its previous elements. So, if I had a div as a column on my page I could shift elements vertically within that by setting their top-margin CSS property.
This is handy in dynamic pages where some elements might not exist according to given condition, eg, a very simple example here:
https://jsfiddle.net/jhartnoll/4s6pcLu0/1/
I have simply defined a column with a div element, positioned two other div elements and made one of them have a 2em vertical gap between it and its predecessor.
If you remove (or set Display:none) element #one then element #two is shifted up the column and positioned 2em from the top of the column, rather than 2em from element #one which is no longer there.
However, if I try to do a similar thing using a CSS grid, thus making the DOM tree simpler and more flexible, I run into a problem:
https://jsfiddle.net/jhartnoll/xvhycg0k/11/
In this case, the columns are set by the CSS grid so are sort of pseudo columns, but when I set my elements to have margin-top: 2em the margin is calculated from the top of the grid column, not relative to a predecessor element.
Therefore, if element #one is not present, #two simply remains 2em down from the top leaving a gap above...
This behaviour renders margin-top useless, because it is exactly interchangeable with top on relative positioned elements.
Is this a bug with CSS Grid, or am I using it wrong, or is there a way around this?
CSS Grid seems great, but I have run into several problems like this where dynamic content is concerned, if elements have potentially variable heights, or may not be there at all, the Grid leaves other elements floating in space, unable to shift up.
EDIT for clarity of the dynamic problem
Thanks for the comments so far. The problem is not with using the layout, I understand how to set up grids, and rows, define sizes, spaces, span etc, the problem is with dynamic content.
Supposing I have an extremely simple product page:
https://jsfiddle.net/jhartnoll/xvhycg0k/42/
Irrespective of the grid spacing, row/column size etc, the concept is simply that I have thrown in a "Price reduced by 10%" splash element above the product title.
Naturally, product pages would be using templates and therefore the HTML and CSS should be fixed and flexible enough to enable elements to be missing or present.
Not all product pages will display the 10% off deal, so on those pages, I would want the Product Title to shift up into the top element position.
This, as far as I can tell, cannot be achieved with grids.
Similarly, if there was a div which contained a product description and underneath it some product cross promotion or something, the description might be of variable length, so with the div as a column example in the my original question, the content would automatically expand the description grid and shift the cross promotion stuff down the page. Again, this can't be achieved with grids?
So, I was messing around with using a grid defining columns only and simply one row per page so that content could be stacked in columns similarly to the original div as a column example, but then I ran into this margin-top problem which, within a Grid is that margin-top is relative to the grid top, not to the elements above.
So I can't find a way of creating a dynamic website, using a template design which allows for conditional elements and variable element dimensions using Grid and without using Javascript to manipulate on page load.
In my mind, there should be an option for a row-shift property to allow elements to jump down a row if the content is too large, or jump up if there is nothing obstructing it... or something like that anyway!
Hey try the following code I guess it will help your requirement!
#column{display:grid;grid-row-gap: 10px;width:4em;height:auto;border:1px solid grey;}
#one{background:red;width:2em ; height:2em}
#two{background:blue;width:2em ; height:2em}
<div>
<div id="column">
<div id="one">
</div>
<div id="two">
</div>
</div>
</div>

How height is calculated without setting it

I'm trying to get more efficient with building responsive websites and since I'm using Bootstrap (not particularly important for this case - I believe), I was looking into Bootsnipp. I decided to view the site's source and noticed one thing I've never seen before: they did not set a height for any of their containers except for the whole page wrapper and the footer. This baffles me because everything falls into place with the website and it's super repsonsive. I understand the elements where they use Bootstrap's classes like "col-sm-4" and whatnot but does anyone understand the art of making the header, a content container, etc calculate heights without specifying in css? Can anyone explain this concept? I tried Googling but not sure of the correct keywords to find answers.
Also, if you need to see yourself, here is the link to their CSS.
Thanks
Understanding the Box Model is important. As an (overly simplified) rule of thumb, you can think of it like this; there are 2 primary types of elements: inline (span, b, strong, ...) and block (div, p, ...).
Block tags by default are width: 100%. That is to say they will naturally stretch to fill their horizontal area.
Inline tags you can think of as being constricting. They shrik to fit the size of their inner elements. This makes sense when you think of a bold tag: it is not unlike highlighting the text you want to be bold. It stays small to fit the content.
In both cases, though, unless you specify a height, both block and inline tags will shrink their height to fit their inner elements. Because of this, you can think of a website as being a bunch of elements stacked on top of each other, where the top of the page is the bottom of the "stack".
Here is an example of divs without specified heights having their heights changed by the size of the interior content. http://jsfiddle.net/S3q2C/ Notice all the divs have a border to easily see its relative size.
If you don't set an explicit height, containers will automatically grow to fit the content (respectively). Sometimes this is desirable, other times not (think overflow hidden). A possible reason why people use explicit heights in containers could be because of absolute positioning, or if they want to align a nested element that is 50px tall, with another that is 200px tall. An explicit height could also be used to maintain perspective say for a picture or other element (maybe a series of elements). While this answer is the end all be all you might be looking for, the key thing I'm trying to pass along is that an explicit height is used when needed, not all the time.
Here's a quick demo showing you two <div> containers, one with a height set, and another with no height.
http://jsfiddle.net/xrZ73/1/

CSS & Nested Divs - Parent Div Won't Take Child Height, Overflow:auto not a good fix

The Context:
I'm building out a div roster to use with jQuery or PhP for my roleplaying Star Trek Fleet (nerdy, yes, I know). I need my divs to behave in certain ways to make it robust enough to pull from XML and generate the roster automatically and auto-size my divs to fit however many names are added.
It will help to take a look at my current build example with Firebug/the like to understand what I'm doing.
Requirements:
Each subsection (Outpost Personnel, Outpost Defense), needs to have a number of divs:
1) The background image & subsection container (div id= outpostPersonnel in this example)
2) Sub-sub section container for each side of the listing, left and right. (Think newspaper paragraph.)
3) The top n number of roster names needed to fill/align to that background image in requirement 1. (div id= initialCommandTags (left side listing) and initialPersonnelTags (right side listing))
4) Div that stretches with n number of additional roster names. (div id = overflowCommandTags, overflowPersonnelTags, )
5) A colour div stripe to make it look like LCARS is still encapsulating the n number of roster names from requirement 4. (div id = colorStretchLeft)
The Problem:
I cannot get the parent subsection- the div from 1 (outpostPersonnel) to adhere exactly to the height of ALL its child divs- all the way down to the height of the overflowCommandTags/overflowPersonnelTags div.
One way I've tried it, and the next subsection (Outpost Defense) overlaps the overflowCommandTags div. The other- which is the way I have my example now (and where I gave up)- puts a ~160 pixel high blank space between the end of the overflowTags div and the top of the next subsection (outpostDefense).
If you firebug my current build example, you'll see that the parent div (outpostPersonnel) extends way the heck down, even though none of its child divs are that tall.
Overflow:auto and Overflow:hidden are NOT viable solutions insofar as I have read, since I need the divs to expand fully, and WITHOUT a scrollbar.
I'm completely stumped. Watch it be a really simple solution, too. Is it something to do with the fact that the parent div is only a BG, while the child divs have actual content?
Thank you for bearing with me this far!
Cheers!
((Also the reason why my div style stuff is in-line is because I'm embedding this on an Enjin page and I can't call a *.css file.))
There are a few things to mention here but I'll start with the reason for the gap in between the two sections.
From what I can see from your inline styles you have used position: relative and varying top andleft values to achieve the desired layout. On the element with ID personnelContainer you have added top: -230px. This is what is causing the gap.
When you position an element relatively you have to imagine that the element is in its original position and that you've just visually moved it. In other words, moving the element does not change the flow of the page, so applying the negative top value as in your example will not change the height of the container. (good reference: http://reference.sitepoint.com/css/relativepositioning)
With this in mind, you could go the route of applying minus top values to each of the sections that follow in order to close the gap, however you are likely to find that this complicates matters further and leads to overlapping content.
The best advice I can give is to read the following articles on floated layouts:
http://css-tricks.com/all-about-floats/
http://www.quirksmode.org/css/clearing.html
Relative positioning has its applications but in this case you should use the float property to achieve your layout. If you read the articles above it will give you a good grounding in floated layouts and how to ensure your sections contain everything correctly. As long as you don't set any fixed heights on any of the child elements you will find they expand to accommodate any amount of content.

HTML/CSS - 3 columns that resize

I am building a very simple page, powered by tumblr.
It has 3 columns of content in the main area. The content divs are all set to a width of 33% and floated left, most of the time this arranges itself as you would expect, but as you resize the window it seems to sometimes revert to 2 columns. Anyone know how to solve this?
The html is here: http://emilestest.tumblr.com
Try to set the .item css width to: 32%. The browser probably miscalculates width sometimes so you probably have a extra pixel or two, so the float overlaps to next line.
There is a Javascript action involved. Your article html elements gets the absolute position and some coordinates. Have a look over those scripts (or disable them, in order to use only CSS for positioning).
In your specific case, there are several solutions:
Place + size the divs with JavaScript and disable CSS layout
Use display: table
Use a table element
Disclaimer: For all those who cry out when they read table:
Using divisions to simulate a table for the display of tabular data is as much a design flaw as using tables to control graphic and page layout.
Source: http://en.wikipedia.org/wiki/Tableless_web_design#The_use_of_tables

div with content overflowing container

I have an <article> element with three children: a header, a content div, and a footer. The article is absolutely positioned with height and width set, so that it fits nicely into a grid of articles. The header has some variable content, such as the article title, date, etc. and is allowed to expand as it needs. The footer is absolutely positioned within some space set aside in the article by padding the bottom of the article. The content div, however, refuses to play nicely.
What's happening is that the grid_content div just takes up however much space it needs to accommodate its content, overflowing the <article> element as it does so. I'd figure out some explicit height to set on it, but both the <article> height and the header height are variable, depending on how many spaces it takes up in the grid and what the article title is, respectively.
Is there some clean way to get the div to respect its containment, or will I need to do some ugly JS hacks to get it to stay put?
Thanks!
http://jsfiddle.net/j2fE4/
OK, so I did manage to solve this, but the solution was a two-part deal involving JavaScript.
First, I used some custom JavaScript to calculate the appropriate height for the .grid_content elements, pasted here for reference. The solution isn't general to other projects, but should illustrate the thought process.
function resizeContentElements() {
$('div.grid_content').each(function(i, element){
var $element = $(element);
var parentHeight = $element.parent().height();
var elementPadding = parseFloat($element.css('padding-top')) + parseFloat($element.css('padding-bottom'));
var siblingSpace = $element.prev().height() + parseFloat($element.prev().css('padding-top')) + parseFloat($element.prev().css('padding-bottom'));
$element.height(parentHeight - siblingSpace - elementPadding);
});
}
After that, I grabbed http://dotdotdot.frebsite.nl/ and applied it to the div.grid_element collection. Everything is getting ellipses just fine, though the point at which the content gets cut off with ellipses does not seem that even, yet. My best guess is that the irregular (and often invalid) markup in those containers is messing with it.