Create a Pentagon Hover Effect with CSS3 and jQuery – Dissecting the Web

Alt Text

Introduction

This is a new series that will focus on cool web elements on the web. My goal is to try and replicate these sleek elements using a combination of HTML, Javascript and CSS3 and hopefully teach something along the way. The first website I want to feature is Watracz.com. It’s a portfolio site that implements a cool pentagon hover effect for displaying his work. It smoothly meshes together a rotate effect with a slight nudge right to the image along with a colorization of the image. Note: This is using CSS3 Transitions which is still not completely standard and browser compatibility may be limited.

Table of Contents

First Look: Images
HTML and CSS
jQuery

First Look: Images

Be aware that I’m not using the most current version of photoshop so some of these options may be different. Open up a photoshop document with the dimensions 300px by 300px. Now fill a circle in white that stretches all of the document:

pentagon hover

Next make a pentagon shape facing down with the polygon tool set to five sides filling roughly most of the circle. Most importantly, make sure it is perfectly centered within the circle:

pentagon hover

Now right click on the shape and select Make Selection. Once you have this selection, go up top to the toolbar and click select. Then hover over Modify and choose Smooth. Choose 10px, or something around that depending on how rounded you want the pentagon:

pentagon hover

This will be the mask that gives the images the shape of the pentagon. Save that as pentagon_mask.png. This effect is dependent on your site having a solid color background. Depending on that color change the white part of the pentagon_mask to that color so it looks seamless with the background.

pentagon hover

HTML and CSS

Now for the HTML and CSS of the site. This will be 90% of the work. Always start your webpage with a css reset style. You can download one here and add it into your webpage like this:

<link href="reset.css" type="text/css" rel="stylesheet" media="screen,projection" />

Also add your own stylesheet in style.css. Start this stylesheet off with these basic containers:

body {
  margin: 0 auto;
  font: 1em/1.3em Helvetica, sans-serif;
}

.clearfix {
  clear: both;
}

.portfolio {
  text-align: center;
}
  .portfolio .pentagon {
    float: left;
    margin: 20px;
    width: 205px;
  }

The structure of these are pretty complex because they require multiple layers of things overlapping. The portfolio will hold all the items, and pentagon will hold each individual item. Next, we have the styles for the image link and the pentagon mask overlay that creates the shape.

    .portfolio .pentagon a {
      float: left;
      width: 200px;
      height: 200px;
      overflow: hidden;
      display: block;  
      position: relative;
    }
      .portfolio .pentagon a img {
        position: absolute;
        left: -75px;
        top: 0;
        -webkit-filter: grayscale(100%);
      	-moz-filter: grayscale(100%);
      	-o-filter: grayscale(100%);
      	-ms-filter: grayscale(100%);
      	filter: grayscale(100%);
        -webkit-transition: 350ms ease-in-out;
      	-moz-transition: 350ms ease-in-out;
      	-o-transition: 350ms ease-in-out;
      	transition: 350ms ease-in-out;
        -webkit-backface-visibility: hidden;
      }
      .portfolio .pentagon a span.mask {
        width: 300px;
        height: 300px;
        position: absolute;
        top: -50px;
        left: -50px;
        z-index: 2;
        background: url("images/pentagon_mask.png") no-repeat;
        -webkit-transition:-webkit-transform 350ms ease-in-out;
      	-moz-transition:-moz-transform 350ms ease-in-out;
      	-o-transition:-o-transform 350ms ease-in-out;
      	transition:transform 350ms ease-in-out;
        -webkit-backface-visibility: hidden;
      }

Inside the container div, pentagon, there is an anchor tag. This anchor tag contains the image of the link and the mask image. The image has the CSS3 filter property which creates the grayscale effect. Both the image and the mask have CSS3 transitions to animate the changes in grayscale and rotation. They both need to have absolute positioning so that they overlap. Don’t forget that the mask needs a higher z-index over the image so it sits on top.

      .portfolio .pentagon a img.hovering {
        left: -50px;
        -webkit-filter: grayscale(0%);
      	-moz-filter: grayscale(0%);
      	-o-filter: grayscale(0%);
      	-ms-filter: grayscale(0%);
      	filter: grayscale(0%);
      }
      .portfolio .pentagon a span.mask:hover{
      	-webkit-transform:rotate(30deg);
      	-moz-transform:rotate(30deg);
          -ms-transform:rotate(30deg);
      	-o-transform:rotate(30deg);
      	transform:rotate(30deg);
      }

These two will be the hovering state changes that creates the interesting animation. The first is a class that we will attach with jQuery which will turn the picture back into color. The second is a hover pseudo class that will rotate the pentagon.

    .pentagon .portfolio-title {
      position: relative;
      float: left;
      width: 100%;
      height: 20px;
      overflow: hidden;
      margin-top: 20px;
    }
      .pentagon .portfolio-title h4 {
        position: relative;
        line-height: 20px;
        width: 100%;
        text-align: center;
        font-weight: bold;
        color: #777;
      }
        .portfolio-title h4 span {
          width: 100%;
          position: absolute;
          margin: 0 auto;
          left: 0;
          color: #4EA838;
          top: 20px;
        }

This last bit of css is for the title. We will also use jQuery to give these its sliding animation. And that’s it for the css. If the transitions are done right and the browser supports it, most of the animation will be done. The last part is just a bit of jQuery.

jQuery

(function($){
	$(function(){


	$('span.mask').hover(
			  function () {
          $(this).siblings('a img').addClass('hovering');
          $(this).parent().siblings(".portfolio-title").children("h4").stop().animate({
              top: -20
            }, 350);
			  }, 
			  function () {
          $(this).siblings('a img').removeClass('hovering');
          $(this).parent().siblings(".portfolio-title").children("h4").stop().animate({
              top: 0
            }, 350);
			  }
	);
	
	
	}); // end of document ready
})(jQuery); // end of jQuery name space

All this does is basically adds the classes to trigger the transition animation, and also animates the titles. And thats it! Check out the final version here: Demo and Download