2

Sometimes we need to combine percentage and fixed values for dimension calculation especially when it comes to create some responsive layouts. As far as I'm concerned I've found only two ways to achieve the desired effect in pure CSS.

Problem

Let's have a quick look on the problem - we need to create a two column layout stretched to the entire width of page where one of the column has a constant width.

<section>
  <article>I fill out all the available space!</article>
  <aside>I'm 50px width!</aside>
</section>

Solution 1 - Making use of calc() function

Example: FIDDLE

The calc() function enables us to combine percentage and fixed values, for example:

article {
  width: calc(100% - 50px);
}

Unfortunately this is not cross browser solution (http://caniuse.com/#search=calc) and it is recommended to use fallbacks (http://html5please.com/#calc).

Solution 2 - Cross-browser fixed layout table

Example: FIDDLE

The width of each column in default table is calculated automatically and depends on the content of cells. In order to resolve the problem we need to force the size of the column, so another solution uses table that has table-layout property set to fixed. It enables us to set the width of any column. I've modified the HTML structure, but it can also be achieved by manipulating with display property... (ugly example: FIDDLE)

Summary

That's a very common problem in responsive world and I am very curious if there is any other ideas how to resolve it in pure CSS and HTML. Any thoughts on that will be appreciated.

Regards.

EDIT

Thank you all for your contribution!
I agree that the problem I shown was too simple :)
You can find a further discussion on that issue here.

Community
  • 1
  • 1
luke
  • 3,531
  • 1
  • 26
  • 46
  • I don't get the *ugly* for `table` layout... It's pretty robust – LcSalazar Sep 22 '14 at 22:16
  • possible duplicate of [CSS: Setting width/height as Percentage minus pixels](http://stackoverflow.com/questions/2434602/css-setting-width-height-as-percentage-minus-pixels) – Rooster Sep 22 '14 at 22:16
  • 1
    Jeez. Are you really dismissing the solution explicitly created for this problem because opera mini and IE 9 don't fully support it? Do you think there's a secret better solution? – Anthony Sep 22 '14 at 22:41
  • Use the flexbox model to have elements fill remaining space instead of having to calc() based on set space. – Anthony Sep 22 '14 at 22:53
  • This is making a very simple thing complicated. – Christina Sep 22 '14 at 22:53
  • @christina - isn't that what CSS stands for? Complicating Simple Stuff? – Anthony Sep 22 '14 at 22:56
  • 1
    Anyway, I answered it using regular old everyday CSS. – Christina Sep 22 '14 at 23:02

3 Answers3

3

That is the simplest thing to do with normal, legacy (back to ie8) support.

http://jsbin.com/moveqe/1

HTML

  <aside>Fixed width </aside>
  <section>Rest of page </section>

CSS

body,
html {
    margin: 0;
    padding: 0;
    height: 100%;
}
aside,
section {
    box-sizing: border-box;
    float: left;
    min-height: 100%;
}
aside {
    background: pink;
    width: 200px;
    margin-right: -200px;
    position: relative;
    z-index: 1;
}
section {
    width: 100%; /* this does not have to be set if it's 100% */
    background: yellow;
    padding-left: 200px;
    position: relative;
}
Christina
  • 34,296
  • 17
  • 83
  • 119
2

You could also do it by using float and overflow like this:

JSFiddle - DEMO

article, aside {
    padding: 5px;
}
article {
    overflow: hidden;
    background: #cee;
}
aside {
    width: 50px;
    background: #ece;
    float:right;
}
section {
    padding: 25px;
    background: #eee;
    overflow: hidden;
}
* {
    box-sizing: border-box;
    -webkit-box-sizing: border-box;
    -moz-box-sizing: border-box;
}
<section>
    <aside>I'm 50px width!</aside>
    <article>I fill out all the available space!</article>
</section>
Anonymous
  • 10,002
  • 3
  • 23
  • 39
  • Can't you also use negative padding or set the display of container to flex box so that all child elements are forced to fit if no width is set? – Anthony Sep 22 '14 at 22:50
  • @Anthony `flex-box` - OP wants cross browser solution and I don't think that you can set `negative` value of `padding` to an element. – Anonymous Sep 22 '14 at 22:54
  • 1
    This is too complicated too. – Christina Sep 22 '14 at 22:54
  • Define cross browser, please. Flexbox model for given example should work fine in any relevant modern browser – Anthony Sep 22 '14 at 22:58
  • @Anthony OP said for using `calc()` - "Unfortunately this is not cross browser solution" that's why I think OP don't want to use `flexbox` layout. Please read the question. – Anonymous Sep 22 '14 at 23:01
  • OP is mistaken for dismissing calc as not cross browser supported and is dreaming if they expext to find any solution that is both simple and fully implemented in all browsers for past 3 versions. We need to quit looking for 100% solutions and push the 75% solutions into common use, or they will never get past draft stage – Anthony Sep 22 '14 at 23:06
  • @Anthony I'm agree with you and you're absolutely right but I'm not the OP. – Anonymous Sep 22 '14 at 23:09
2

my 2¢ and Three ways to do it:

jsBin demo (Aside left) & jsBin demo (Aside right)

article {
  margin-right: 150px;
}
aside {
  width: 150px;
  position:absolute;
  right:0; top:0;
}


There's even a totally banal solution. You can use this simple trick:
jsBin demo and make body act as article.

body, html {
    height: 100%;
}
aside {
    float: left;
    min-height: 100%;
    width: 150px;
}


There's another smarter solution (applicable also to even more columns layout)
and that's doing it like table does:
jsBin demo

section {
  display: table;
  table-layout: fixed;   
  width: 100%;
}
article, aside{
  display: table-cell;
}
aside {
  width: 150px;
}
Community
  • 1
  • 1
Roko C. Buljan
  • 196,159
  • 39
  • 305
  • 313