Images on web pages are more interesting when the user can interact with them. In this post, we will show how to make images more interesting by using ImageMapster, an open-source jQuery plugin that activates HTML image maps. We will also go over how to use some of the more nifty features of ImageMapster, including customizable tool tips, area highlighting, and dynamic image map scaling.

Image Maps

An image map is an HTML <map> element containing lists of coordinates from an image grouped together in <area> tags. How do we get these coordinates? Well, a quick way to obtain the coordinates to make your own image map is to use a free image map generator web tool. My favorite is Easy Imagemap Generator. All you have to do is upload the image and select the desired area. The coordinates are then generated for each selected area automatically. Let’s pick an image to upload.

We took this adorable picture of Spongebob and Plankton during our lunch break out in Jellyfish Fields.

Spongebob FUN

Now, we all love Spongebob, but this image doesn’t tell the whole story. What do the letters, “F”, “U”, and “N” stand for? No one knows except us, so let’s share our experience! We can start by uploading the picture into Easy Imagemap Generator and creating an image map. We should outline areas over the letters “F”, “U”, and “N” and one rough area between Spongebob and Plankton, since we want to highlight something they said together during the picture.

You should now have HTML code for an image map that looks similar to this:

<img src="url/to/your/image.jpg" alt="" usemap="#Map" />
<map name="Map" id="Map">
    <area alt="" title="" href="#" shape="poly" coords="274,147,285,124,413,88,425,131,420,161,355,177,355,190,403,178,408,206,405,229,375,237,380,271,339,283,322,288,326,261,316,258,307,258" />
    <area alt="" title="" href="#" shape="poly" coords="642,111,666,107,705,133,678,209,677,222,681,229,687,237,699,233,711,212,723,188,741,162,744,152,764,147,800,174,779,227,761,264,751,276,734,280,725,286,723,298,718,303,692,299,666,290,645,280,632,268,620,249,615,224,618,192" />
    <area alt="" title="" href="#" shape="poly" coords="839,356,867,391,861,417,857,432,886,406,921,414,947,458,845,557,816,558,776,528,783,477,768,506,747,500,712,470,808,351" />
    <area alt="" title="" href="#" shape="poly" coords="438,516,571,477,685,518,742,574,735,643,438,583" />
</map>

The code that is generated from the Easy Imagemap Generator site is not quite complete for our needs. Let’s replace each title with an id instead. We can also get rid of the id for the <map> element, since we won’t be using it for this project.

<map name="Map">
    <area alt="" id="id1" href="#" shape="poly" coords="274,147,285,124,413,88,425,131,420,161,355,177,355,190,403,178,408,206,405,229,375,237,380,271,339,283,322,288,326,261,316,258,307,258" />
    <area alt="" id="id2" href="#" shape="poly" coords="642,111,666,107,705,133,678,209,677,222,681,229,687,237,699,233,711,212,723,188,741,162,744,152,764,147,800,174,779,227,761,264,751,276,734,280,725,286,723,298,718,303,692,299,666,290,645,280,632,268,620,249,615,224,618,192" />
    <area alt="" id="id3" href="#" shape="poly" coords="839,356,867,391,861,417,857,432,886,406,921,414,947,458,845,557,816,558,776,528,783,477,768,506,747,500,712,470,808,351" />
    <area alt="" id="id4" href="#" shape="poly" coords="438,516,571,477,685,518,742,574,735,643,438,583" />
</map>

Great! Now we have a working image map. Let’s include our desired image in our HTML.

<img id="image" src="assets/spongebob_fun.jpg" width="1152" height="864" usemap="#Map" />

Our code so far is:

<div>
    <img id="image" src="assets/spongebob_fun.jpg" width="1152" height="864" usemap="#Map" />
    <map name="Map">
        <area alt="" id="id1" href="#" shape="poly" coords="274,147,285,124,413,88,425,131,420,161,355,177,355,190,403,178,408,206,405,229,375,237,380,271,339,283,322,288,326,261,316,258,307,258" />
        <area alt="" id="id2" href="#" shape="poly" coords="642,111,666,107,705,133,678,209,677,222,681,229,687,237,699,233,711,212,723,188,741,162,744,152,764,147,800,174,779,227,761,264,751,276,734,280,725,286,723,298,718,303,692,299,666,290,645,280,632,268,620,249,615,224,618,192" />
        <area alt="" id="id3" href="#" shape="poly" coords="839,356,867,391,861,417,857,432,886,406,921,414,947,458,845,557,816,558,776,528,783,477,768,506,747,500,712,470,808,351" />
        <area alt="" id="id4" href="#" shape="poly" coords="438,516,571,477,685,518,742,574,735,643,438,583" />
    </map>
