jQuery Text Slider

Use the jQuery UI to Control the Size of Your Text

JQuery’s UI can add so much to a web page. There are many different widgets that the UI provides. One up and coming star, is the slider. In this tutorial, I will show you how to use a slider to control the text size of an article on a page. This lets the user control exactly the size that suits them, and is also a pretty impressive feature to have on a site!

The slider portion of this tutorial reproduces a technique originally created by Buck Wilson.

Our Goal

We will eventually want our page to look something like this:

Behavior:

  • When the slider is dragged, a bubble will fade in, telling the current size.
  • The text "current text size" will also appear with the current text size next to it.
  • We will also attempt to make the text increase one px or decrease one px on the click of the plus or minus sign.

preview

Step 1: Getting the Necessary Javascript Files

Obviously we need JQuery, but we’re also going to need some UI files to extend JQuery. We can get a UI file that is custom to our needs at the JQuery UI Build Your Download page.

JQuery UI Download Page

As you can see, there are some really great sounding effects there! As tempting as it may be though, we don’t need all of these effects to achieve the desired product. All we need is:

Step 2: The HTML

For this tutorial, I’m not going to waste time explaining the basics of HTML, and creating a layout using it and CSS. If you’d like to learn more about that, there are other tutorials here like my Top Panel tutorial or Collis’ Tabbed Content tutorial.

<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01//EN"
   "http://www.w3.org/TR/html4/strict.dtd">
<html lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<title>Nettuts Slider</title>
<!--[if lt IE 7]>
<script src="http://ie7-js.googlecode.com/svn/version/2.0(beta3)/IE7.js" type="text/javascript"></script>
<![endif]-->
<script type="text/javascript" src="http://code.jquery.com/jquery-latest.js"></script>
<script type="text/javascript" src="scripts/jquery.ui.js"></script>
<script type="text/javascript" src="scripts/cookie.js"></script>
</head>
<body>
<div id="header">
  <div class="slider_container">
    <div class="minus"></div>
    <div class="slider_bar">
      <div id="slider_caption"></div>
      <div id="slider1_handle" class="slider_handle"></div>
    </div>
    <div class="add"></div>
  </div>
</div>
<div id="text">
  <h1>Text Size Slider</h1>
  <div id="font_indicator">Current Font Size: <b></b> </div>
  <p> Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into electronic typesetting, remaining essentially unchanged. It was popularized in the 1960s with the release of Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like Aldus PageMaker including versions of Lorem Ipsum. </p>
</div>
</body>
</html>

So you’ll notice several things:

  1. The PNG fix for IE 5.5 and 6. I’ve linked directly to the google code page. This means I will have to end every transparent PNG with a -trans.png .
  2. I have also linked directly to JQuery and our custom made UI file.
  3. I have put the necessary tags for the slider in the #header

NOTE: For the slider to work, we need to have a bar and a handle.

Step 3: The CSS

Here is the CSS to make that page look a little bit better. This page is pretty simple, and therefore the CSS is pretty simple as well:

body {
	background: #373737;
	text-align: center;
	margin: 0px;
}
#header {
	width: 700px;
	height: 200px;
	background: #48887d url(images/header.jpg);
	margin-left: auto;
	margin-right: auto;
	position: relative;
}
.slider_container {
	position: absolute;
	height: 25px;
	top: 170px;
	left: 165px;
}
.minus {
	background: url(images/minus-trans.png) no-repeat;
	height: 9px;
	width: 25px;
	overflow: hidden;
	float: left;
	cursor: pointer;
}
.slider_bar {
	background: url(images/bar-trans.png) no-repeat;
	height: 9px;
	width: 316px;
	float: left;
	margin: 0px 5px;
	position: relative;
}
.add {
	background: url(images/add-trans.png) no-repeat;
	height: 25px;
	width: 23px;
	float: left;
	position: relative;
	top: -5px;
	cursor: pointer;
}
.slider_handle {
	background: url(images/selector-trans.png) no-repeat;
	height: 25px;
	width: 12px;
	position: absolute;
	top: -8px;
}
#slider_caption {
	background: url(images/caption-trans.png) no-repeat;
	height: 45px;
	width: 38px;
	overflow: hidden;
	position: absolute;
	top: -50px;
	margin-left:-10px;
	padding: 5px 0px 0px 0px;
	font-family: "Myriad Pro";
	color: #36665d;
	font-weight: bold;
	text-align: center;
}
#text {
	font-family: Helvetica, Arial, sans-serif;
	width: 655px;
	background: #f9f9f9;
	margin-left: auto;
	margin-right: auto;
	padding: 20px 20px 20px 25px;
	position: relative;
}
#text p {
	font-size: 12px;
	text-align: left;
	color: black;
}
#text h1 {
	text-align: left;
	margin-left: 20px;
}

