0

I have a very simple CSS 100% example, that logically as I understand it, should work, but doesn't. Can someone please explain why?

HTML:

<div id="header">header</div>
<div id="nav">Nav</div>
<div id="title">title</div>
<div id="content">
    Content
</div>

CSS:

html {
    height:100%;
    padding: 0;
    margin: 0;
}
body {
    height: 100%;
    padding: 0;
    margin: 0;
}
#header {
    background-color:red;
    padding: 0;
    margin: 0;
}
#nav {
    background-color:gray;
    padding: 0;
    margin: 0;
}
#title {
    background-color:azure;
    padding: 0;
    margin: 0;
}
#content {
    background-color:antiquewhite;
    height:100%;
    padding: 0;
    margin: 0;
}

To my understanding, there should be no vertical scroll bar. Yet one appears.

Here is a fiddle to demonstrate: http://jsfiddle.net/codeowl/9wABW/

Thank you for your time,

Regards,

Scott

UPDATE:

Here is what I ended up doing:

I developed a stack and fill approach as follows. Unfortunately fiddle has an issue with me trying to access the window in java script, so I can only paste the code:

CSS:

#header {
    background-color:red;
}
#nav {
    background-color:gray;
}
#title {
    background-color:azure;
}
#content {
    background:green;
}

HTML:

<div id="header" class="stack-y">header</div>
<div id="nav" class="stack-y">Nav</div>
<div id="title" class="stack-y">title</div>
<div id="content" class="fill-y">
    <div data-role="splitter"
        data-panes="[
        { scrollable: false, collapsible: true, size: '300px' },
        { scrollable: false, collapsible: true }
        ]" 
        class="fill-y">
        <div>
            Left Pane
        </div>
        <div>
            Right Pane
        </div>
    </div>
    <div class="stack-y">Test Content</div>
</div>

Java Script:

$(document).ready(function () {
    var fResizeLayout = null;

    fResizeLayout = function() {
        var aFillElements = $('.fill-y');
        $.each(aFillElements, function (i, e) {
            var p = null,
                iPY = 0,
                iY = 0,
                iH = 0;
            e = $(e);
            p = e.parent();
            if (p.prop('tagName') === 'body') { iPY = $(window).height(); }
            else { iPY = p.innerHeight(); }
            e.siblings('.stack-y').each(function () {
                iY += $(this).outerHeight(true);
            });
            iH = (iPY - iY - parseInt(e.css('border-top-width'), 10) - parseInt(e.css('border-bottom-width'), 10));
            e.height(iH);
        });
        kendo.resize($('#content'));
    };

    kendo.init($('#content'));
    fResizeLayout();

    $(window).on('resize', function () {
        if (this.resizeTO) clearTimeout(this.resizeTO);
        this.resizeTO = setTimeout(function () {
            $(this).trigger('resizeEnd');
        }, 200);
    });

    $(window).on('resizeEnd', function () {
        fResizeLayout();
    });            
});

Of course you will need to include the kendo libraries for the kendo part to work.

<link href="http://cdn.kendostatic.com/2013.3.1119/styles/kendo.common.min.css" rel="stylesheet" type="text/css" />
<link href="http://cdn.kendostatic.com/2013.3.1119/styles/kendo.default.min.css" rel="stylesheet" type="text/css" />
<script src="http://code.jquery.com/jquery-1.9.1.min.js"></script>
<script src="http://cdn.kendostatic.com/2013.3.1119/js/kendo.all.min.js"></script>

Without the keno libraries:

HTML:

<div id="header" class="stack-y">header</div>
<div id="nav" class="stack-y">Nav</div>
<div id="title" class="stack-y">title</div>
<div id="content" class="fill-y">
    Test Fill Content
</div>
<div class="stack-y">Test Stacked Content</div>

Java Script:

$(document).ready(function () {
    var fResizeLayout = null;

    fResizeLayout = function() {
        var aFillElements = $('.fill-y');
        $.each(aFillElements, function (i, e) {
            var p = null,
                iPY = 0,
                iY = 0,
                iH = 0;
            e = $(e);
            p = e.parent();
            if (p.prop('tagName') === 'body') { iPY = $(window).height(); }
            else { iPY = p.innerHeight(); }
            e.siblings('.stack-y').each(function () {
                iY += $(this).outerHeight(true);
            });
            iH = (iPY - iY - parseInt(e.css('border-top-width'), 10) - parseInt(e.css('border-bottom-width'), 10));
            e.height(iH);
        });
    };

    fResizeLayout();

    $(window).on('resize', function () {
        if (this.resizeTO) clearTimeout(this.resizeTO);
        this.resizeTO = setTimeout(function () {
            $(this).trigger('resizeEnd');
        }, 200);
    });

    $(window).on('resizeEnd', function () {
        fResizeLayout();
    });            
});

Credit to Carlos for the resizeEnd part: https://stackoverflow.com/a/12692647/2109254

Thanks to all those that contributed.

Hopefully this can help someone else.

Regards,

Scott

Community
  • 1
  • 1
user2109254
  • 1,709
  • 2
  • 30
  • 49