</div>

Make sure the href="#" code is in there! ImageMapster looks for that piece of code when analyzing the image maps. We will now use some JavaScript to put ImageMapster into action!

Using ImageMapster

ImageMapster requires jQuery. Luckily, Google hosts the jQuery library, so we can just add their hosted URL into our header. We also need to download the ImageMapster script found on its GitHub page and include that in our header as well, so we can start using it. The script file ending in “.min.js” is just a compressed version of the regular “.js” file, so either can be used. The regular “.js” script file will display more readable errors, so use that one during development, and then switch to the “.min.js” script file during production for performance improvements.

<head>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
    <script src="/path/to/jquery.imagemapster.min.js"></script>
</head>

We can invoke ImageMapster by calling the $('img').mapster() function within the script block. We can target a specific area of the image by using the id of each <area> as the key. This code needs to be embedded between a <script> tag. This is the JavaScript portion of our code. Now, we need to define some options. We can start with the following:

<script>
$(function() {
    $('#image').mapster({
        mapKey: 'id',
        fillColor: '000000',
        fillOpacity: 0.5,
        areas: 
        [{
            key: 'id1',
            staticState: false
        },
        {
            key: 'id2',
            staticState: false
        },
        {
            key: 'id3',
            staticState: false
        },
        {
            key: 'id4',
            staticState: false,
            fill: false
        }]
    });
});
</script>

These options will add a transparent shade on mouseover to each area to highlight its importance to the user. So, why is the fill: false option included for the id4 key? Well, id4 represents the area between Spongebob and Plankton. We don’t want this area highlighted on mouseover. That would just look ugly. We have staticState: false, because we don’t want users to be able to select the imagemap area. Selecting that area would leave it highlighted until the user selects it again, which serves no purpose for us. Now, let’s add a custom tooltip on mouseover too!

We need to create four string variables for each area that needs a tooltip.

var letter_f = 'F is for friends who do stuff together!';
var letter_u = 'U is for you and me!';
var letter_n = 'N is for anywhere and anytime at all!';
var dialogue = 'Down here in the deep blue sea!';

We also have to add the following options to show the tooltips.

showToolTip: true,
toolTipClose: ["tooltip-click", "area-click", "image-mouseout", "area-mouseout"],
toolTipContainer: '<div style="border:0.5px solid black; background: #FFFFFF; font-family:Titillium Web; text-align: left; font-size: 20px; position:absolute; width:250px; padding:4px; box-shadow: rgb(83, 83, 83) 3px 3px 5px; border-radius: 6px; opacity: 0.90; display: block; z-index: 9999;"></div>'

The toolTipContainer option could have been left out, but then we would be using the boring, default styling for tooltips. This style will make the tooltips look more modern and classy.

Lastly, we need to select the tooltip text we are going to use for each area. Here is our finished ImageMapster function. Don’t forget to include the jQuery and ImageMapster scripts in the header as we did previously.

<script>
$(function() {
var letter_f = 'F is for friends who do stuff together!';
var letter_u = 'U is for you and me!';
var letter_n = 'N is for anywhere and anytime at all!';
var dialogue = 'Down here in the deep blue sea!';

$('#image').mapster({
    mapKey: 'id',
    fillColor: '000000',
    fillOpacity: 0.5,
    showToolTip: true,
    toolTipClose: ["tooltip-click", "area-click", "image-mouseout", "area-mouseout"],
    toolTipContainer: '<div style="border:0.5px solid black; background: #FFFFFF; font-family:Titillium Web; text-align: left; font-size: 20px; position:absolute; width:250px; padding:4px; box-shadow: rgb(83, 83, 83) 3px 3px 5px; border-radius: 6px; opacity: 0.90; display: block; z-index: 9999;"></div>',
    areas: 
        [{
            key: 'id1',
            staticState: false,
            toolTip: letter_f,
        },
        {
            key: 'id2',
            staticState: false,
            toolTip: letter_u
        },
        {
            key: 'id3',
            staticState: false,
            toolTip: letter_n
        },
        {
            key: 'id4',
            staticState: false,
            fill: false,
            toolTip: dialogue
        }]
    });
});
</script>

Here is the finished product.

spongebob_tooltip

We have a pretty long function and working code, but we’re still not finished telling the story. Watch what happens if we change the size of the browser window.

spongebob_not_resized

We need to allow dynamic resizing of the image when the browser window is resized. Fortunately, ImageMapster generously has a script for that! As shown in the JSFiddle’s “JavaScript” section, we need to add the onWindowResize() and resize() functions to implement dynamic resizing. We also need to add resizeTime and resizeDelay variables to customize the resize duration and delay. Here is our finished code to get ImageMapster fully working!

