Javascript – Dynamically Resize Text Based on Container Width

font-sizejavascriptjqueryresponsive-design

I'm working on a responsive design and I have some display <h3> tags that I would like to scale down when the width of the browser window is reduced.

The initial setup, based on a width of 960px:

  1. The body font-size is set to 14px
  2. The font-size of the h3 tag is 40px
  3. The width of the containing div is 230px

So here's what I worked out for the javascript/jQuery:

$(window).resize(function(){
    var containerSize = $('.container').width();
    var textPercentage = 0.17391304347826086956521739130435; /* 40/230 */
    var textRatio = containerSize * textPercentage;
    var textEms = textRatio / 14;

    $('.container h3').css(fontSize,textEms+"em");
});

My javscript skills are obviously quite limited, so I was hoping you could help me get this all purdy and working right. I think the $(window).resize function is the wrong event to use, since the text should resize automatically on page load, not just on window resize.

Thanks in advance for the help!

Note: I don't want the text to stretch to the edges of the containers, which is why I'm not using FitText.js or BigText.js.

Best Answer

window.resize is the correct event but it doesn't fire on page-load. You can however just add .trigger('resize') to your code to make it fire on page-load:

$(window).bind('resize', function(){
    var containerSize  = $('.container').width(),
        textPercentage = 0.17391304347826086956521739130435, /* 40/230 */
        textRatio      = containerSize * textPercentage,
        textEms        = textRatio / 14;

    $('.container h3').css(fontSize, textEms+"em");
}).trigger('resize');

You are going to want to run this code after document.ready to make sure the width you are getting for the container is correct. You could also place this code at the bottom of your HTML document (which you should do with or without the document.ready event handler) which will make sure the elements are available when you run this code:

//wait for `document.ready` to fire
$(function () {

    //cache the .container and H3 elements
    var $container = $('.container'),
        $h3        = $container.find('h3');

    //bind event handler to `window.resize`
    $(window).bind('resize', function(){

        //get the width of the container
        var containerSize  = $container.width(),
            textPercentage = 0.17391304347826086956521739130435, /* 40/230 */
            textRatio      = containerSize * textPercentage,
            textEms        = textRatio / 14;

        $h3.css('fontSize', textEms+"em");
    }).trigger('resize');
});

Notice that I cached the H3 element(s) so it/then don't have to be selected every resize event, because when you actually re-size your browser there are tons of these events that fire.