3 Answers3

0

instead of using height:100% use height:auto..and it will work..:)

Leo the lion
  • 3,164
  • 2
  • 22
  • 40
  • it does not work. I am testing with Chrome and using auto on any combination of the html, body and content elements does not give me 100% height. – user2109254 Apr 25 '14 at 12:16
  • height:auto will work as in way that if you will put content then it will automatically adjust but if you will not put anything then it will remain like this..you must put something in it to use..or try to give height in px.. – Leo the lion Apr 25 '14 at 12:23
  • Ok, we agree then, height auto doesn't solve the problem. Thanks for trying ;-) – user2109254 Apr 25 '14 at 12:27
  • Hey..its basic of html..if you will have a big bag of plastic..yes it will b like 100% height but if you wont fill it inside..how will it look like..shrinked so it doesnt mean that bag is nt having 100% height so..till you wont fill..no one can solve this..sorry but its truth of HTML.. – Leo the lion Apr 25 '14 at 12:30
0

Think about what you are doing. you are telling content to be 100% of it's containing element. This would be body.

Thus, content will take up the size of the window, but you still have three other divs with height, thus total content size will = 100% (body size) + header + nav + title

If you want to fix this, you could simply make the inner contents add up to 100% and adjust the percentages to what you need. Take a look:

http://jsfiddle.net/9wABW/3/

taylorcressy
  • 966
  • 8
  • 23
  • Yes I understand what is happening now, and why the scroll bar appears. I was hoping there was an easy way to get the content div to fill the remaining space, without having the scroll bar. I don't want to use % as I want the header, title and nav to be the height of their content. – user2109254 Apr 25 '14 at 13:58
0

Edit

This will give exactly the layout you are looking for, using display:table-row in the wrapped content.

html {
    height:100%;
    padding: 0;
    margin: 0;
}
body {
    height: 100%;
    padding: 0;
    margin: 0;
}
#header {
    background-color:red;
    padding: 0;
    margin: 0;
    display: table-row;
    height:1px;
}
#nav {
    background-color:gray;
    padding: 0;
    margin: 0;
    display:table-row;
    height:1px;
}
#title {
    background-color:azure;
    padding: 0;
    margin: 0;
    display:table-row;
    height:1px;
}
#content {
    background:green;
    padding: 0;
    margin: 0;
    display:table-row;
}
#wrapper {height:100%;width:100%;margin:0;padding:0;display:table}



<div id="wrapper">    
    <div id="header">header</div>

    <div id="nav">Nav</div>
    <div id="title">title</div>
    <div id="content">
        Content
    </div>
</div>

Check your updated fiddle

You need a wrapper for the elements, depending on your specific layout you might want to play with table css attributes (display: table-row etc).

<div id="wrapper">    
    <div id="header">header</div>

    <div id="nav">Nav</div>
    <div id="title">title</div>
    <div id="content">
        Content
    </div>
</div>



html {
    height:100%;
    padding: 0;
    margin: 0;
}
body {
    height: 100%;
    padding: 0;
    margin: 0;
}
#header {
    background-color:red;
    padding: 0;
    margin: 0;
}
#nav {
    background-color:gray;
    padding: 0;
    margin: 0;
}
#title {
    background-color:azure;
    padding: 0;
    margin: 0;
}
#content {

    padding: 0;
    margin: 0;
}
#wrapper {height:100%;margin:0;padding:0;background-color:antiquewhite;}
alou
  • 1,432
  • 13
  • 16
  • Actually, strictly speaking, there is no need for a wrapper. – taylorcressy Apr 25 '14 at 12:08
  • True... but still, it's good practice for better manipulation. You should not use body for styling, imho, and wrapped classes can have all the paddings and borders and margins you want, in a standard height layout. – alou Apr 25 '14 at 12:17
  • This does not work. The content element is not 100% height. See this fiddle where I have put a bg color on it to prove this. http://jsfiddle.net/codeowl/m5VHp/ All you have done here is put all the elements in a wrapper and given that a color. It has not solved the problem. Thanks for responding anyway though. – user2109254 Apr 25 '14 at 12:19
  • @user2109254 You didn't ask for a content element to have 100% height, this is impossible without scrolling since there are already other elements on top of it. Maybe you should reconsider and clarify exactly what your want as a result. – alou Apr 25 '14 at 12:26
  • Pointing out again: what I think you want to do, is solved with a wrapper class displayed as display: table;height:100% and then having each wrapped element displayed as display:table-row; . This way, you may have specific height for header / footer and the content will cover all of the remaining space up to 100% – alou Apr 25 '14 at 12:44
  • @alou I agree with you that you SHOULD NOT use the body for styling, but the point is, is that whether or not there is a wrapper is irrelevant to the question. – taylorcressy Apr 25 '14 at 12:55
  • @alou thanks for doing the extra work on this. While this does solve the problem I posed, I also creates new ones, related to the 3rd Party Components I am using (kendoUI)... I have an idea in mind to get around this... I will need to do some testing... thanks for your efforts. – user2109254 Apr 25 '14 at 23:38