<head>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
    <script src="/path/to/jquery.imagemapster.min.js"></script>
</head>
<body>
    <div>
        <img id="image" src="assets/spongebob_fun.jpg" width="1152" height="864" usemap="#Map" />
        <map name="Map">
            <area alt="" id="id1" href="#" shape="poly" coords="274,147,285,124,413,88,425,131,420,161,355,177,355,190,403,178,408,206,405,229,375,237,380,271,339,283,322,288,326,261,316,258,307,258" />
            <area alt="" id="id2" href="#" shape="poly" coords="642,111,666,107,705,133,678,209,677,222,681,229,687,237,699,233,711,212,723,188,741,162,744,152,764,147,800,174,779,227,761,264,751,276,734,280,725,286,723,298,718,303,692,299,666,290,645,280,632,268,620,249,615,224,618,192" />
            <area alt="" id="id3" href="#" shape="poly" coords="839,356,867,391,861,417,857,432,886,406,921,414,947,458,845,557,816,558,776,528,783,477,768,506,747,500,712,470,808,351" />
            <area alt="" id="id4" href="#" shape="poly" coords="438,516,571,477,685,518,742,574,735,643,438,583" />
        </map>
    </div>
    <script>
    $(function() {
         var resizeTime = 25;    /* Duration of the resize effect. */
         var resizeDelay = 25;   /* Time to wait before checking the window size again. */
         var letter_f = 'F is for friends who do stuff together!';
         var letter_u = 'U is for you and me!';
         var letter_n = 'N is for anywhere and anytime at all!';
         var dialogue = 'Down here in the deep blue sea!';

        $('#image').mapster({
            mapKey: 'id',
            fillColor: '000000',
            fillOpacity: 0.5,
            showToolTip: true,
            toolTipClose: ["tooltip-click", "area-click", "image-mouseout", "area-mouseout"],
            toolTipContainer: '<div style="border:0.5px solid black; background: #FFFFFF; font-family:Titillium Web; text-align: left; font-size: 20px; position:absolute; width:250px; padding:4px; box-shadow: rgb(83, 83, 83) 3px 3px 5px; border-radius: 6px; opacity: 0.90; display: block; z-index: 9999;"></div>',
            areas: 
            [{
                key: 'id1',
                staticState: false,
                toolTip: letter_f,
            },
            {
                key: 'id2',
                staticState: false,
                toolTip: letter_u
            },
            {
                key: 'id3',
                staticState: false,
                toolTip: letter_n
            },
            {
                key: 'id4',
                staticState: false,
                fill: false,
                toolTip: dialogue
            }]
        });

        /* Resize the map to fit within the boundaries provided */
        function resize(maxWidth,maxHeight) {
             var image =  $('#image'),
                imgWidth = image.width(),
                imgHeight = image.height(),
                newWidth=0,
                newHeight=0;

            if (imgWidth/maxWidth>imgHeight/maxHeight) {
                newWidth = maxWidth - 50;
            } else {
                newHeight = maxHeight - 100;
            }
            image.mapster('resize',newWidth,newHeight,resizeTime);   
        }

        /* Track window resizing events, but only actually call the map resize when 
           the window isn't being resized any more */
        function onWindowResize() {
            var curWidth = $(window).width(),
                curHeight = $(window).height(),
                checking=false;
            if (checking) {
                return;
            }
            checking = true;
            window.setTimeout(function() {
                var newWidth = $(window).width(),
                    newHeight = $(window).height();
                if (newWidth === curWidth &&
                    newHeight === curHeight) {
                    resize(newWidth,newHeight); 
                }
                checking=false;
            },resizeDelay );
        }
        $(window).bind('resize',onWindowResize); 
    });
    </script>
</body>

The resize() function does the actual resizing to fit the image within the boundaries of the window. The onWindowResize() function tracks the window resizing events. Now when the browser window resizes, the image and its image maps will resize along with it! Plus, the tooltips and area highlighting still work!

spongebob_resized

We are finally done telling our story! ImageMapster also provides many functional demos and great documentation. There are also more demos on JSFiddle under the “Fiddle With It” section on the ImageMapster page, which show you how to do some nifty tricks and techniques. Hopefully this provided a solid introduction to the ImageMapster tool. Remember, don’t just settle for that static image. Make it interactive!


The Spongebob image on this page was used from the “F.U.N.” article image gallery, uploaded by the user, “120d” at the time on the Encyclopedia SpongeBobia wiki at Fandom and is licensed under the Creative Commons Attribution-Share Alike License.