Capt. Horatio T.P. Webb
 
RESPONSIVE WEB DESIGN
Parks -- Spring 2016

 

The principle issues of responsive web design involves dealing 'responsively' with: web page layout; screen size; orientation and navigation across a variety of 'devices' such as: mobile (smart phones), pads, tablets and personal computers.

This is no small task and often has been approached by building multiple web pages -- one for each type of device. Clearly there should be some unifying technologies or techniques that allow a single web page to detect and respond to the many variations. The two most cited contribution to this discussion are two books:

These both qualify as required reading. Over the past five years various other authors and developers have honed this topic along various dimension of technology and design -- but the principles from the two works above are generally accepted.

How is this to be done? With CSS!

This sequence of topics in this course necessitates having covering the basics of HTML, then CCS and lastly Responsive Design. So having finished these essential elements we can now turn our attention to responsiveness.

  1. liquid (aka fluid)

    The address the issues of various screen sizes (i.e., screen resolutions) across a variety of devices, the central issues is to be able to adjust the size of things relative to the space available. Traditional page layout designs used fixed pixel measurements to size the web page elements (e.g., ...style="width:200px;"...). Any element using this fixed pixel dimension would, however, consume different amounts of the screen real estate on different devices with various pixel resolutions. The CSS attribute that allows to easily address this issue is to specify a page element's size using a percentage rather than a fixed pixel width (e.g., ... style="width:20%; ...). This could apply to an element's size properties: like width or height as well as an element's page location like top or left or an element's characteristics like font-size, border-width, etc.

     For example, use this slider to change the size (using width:some_number%;) of the image below:

    Width: 15% 50%

     HTML element for the image below is now:

    <img src="ballpit.jpg" id="bp1" style="width:;">

    Note that if you change your browser window size the image changes size -- and maintains the same relative screen area.

    CCS3 provides some addition measurements to assist in sizing HTML elements.
    There are four useful viewpoint attributes: vh; vh; vmin; and vamx.

    1. some numbervw

      means viewport width percentage:
         e.g., 1vw is 1% of viewport width
      means viewport width percentage:
         e.g., 1.8vw is 1.8% of viewport width

    2. some numbervh

      means viewport height percentage:
         e.g., 1vh is 1% of viewport height
      means viewport height percentage:
         e.g., 1.8vh is 1.8% of viewport height

    3. some numbervmin

      means the smallest viewport percentage which ever is smaller of vw or vh:
         e.g., 1vmin is 1% of viewport width or height whichever is smaller

    4. some numbervmax

      means the largest viewport percentage which ever is larger if vw or vh:
         e.g., 1vmax is 1% of viewport width or height whichever is larger

    This browser viewport values are currently:

    Note below what would happen if we used a border.

    The offset width is two pixels larger since .offsetWidth includes the border. See the box-sizing correction below.

    And additional use of these viewport attributes is the sizing of fonts for readability. Various authors discuss this:

    Let us take Xavier's recommendation and note that the font-size for the body of this document is:

    font-size:1em;
    Choose Line Width: 23em 37 em
    Current Width:   30.0 em
    Byte Count:
    Approximate Line Count: lines

    Lorem ipsum dolor sit amet, consectetur adipiscing elit. Phasellus pulvinar, justo quis tincidunt accumsan, lectus risus facilisis urna, sit amet convallis ex eros nec massa. Nam eros eros, venenatis ut tristique volutpat, ornare eget dolor. Aenean auctor volutpat accumsan. Etiam ut lectus iaculis, hendrerit turpis ut, pulvinar velit. Pellentesque habitant morbi tristique senectus et netus et malesuada fames ac turpis egestas. Nam dui tellus, fringilla sed rutrum interdum, convallis vel dolor. Nam rutrum, orci lacinia aliquet faucibus, erat lectus luctus neque, in finibus arcu lorem vitae sapien. Sed convallis augue arcu, non sagittis nunc consectetur non. In sed euismod erat, non pulvinar sem. Praesent maximus neque sed eros convallis egestas.

  2. media queries

    A CSS media query is essentially an "if statement" that tests a condition. If the condition (query) is true then specific CSS is applied.

  3. Layout Options

    Central to any webpage layout is the the spatial organization of page elements. Responsive design utilizes several techniques to arrange the page elements. The three common issues are:

    1. Grid Layout using negative margins
    2. Grid Layout affected by box-sizing: border-box
    3. Grid Layout using flexbox

    These approaches use CSS to accomplish the layout task. Others approaches are available (e.g., javascript control of CSS properties) but these are the ones most common discussed.

    1. Grid Layout using negative margins

      EXAMPLE THREE COLUMN GRID

      CENTER DIV BLOCK

      outer DIV CSS for all three DIVs:

      float: left;
      width: 800px;
      background-color: #eeeeee;
      border:solid DarkGreen 1px;

      this center DIV CSS:

      padding: 10px;
      background-color: #ddffdd;
      margin: 0 200px 0 160px;

      The two margins chosen for this center DIV must match widths of the left DIV and right DIV. In this case:

      • the right margin is 200px
        and matches the width of the right DIV.
      • the left margin is 160px
        and matches the width of the left DIV.

      Note: this grid layout will fail if the browser window provides less than a 800px width for the grid.  

       

       

      RIGHT SIDE DIV

      this DIV has CSS:

      float-left;
      width:190px;
      padding:5px;
      margin-left:-200px;

      Note that the total width = 200px
      [width+2*padding]
      [190px + 2 * 5px]
      and the right margin of the center DIV is also 200px.

      Note negative 200px
      left-margin shifts
      this DIV an amount
      equal to its width

       

      LEFT SIDE DIV

      this DIV has CSS:

      float-left;
      width:150px;
      padding:5px;
      margin-left:-800px;

      Note negative
      left-margin shifts
      this DIV all the
      way to the left

      Note that the total width = 160px
      [width+2*padding]
      [150px + 2 * 5px]
      and the left margin of the center DIV is also 160px.

       

    2. Grid Layout affected by box-sizing: border-box;

      The box-sizing issue arises because of the way the actual width and height of a box element is calculated. Normally the actual total amount of horizontal/vertical space consumed by a HTML box element such as a DIV block is:

      content width (or content height)  + 2 * padding + 2 * border-width + 2 * margin

      The content width (or content height) is used for reporting the height and width specification -- just the content alone. Normally the padding and border size are not included in the width/height values.

      Fine adjustments to the attributes create difficulties when precise calculations are needed to maintain the layout. To simplify the calculations (and hence the design issue), the box-sizing: border-box feature was added.

      When this CSS attribute box-sizing:box-border is employed the width and height values include:

      content width (or content height)  + 2 * padding + 2 * border-width

      As its name implies, the width and height measurements are calculated and reported differently based using the box-sizing:box-border -- it is not traditional CSS width and height.

      Consider:

      This DIV with id='bx1' has:

      width:300px;
      padding:20px;
      border:5px solid black;

      javascript reports width=

      This DIV with id='bx2' has:

      width:300px;
      padding:20px;
      border:5px solid black;
      box-sizing:border-box;

      javascript reports width=

      This CSS box-sizing:box-border changes what width and height of the box elements mean and how it is calculated.

    3. Grid Layout using flexbox

      Before beginning there a few new HTML 5 tags we should review. They are called "semantic" elements. These elements refers to the fact that the tag name is an indicator of the type of content they content. They perform no function that is different from a DIV block -- they just have tag name that 'indicate' the type of information they contain: the semantic tags are:

      • <article>...</article>
      • <aside>...</aside>
      • <details>...</details>
      • <figcaption>...</figcaption>
      • <figure>...</figure>
      • <footer>...</footer>
      • <header>...</header>
      • <main>...</main>
      • <mark>...</mark>
      • <nav >...</nav>
      • <section>...</section>
      • <summary>...</summary>
      • <time>...</time>

      The tags may have an id="some_name" and be styled like any other box element. They perform no transformations on the data they contain.

      Here is our page content to be used as a flexbox

      <header>head</header>
        <div id='main'>
              <nav>navbar</nav>
              <article>content</article>
              <aside>aside</aside>
         </div>
      <footer>foot</footer>

      Our first task is to provide an element for the flexbox container. We will use the semantic tag:

      <main id="main">...</main>

      for our container and provide the optional id="main" (to avoid conflict with other examples on this page).

      We wish to layout our three content components of the main in order, side-by-side across one row. This will be accomplished by using the property flex-flow:row (the alternative is to lay them out in a column -- i.e., stack them on top of one another -- and the CSS would be flex-flow:column;).

      Our minimal CSS for the flexbox container is:

      #main {display:flex
              flex-flow:row;}

      For our three content parts of main

      1. nav

        The relevant css required is:

        #main > nav {
                flex: 1 6 20%;
                order: 1;}

      2. article

        The relevant css required is:

        #main > article {
                flex: 3 1 60%;
                order: 2;}

      3. aside

        The relevant css required is:

        #main > aside {
                flex: 1 6 20%;
                order: 3;}

      The two useful CSS properties here are:
      1. flex

        flex is a composite property of three other specifications:

        1. flex-grow

          Specifies the the amount of space inside the container that the item should grow relative to the other items in the container. The value is a number which is compared to the other the sum of all flex-grow values for all the components in the container. For example, if there are three components with flex-grow values of 2,3, and 5, the the first has 2/(2+3+5) proportion of the space, the second would have 3/(2+3+5) proportion of the space, and the third would have 5/(2+3+5) proportion of the space.

          In our example the three flex-grow values for the components: nav, article and aside) are 1,3, and 1, respectively yielding a space usage of: 1/6, 3/6, and 1/6.

        2. flex-shrink

          Specifies the the amount of space inside the container that the item should shrink use relative to the other items in the container. The value is a number which is compared to the other the sum of all flex-shrink values for all the components in the container. For example, if there are three components with flex-shrink values of 2,2, and 4, the the first would shrink to 2/(2+2+4) proportion of the space, the second would shrink to 2/(2+2+4) proportion of the space, and the third would shrink to 4/(2+2+4) proportion of the space.

          In our example the three flex-shrink values for the components: nav, article and aside are 1,3, and 1, respectively would shrink the components to: 1/6, 3/6, and 1/6 of the space.

        3. flex-basis

          Specifies the initial length of the component stated as a length of measure (like 10px) or a percentage.

          In our example the three flex-grow values for the components: nav, article and aside) are 1,3, and 1, respectively yielding a space usage of: 1/6, 3/6, and 1/6.

      2. order

        Specifies the ordinal order in which the items are placed into the container. The first is 1, followed by 2, etc.

      Below is the resulting layout produced by the flexbox specifications.

      head
      content

      Lorem ipsum dolor sit amet, consectetur adipiscing elit. Duis leo diam, faucibus a dolor vel, luctus imperdiet justo. Etiam malesuada tortor ut condimentum vehicula. Integer finibus quam iaculis tortor consectetur facilisis. Donec posuere nunc vitae augue sagittis cursus. Interdum et malesuada fames ac ante ipsum primis in faucibus. Class aptent taciti sociosqu ad litora torquent per conubia nostra, per inceptos himenaeos. Nullam blandit, purus vitae tincidunt accumsan, erat mi laoreet tellus, non accumsan arcu tellus eu ante. Aenean vel massa dolor. Donec pellentesque efficitur ligula, eu placerat metus blandit at. Phasellus laoreet volutpat risus in hendrerit. Donec gravida dui a ante pulvinar, et luctus ante fringilla. Praesent in lacus ultrices est tristique tempus sit amet porta felis. Morbi viverra urna quis sapien egestas, at placerat ligula mollis. Nulla bibendum iaculis interdum. Morbi tempor, mi eu suscipit hendrerit, ex est egestas nisl, a venenatis tellus quam nec nulla.

      Duis nec volutpat massa. Quisque eget enim nec ante viverra egestas. Pellentesque maximus vulputate enim, non consequat diam. Morbi sagittis faucibus eros, in aliquam nisi posuere sollicitudin. Aenean non efficitur risus. Maecenas semper magna vel arcu bibendum feugiat. Aliquam sed rutrum nisl. Nam metus odio, accumsan eget velit quis, porta tincidunt eros. Curabitur facilisis, tellus non sollicitudin semper, nisi felis varius sem, eu condimentum ex purus hendrerit orci. Sed commodo magna sapien, non consequat eros porta et. Nam libero magna, auctor eu nunc et, fringilla cursus sapien. Morbi dictum lobortis felis, eget venenatis orci maximus sed. Fusce eu risus eu purus lacinia gravida quis et justo. Nullam semper dolor non feugiat luctus.

      foot

      As you are probably viewing this in a browser, if you narrow the browser viewport you will see the flexbox layout change organization as the once the visible window is in narrower than wide (portrait).The CSS that accomplished this utilized a media query to capture the max-width condition:

      /* Too narrow to support three columns */
      @media screen and (max-width: 640px) {

      #main, #page {flex-direction: column;}

      #main > article, #main > nav, #main > aside {
      /* Return them to document order */
              order: 0;}

      #main > nav, #main > aside, header, footer {
              min-height: 50px; max-height: 50px;}

      #main > article, #main > nav, #main > aside { /* to fix ie bug */          flex:1 0 auto;}

      /* http://stackoverflow.com/questions/26596813/internet-explorer-doesnt-honor-my-min-height-100-with-flexbox */
      }

      Most important in the above CSS is the detection of narrow width by the media query which:

      1. changes the layout from adjacent components in a row to components stacked in a column:

        flex-direction:column

      2. set the heights for all components except the article:

        #main > nav, #main > aside, header, footer {
           min-height: 50px; max-height: 650px;}

      3. returns the order to that specified in the HTML document

        #main > article, #main > nav, #main > aside {order: 0;}

      4. fixes an IE bug:

        #main > article, #main > nav, #main > aside {flex:1 0 auto;}

        see this

The entire process of responsive design has received a considerable amount of attention and been largely attributed to the original proposals made by:

  1. Ethan Marcotte's 2011 book Responsive Web Design (now in 2nd edition)
  2. Luke Wroblewski's 2011 book Mobile First

The features of the CSS-based are constantly in flux and are being updated and modified rapidly. This approach is very popular and will continue to impact the web design. And flexbox is clearly the superior way to do this.

But there are other viewpoints. See e.g,:

These are but a few of the many criticisms. I have some of my own.


Much of this page and its examples are based on Mozilla Development Network's and specifically their
flexbox page