p{
font-family: Arial, Helvetica, sans-serif;
color: #CCCCCC;
}

#font_indicator{
position: absolute;
right: 100px;
top: 50px;
font-size: 10px;
display: none;
}

Again, I’m not going to go into great detail with the CSS either. If you still need more help with that, be sure to check out those two tutorials I mentioned above. If you do have any questions, be sure to let me know in the comments.

Notice that all of the png images that have alpha transparency have a -trans.png ending.

Step 4: Basic Slider Effects

When I was first learning about the slider effect, I Googled it to research a little bit more about it and how it works. Well I was lucky to find this amazing screencast. It had a really neat effect too; a caption that appeared to display the position of the slider, on top of the slider. Unfortunately, they stopped there. We’re going to use a variation of their JQuery code as a jumping off point:

$(function() {
	$('#slider_caption').hide();
	var captionVisible = false;
	$('.slider_bar').slider({
		handle: '.slider_handle',
		startValue: 26,
		minValue: 0,
		maxValue: 100,
		start: function(e, ui) {
			$('#slider_caption').fadeIn('fast', function() { captionVisible = true;});
		},
		stop: function(e, ui) { 
			if (captionVisible == false) {
				$('#slider_caption').fadeIn('fast', function() { captionVisible = true;});

				$('#slider_caption').css('left', ui.handle.css('left')).text(Math.round(ui.value * 15/100 + 8 ));

				$("div#text p").animate({fontSize: ui.value * 15/100 + 8 }).fadeIn("slow");
			}
			$('#slider_caption').fadeOut('fast', function() { captionVisible = false; });
			
		},
	
		slide: function(e, ui) {
			$('#slider_caption').css('left', ui.handle.css('left')).text(Math.round(ui.value * 15/100 + 8 ));

			$("div#text p").css({fontSize: ui.value * 15/100 + 8 }).fadeIn("slow");
		}
	});

Some Key Ideas:

  • First, we hide the caption with Javascript. This makes the caption visible if Javascript is disabled for just a little bit more accessibility.
  • As you can see, we now have a .slider modifier and several sub items as well:
    • startValue : This specifies the position that the handle starts at
    • minValue : This specifies the minimum value that the handle will go to
    • maxValue: This specifies the maximum value that the handle will go to
    • start: This allows us to tell JQuery what to do when the user starts sliding the bar
    • stop: This specifies what happens when the slider is let go of
    • slide: This specifies what happens when the slider is being slid
    • handle: This allows us to specify what will be the handle
  • We also assign a variable that will help us know, when stop: occurs, whether the caption is visible or not, and then perform an action based on that conclusion.
  • We also had to put a limit on the font sizes possible, so we limited the slider value possibilities to between 8 and 23. We did this by performing basic math on the value of the slider. (multiplied it by 15/100 and added 8 )
  • This equation resulted in decimal place sizes, so we had to round it the Math.round
  • Notice also, the method by which we made the caption stay on top of the handle. We made the css left value of the caption equal to the handle.
  • Notice that on the stop: I have the text size animated, while on the slide, I have the css size constantly changing. This might seem counter-intuitive, that on slide: I wouldn’t animate it, but by the essence of gradually sliding and enlarging the size it does the same thing. If I were to animate instead of just changing the css, it would be choppy and unresponsive.

Step 5: Adding the Text Caption

$(function() {
	$('#slider_caption').hide();
	var calloutVisible = false;
	$('.slider_bar').slider({
		handle: '.slider_handle',
		startValue: 26,
		minValue: 0,
		maxValue: 100,
		start: function(e, ui) {
			$('#slider_caption').fadeIn('fast', function() { calloutVisible = true;});
			$('#font_indicator').fadeIn('slow');
		},
		stop: function(e, ui) { 
			if (calloutVisible == false) {
				$('#slider_caption').fadeIn('fast', function() { calloutVisible = true;});
				$('#font_indicator').fadeIn('slow');
				$('#slider_caption').css('left', ui.handle.css('left')).text(Math.round(ui.value * 15/100 + 8 ));
				$('#font_indicator b').text(Math.round(ui.value * 15/100 + 8 ));
				$("div#text p").animate({fontSize: ui.value * 15/100 + 8 }).fadeIn("slow");
			}
			$('#slider_caption').fadeOut('fast', function() { calloutVisible = false; });
			$('#font_indicator').fadeOut('slow');
			
			
		},
	
		slide: function(e, ui) {
			$('#slider_caption').css('left', ui.handle.css('left')).text(Math.round(ui.value * 15/100 + 8 ));
			$('#font_indicator b').text(Math.round(ui.value * 15/100 + 8 ));
			$("div#text p").css({fontSize: ui.value * 15/100 + 8 }).fadeIn("slow");
		}
	});

Key Ideas about #font_indicator

  • We added the same fade in and fade out effects in the same spots as the caption
  • We left out the css left position though
  • Notice that we have a <b> tag within the div#font-indicator. This not only makes the number stand out more, but allows us to just put the current slider handle value as text into it. If we just appended to the end of the div, every font size value would just pile up at the end.

Step 6: Giving the Plus and Minus Actions

This just wouldn’t be a functional design, if we didn’t give the plus and minus signs actions on click. This code might be a little bit sloppy and not perfectly efficient, but it gets the job done. This project required a surprising amount of math, which explains some of the wacky numbers that end up being used.

Without further ado, here is the rest of the javascript, I’ll explain it afterward:

	  $(".add").click(function(){
    var currentFontSize = $('#text p').css('font-size');
    var currentFontSizeNum = parseFloat(currentFontSize, 10);
    var newFontSize = currentFontSizeNum+1;
	if (newFontSize < 24) {
    $('#text p').css('font-size', newFontSize);
	$('#slider_caption').css('left', newFontSize*19.75 - 158).fadeIn('fast').text(Math.round(newFontSize )).fadeOut();
	$('.slider_handle').css('left', newFontSize*19.75 - 158);
	$('#font_indicator').fadeIn('slow');
	$('#font_indicator b').text(Math.round(newFontSize ));
	$('#font_indicator').fadeOut('slow');
	}
	else{
	$('#font_indicator').fadeIn('slow');
	$('#font_indicator b').text("Isn't 23 big enough?");
	$('#font_indicator').fadeOut('slow');
	}
    return false;
  });
  	  $(".minus").click(function(){
    var currentFontSize = $('#text p').css('font-size');
    var currentFontSizeNum = parseFloat(currentFontSize, 10);
    var newFontSize = currentFontSizeNum-1;
	if (newFontSize > 8) {
    $('#text p').css('font-size', newFontSize);
	$('#slider_caption').css('left', newFontSize*19.75 - 158).fadeIn('fast').text(Math.round(newFontSize )).fadeOut();
	$('.slider_handle').css('left', newFontSize*19.75 - 158);
	$('#font_indicator').fadeIn('slow');
	$('#font_indicator b').text(Math.round(newFontSize ));
	$('#font_indicator').fadeOut('slow');
	}
	else{
	$('#font_indicator').fadeIn('slow');
	$('#font_indicator b').text("Isn't 8 small enough?");
	$('#font_indicator').fadeOut('slow');
	}
	return false;
  });
  

Some Key Notes:

  • If you know basic Javascript syntax, this should be pretty self evident.
  • I assign an initial variable to get the current font size.
  • I then convert it to an integer
  • I then create another variable that is one value higher.
  • I place a limit between under 24 and above 8, by using an if else statement.

Math Time

Adjusting the handle and caption to react to the plus and minus click was a real challenge. What I ended up doing, was figuring out the width of the bar (316px), and dividing that between the 16 possible font sizes (8-23) to figured out how much space each increment took.

316/16 =

19.75

To be safe, I then needed to figure out the starting spot for the font size. I knew this wasn’t exactly 12, because I modified it slightly with the 15/100 + 8. So I took the starting value of the handle (26) and multiplied it by that:

26*15/100 + 8=

11.9

I figured that, since it was rounded it would be twelve anyway.

So I figured that the handle would be the [font size*19.75 - 158 (The first 8 sizes)]px.

Just thought that I’d give you a glimpse into my weird and over complicated math ;) .There’s probably much easier ways to do it, but I guess this is my logic.

Step 7: Cookie Time, reading the cookie

For dealing with cookies I used Klaus Hartl’s excellent cookie plugin. You can view the basic syntax of the plugin in the link I provided. The challenge, was to find a spot that would reliably set the cookie. I ended up setting it when the browser refreshes or changes the page. This way, it only does it when necessary and realiably too. First we add the code to the top of the javascript file to read the cookie:

var startSize = $.cookie('fontSize');
var startSize = parseFloat(startSize, 12);

$('#text p').css('font-size', startSize);

What I Did:

  • I first read the cookie and sent it to the variable startSize
  • I then changed that variable into an integer
  • I then added that number to the default css of the text

Step 8: Setting The Cookie

As I mentioned above, we need to set the cookie when the page is exited. We do this by using the following code:

  window.onbeforeunload = leaveCookie;

function leaveCookie()
{
			var FontSize = $('#text p').css('font-size');
   			var IntFontSize = parseFloat(FontSize, 10);
			$.cookie('fontSize', IntFontSize);
}

What I Did:

  • NOTE: This JS is outside of the JQuery $(function() {});
  • First, I activated a function when the browser left the page
  • Then I converted the text size into an integer
  • Then I put this into the cookie

That’s It!

Hope you found this tutorial useful! Please excuse my programming logic, I don’t always think so efficiently :P. If you have any questions or comments please feel free to let me know in the comments!

  • Subscribe to the NETTUTS RSS Feed for more daily web development tuts and articles.


Tags: jQuery
Note: Want to add some source code? Type <pre><code> before it and </code></pre> after it. Find out more
  • Tony

    1st

  • steve

    WOW – that’s something very, very, very cool! :-) thx for this tutorial!

  • http://www.1stwebdesigner.com Dainis Graveris

    Wow, demo looks just great – never thought jquery can do something like this too!

  • http://craigsnedeker.blogspot.com/ Craigsnedeker

    NO!!! NOT MATH :P

    I think this is awesome!

  • http://www.ben-griffiths.com Ben Griffiths

    Great tutorial, and a fantastic way to show how jquery can be used to help usability as well as create snazzy effects – thanks :D

  • http://curtisallenblog.com curtis allen

    nice tutorial, keep up the good work.

    • sds

      asasd

  • http://www.kurtcruse.com Kurt Cruse

    @Toni

    Sweet comment, congratulations. Maybe later you can build a huge RSS feed and check it every 9 seconds so you can do it 3 more times today and well then you’ll be the coolest guy ever. Ever.

    On a more applicable note – great tutorial! Love this site.

  • James

    There is a small bug in the code. Although you can move the slider to either extremity of the rule, if you use the “+” and “-” buttons you can only get to the penultimate setting that is 9 or 22 points before it no longer moves and gives you the “Isn’t 8/23 points big/small enough for you?”

    So perhaps you need to check your Math? ;)

  • http://ndezigns.com Nate

    Very cool. Thanks for sharing.

  • http://www.section9studios.com Jason

    Great article! I love seeing more of jQuery stuff, as Im just beginning to use it myself (albeit a bit late to the party I admit!). Also, I do believe James is correct in that it appears to be a bug – since you use the +/- and it maxes at 22 and mins at 9 (but the message says you are at 8 or 23). Very minor sure, but worth noting ;)

  • http://www.aplaceformyhead.co.uk Matt Fairbrass

    Beautiful, brilliant tutorial with rewarding results. It’s nice to see accessibility can be addressed with jQuery, whilst maintaining a high level of design on the UI front. Shall be using in the future for my own development purposes.

  • Seab

    not work in IE6?

  • http://www.peacockcarter.co.uk Richard, Peacock Carter

    Nice tutorial!

    By the way, in Opera 9.27 (Win XP), clicking the ‘+’ when the value is at ’22′ doesn’t increase the value to 23, but does display the ‘
    Current Font Size: Isn’t 23 big enough?’ message.

  • http://www.cssjockey.com CSS:Jockey

    WOW!! this one is really cool.
    This will embed well the background selection on my site. I am sure I am gonna use it..

  • L2

    Doesn’t work in IE7.

    Well I guess some people check before they submit there tutorial and some don’t.

  • L2

    Delete above, now it works but with the ‘+’ symbol I only get to 22 to, and it messages “Current Font Size: Isn’t 23 big enough?”

  • http://www.freshclickmedia.com Shane

    @Kurt – as I read that first comment, I wanted to be the first to comment on how futile that first comment was :)

    I like the tutorial quite a bit. It’s refreshing to see jQuery being used for something other than a slidey panel or fade-in/-out div.

    Nice work.

  • http://www.jakeisonline.com Jake Holman

    Painfully explained to the detail tutorial, just how it should be ;)

    Thanks!

  • http://www.insicdesigns.info insic

    WOW very nice tutorial. thanks you

  • http://www.insicdesigns.info insic

    Just a follow up. Where is the part two of the php5 framework series.

  • http://creatingdrew.com Drew Douglass

    You guys have done it again, thanks for the stunning tutorial.

    Best Regards,

    Drew Douglaaa

  • http://cyberantix.org Connor
    Author

    Glad you guys like it…

  • http://8trk.com mark

    I dont know much about jQuery so I have a question. It seems that start/stop/slide functions are events that are fired when the slider changes state. If that is the case, why do you run the selector everytime the event is fired.

    $(‘#slider_caption’)

    Wouldn’t it be more efficient to make a reference to the element outside of the event and then use the reference?

  • http://www.makedesignnotwar.com Make Design, Not War

    Oh, that’s hot. Beautiful application of this technique – definitely something I’ll be checking back on in the future. I love it when accessibility solutions are as brilliant as this. Thanks for the well written tutorial on it.

  • http://www.partlyblog.com Sean Nelson

    So useful. I’ll have to give this a try.

  • http://informationrain.com/ Chris Papadopoulos

    Very cool trick. Bookmarked. I’m surprised at how fluid the transition between sizes appears.

    But honestly, I hope I almost never see this in the wild. Websites should be designed with legible text size from the beginning. Creating additional sliders and buttons to change the text size is a time-consuming fix to a fundamental flaw.

    Where this might be really appropriate is in specialized web applications. Say you print custom t-shirts and you want to have a quick tool to allow a user to pick how big his t-shirt text is. In this type of context a slider would be a really nifty solution.

    But I really dislike this type of approach for major content areas on a blog or news site.

  • http://desertlion.net Rijalul Fikri

    Very useful article. Surely will try this sometime. I personally like small text, but not my reader :)

  • http://www.freshclickmedia.com Shane

    @Chris – legible text size is difficult to define. What is legible to me may not be legible to people who have sight issues.

    We shouldn’t be using pixels to specify our font sizes, so that the text is resizeable using default browser text resize functionality. Having said that, lots of government sites do feature text resize buttons (perhaps three links with different sized ‘A’ characters on them) to help users. Therefore, this is an extension of that. Perhaps so many different sizes is over-the-top in the real world, but this is a demo. Nobody’s going to put a great big slider at the top of the page either, are they?

    As an aside, when I visit CSS-driven sites, I often change the text size as a matter of course, just to see how the design copes. You’d be surprised how many that break with overlapping and disappearing text because the designer assumed the text size would never change :)

  • http://www.guillaumevoisin.fr Guillaume

    Very useful tip! I really appreciate the way you create tutorials, so well detailed!

  • cheese

    Demo doesn’t do anything for me (IE6)

  • http://laminbarrow.com Lamin Barrow

    Very nice.. the only downside IMO of-course is that is that it you have to use the jquery UI for this becasue it kid of heavy (201 Kb Minified)

  • http://cyberantix.org Connor
    Author

    Er…Lamin, compressed it is 9.20 kb. Do you mean the entire library uncompressed?

  • http://ha.xors.org Braden Keith

    Man that turned out nice

  • http://www.conspiratordesign.com Christopher Webb

    James brings up a great point. The way the current code stands, you’ll never really get 8 or 23 because the code dictates less than or greater than. If you really wanted the messages to match the values, correct the code to read:

    if (newFontSize >= 8) {
    if (newFontSize http://www.twitter.com/conspirator

  • http://www.conspiratordesign.com Christopher Webb

    For what it’s worth, the demo doesn’t work for some reason because it points to the latest version of jQuery. When I downloaded the demo and pointed it to my local version of jQuery (1.2.6), it worked like a charm. Great tutorial!

  • http://keepthewebweird.com Buck Wilson

    You could have at least given me credit for the jQuery code & art if you’re going to rip off my tutorial.

    http://www.keepthewebweird.com/creating-a-nice-slider-with-jquery-ui/

    the JavaScript is nearly a line for line. You didn’t even change the variable names.

  • http://cyberantix.org Connor
    Author

    Hi Buck,

    Sorry for any misunderstanding. I thought I had emailed you. And I did link to it up above. If you look in step 4, you can see that I said:


    Well I was lucky to find this amazing screencast (with a link). It had a really neat effect too; a caption that appeared to display the position of the slider, on top of the slider. Unfortunately, they stopped there. We’re going to use a variation of their JQuery code as a jumping off point:

  • Pingback: The Twenty Most Earth-Shattering Tutorials on NETTUTS! - NETTUTS

  • http://URL(Optional) GM

    This code works great in FireFox, but it does work at all in IE7

  • Pingback: 「手元感覚」の操作感を実現するスクリプト | 札幌のホームページ制作 Webデザイン会社 アイタス

  • http://www.gravatar.com/avatar/84a4b72c996bfc158c43e23288499bd2?s=80&d=http%3A%2F%2Fnettuts.s3.amazonaws.com%2FMisc%2Freader_nettuts.jpg&r=PG aa

    This code works great in FireFox, but it does work at all in IE7

  • Pingback: » The Twenty Most Earth-Shattering Tutorials on NETTUTS!

  • Pingback: jQuery Tip: Quick and Easy Font Resizing | Dev Tips | Become a Better Developer, One Tip at a Time.

  • Pingback: » Use the jQuery UI to Control the Size of Your Text

  • http://www.omairarts.com Omair Rais

    The slider is very handy for me.

    Thanks
    Omair Rais
    http://www.omairarts.com

  • http://next.pixeldepo.com Radoslav Stankob

    For slider like this I make different css styles – text-size-1, text-size-2, … and only change them one element.

  • http://www.fangjuke.com tomgary

    What pretty slider !
    Thak you !

  • http://and8.net soking

    Nice!

  • http://www.econtentmanager.pt Netflash

    It’s a great effect but you should have checked in IE7. It’s not working correctly. Dragging the slider does nothing. Only works if you use the + and – buttons.

  • Pingback: jQuery: câteva pluginuri | CNET.ro