Cool inset Text Effect with CSS3 Text-Shadow

So, I have seen a few tutorials online about using text-shadow to create a basic inset text effect, but they are all lacking the real design aspect that makes the type look like it is actually INSET. That aspect is the inner shadow.

Introduction

I played around with trying to hack box-shadow into background-image in the same way that you can add linear gradients to text, but to no avail.

Well, in any case, I finally was able to get something to work, and yes, it is pretty killer.


insetText

That’s it right there. But, let’s take a look at how and why this works.

First let’s start with defining our class and setting our font. We have styled our div and our body and now we want this text to look like it is stamped into to page.

The CSS

.insetText {
        font-family: Lucida Grande;
}

The next step we want to take is to set the background-color of the text to the color that we want the inset to be. So…

.insetText {
        font-family: Lucida Grande;
        background-color: #666666;
}

Next, we are going to use the background-clip CSS3 property to create a clipping mask using the text to mask the background. Now if you are a designer, you probably already know how a clipping mask works. The color black is transparent to the background and the color white is opaque. Thus, the image behind the mask will show through on only the black parts and the white parts will ‘clip’ it. Remember that, because it’s important.

Remember, CSS3 is not standard yet and may not be supported in older browsers. For now, it’s best to use the standard AND browser specific properties for any CSS3, so…

.insetText {
        font-family: Lucida Grande;
        background-color: #666666;
        -webkit-background-clip: text;
	-moz-background-clip: text;
	background-clip: text;
}

Now, I know. It doesn’t look like that did anything, whatsoever. We are back where we started, right? Wrong, in truth, the background color has been clipped behind the text, so it only shows through where the text is. The problem is that the browser default CSS is to make text black. So, now we simply use color to make the text transparent.

.insetText {
        font-family: Lucida Grande;
        background-color: #666666;
        -webkit-background-clip: text;
	-moz-background-clip: text;
	background-clip: text;
        color: transparent;
}

Now we’re getting somewhere. We have taken transparent text and used it to clip it’s grey background. Here is where the magic happens. We will use the text-shadow property with rgba colors. Since the text is transparent, the entire shadow, even what is normally hidden by the text in front of it, will show. If we offset the shadow vertically, it will appear as if it is on the inside of the text. And if we blur the edges, it should actually appear like an inset shadow, since the darker clipped background fading into the white shadow right? And the shadow that falls outside of the clipping mask should appear to glow slightly, since that it’s closer in color to the contrasting background! So…

.insetText {
        font-family: Lucida Grande;
        background-color: #666666;
        -webkit-background-clip: text;
	-moz-background-clip: text;
	background-clip: text;
        color: transparent;
        text-shadow: rgba(255,255,255,1.0) 0px 3px 3px;
}

Yeah, that looks pretty good, right? I just don’t like how the inside of the text in now white. It looks kind of unnatural, and it really takes away from the outer glow that gives it the inset look. So let’s revise our shadow color by dropping it’s opacity or ‘a’ value to 0.5. Like so…

.insetText {
        font-family: Lucida Grande;
        background-color: #666666;
        -webkit-background-clip: text;
	-moz-background-clip: text;
	background-clip: text;
        color: transparent;
        text-shadow: rgba(255,255,255,0.5) 0px 3px 3px;
}

Perfect! Now we have a completely CSS based inset text effect! We can now add this class to any text element on our websites, without having to open Photoshop or Illustrator, create the document, design the effect, save the image, upload the image, and then place the image in our markup where it will slow down our load time. You would add this to your markup like so…

<h1>This is inset text</h1>

This solution is great for headings. The smaller you make your text the smaller you will need to make your text-shadow.

NOTE: This method is currently only supported by Webkit browser like Google Chrome and Apple Safari.

Thanks for reading, and I hope this helped!

view demo

Posted by: Dhiraj kumar

CSS3 Buttons with Cool Effects – Pure CSS

Nowadays, using subtle patterns is kinda cool so I thought why not using them also on buttons? The idea was to create some nice CSS3 patterned buttons and in this article you’ll see what I’ve been working on lately.

css3-patterned-buttons

view demo

I wrote before about CSS3 buttons, so you may want to check also these articles:

CSS3 patterned buttons features

  • Easy-to-use.
  • Contain the transitions on gradients hack.
  • As you may have expected, no images used here. Instead, an base64 string is used to create the patterned effect.
  • Stilish pressed behavior when grouped.

Buttons

Basically, to create a button, the only thing you have to do is this:

<a href="" class="button">Button</a>

or

<button class="button">Button</button>

You could also use something like <input type="submit"> but for best cross-browser rendering, just stick to the above.

THE CSS

.button{
  display: inline-block;
  *display: inline;
  zoom: 1;
  padding: 6px 20px;
  margin: 0;
  cursor: pointer;
  border: 1px solid #bbb;
  overflow: visible;
  font: bold 13px arial, helvetica, sans-serif;
  text-decoration: none;
  white-space: nowrap;
  color: #555;
  background-color: #ddd;
  background-image: linear-gradient(top, rgba(255,255,255,1),
                                         rgba(255,255,255,0)),
                    url(data:image/png;base64,iVBORw0KGg[...]QmCC); 
  transition: background-color .2s ease-out;
  background-clip: padding-box; /* Fix bleeding */
  border-radius: 3px;
  box-shadow: 0 1px 0 rgba(0, 0, 0, .3),
              0 2px 2px -1px rgba(0, 0, 0, .5),
              0 1px 0 rgba(255, 255, 255, .3) inset;
  text-shadow: 0 1px 0 rgba(255,255,255, .9);  
}

.button:hover{
  background-color: #eee;
  color: #555;
}

.button:active{
  background: #e9e9e9;
  position: relative;
  top: 1px;
  text-shadow: none;
  box-shadow: 0 1px 1px rgba(0, 0, 0, .3) inset;
}

Different buttons sizes

If you want to make a more prominent or a less prominent call-to-action button, you have options:

css3-patterned-buttons

<button class="small button">Button</button>

or

<button class="large button">Button</button>

THE CSS

/* Smaller buttons styles */

.button.small{
  padding: 4px 12px;
}

/* Larger buttons styles */

.button.large{
  padding: 12px 30px;
  text-transform: uppercase;
}

.button.large:active{
  top: 2px;
}

Various buttons colors

You’ll need custom colors for successful actions or negative ones as delete:

css3-patterned-buttons

<button class="button">Button</button>
<button class="color red button">Button</button>
<button class="color green button">Button</button>
<button class="color blue button">Button</button>

THE CSS

.button.color{
  color: #fff;
  text-shadow: 0 1px 0 rgba(0,0,0,.2);
  background-image: linear-gradient(top, rgba(255,255,255,.3), 
  					 rgba(255,255,255,0)),
                    url(data:image/png;base64,iVBORw0KGg[...]QmCC);
}

/* */

.button.green{
  background-color: #57a957;
  border-color: #57a957;
}

.button.green:hover{
  background-color: #62c462;
}

.button.green:active{
  background: #57a957;
}

/* */

.button.red{
  background-color: #c43c35;
  border-color: #c43c35;
}

.button.red:hover{
  background-color: #ee5f5b;
}

.button.red:active{
  background: #c43c35;
}

/* */

.button.blue{
  background-color: #269CE9;
  border-color: #269CE9;
}

.button.blue:hover{
  background-color: #70B9E8;
}

.button.blue:active{
  background: #269CE9;
}

Disabled states

In case you’re using buttons or inputs, in some cases you’ll need them to be disabled until a certain task is triggered:

css3-patterned-buttons

<button class="button" disabled>Button</button>
<button class="color red button" disabled>Button</button>
<button class="color green button" disabled>Button</button>
<button class="color blue button" disabled>Button</button>

THE CSS

.button[disabled], .button[disabled]:hover, .button[disabled]:active{
  border-color: #eaeaea;
  background: #fafafa;
  cursor: default;
  position: static;
  color: #999;
  /* Usually, !important should be avoided but here it's really needed :) */
  box-shadow: none !important;
  text-shadow: none !important;
}

.green[disabled], .green[disabled]:hover, .green[disabled]:active{
  border-color: #57A957;
  background: #57A957;
  color: #D2FFD2;
}

.red[disabled], .red[disabled]:hover, .red[disabled]:active{
  border-color: #C43C35;
  background: #C43C35;
  color: #FFD3D3;
}

.blue[disabled], .blue[disabled]:hover, .blue[disabled]:active{
  border-color: #269CE9;
  background: #269CE9;
  color: #93D5FF;
}

Grouped buttons

There will be cases when you’ll need to group similar call-to-action buttons:

css3-patterned-buttons

<ul class="button-group">
	<li><button class="button">Button</button></li>
	<li><button class="button">Button</button></li>
	<li><button class="button">Button</button></li>
	<li><button class="button">Button</button></li>
</ul>

THE CSS

.button-group,
.button-group li{
  display: inline-block;
  *display: inline;
  zoom: 1;
}

.button-group{
  font-size: 0; /* Inline block elements gap - fix */
  margin: 0;
  padding: 0;
  background: rgba(0, 0, 0, .04);
  border-bottom: 1px solid rgba(0, 0, 0, .07);
  padding: 7px;
  border-radius: 7px; 
}

.button-group li{
  margin-right: -1px; /* Overlap each right button border */
}

.button-group .button{
  font-size: 13px; /* Set the font size, different from inherited 0 */
  border-radius: 0; 
}

.button-group .button:active{
  box-shadow: 0 0 1px rgba(0, 0, 0, .2) inset,
              5px 0 5px -3px rgba(0, 0, 0, .2) inset,
              -5px 0 5px -3px rgba(0, 0, 0, .2) inset;   
}

.button-group li:first-child .button{
  border-radius: 3px 0 0 3px;
}

.button-group li:first-child .button:active{
  box-shadow: 0 0 1px rgba(0, 0, 0, .2) inset,
              -5px 0 5px -3px rgba(0, 0, 0, .2) inset;
}

.button-group li:last-child .button{
  border-radius: 0 3px 3px 0;
}

.button-group li:last-child .button:active{
  box-shadow: 0 0 1px rgba(0, 0, 0, .2) inset,
              5px 0 5px -3px rgba(0, 0, 0, .2) inset;
}

Browser compatibility

CSS3 patterned buttons works in all major browsers. But of course CSS3 features used here do not work in oder browsers like IE8 and below.

view demo

This is it!

There are so many CSS3 buttons in the wild and I know it. Yet I’m confident that my CSS3 patterned buttons might inspire you and I hope you’ll find it useful for your future projects.

Posted by: Dhiraj kumar

Animated 3D Bouncing Ball with CSS3, Html5

Hi guys! Today we are going to see another great example of how to use the power of CSS3. We will start by creating a very cool and realistic 3D ball with pure CSS3 properties, and add a little CSS3 animations for giving the ball a “bouncing” effect.

Please note: the result of this tutorial will only work as intended in browsers that support the respective CSS properties (gradient, shadow, border-radius, keyframe animation).css-3d-bouncing-ball

THE HTML

Let’s start with some very basic HTML:

<div id="ballWrapper">
     <div id="ball"></div>
     <div id="ballShadow"></div>
</div>

What we have here are 3 simple DIV elements. “#ballWrapper” is the main DIV which wraps the ball. This DIV will determine the ball’s position and height on the screen. Next, we have the “#ball” element which is the ball markup, and finally there is the “#ballShadow” which holds the ball’s shadow separately from the ball itself.

THE CSS

First, we’ll want to set a basic width and height to our ‘#ballWrapper’ DIV. It will help us position it to the center of the screen:

#ballWrapper {
    width: 140px;
    height: 300px;
    position: fixed;
    left: 50%;
    top: 50%;
    margin: -150px 0 0 -70px;
}

Note that I gave the DIV both top and left position properties of  ‘50%’, and a negative top and left margin which is calculated to be exactly half of the original height and width of the DIV. That way we can center the ball on the screen.

Next in line, let’s give our ball some styles (grow up, it’s not that funny… :])

#ball {
    width: 140px;
    height: 140px;
    border-radius: 70px;
    background: linear-gradient(top,  rgba(187,187,187,1) 0%,rgba(119,119,119,1) 99%);
    box-shadow: inset 0 -5px 15px rgba(255,255,255,0.4), 
                inset -2px -1px 40px rgba(0,0,0,0.4), 
                0 0 1px #000;   
}

We are giving the ball equal width and height and a ‘border-radius‘ property with a value of  ’70px’ (which is half of the original width and height we’ve set) so it will be a ball and not an oval shape.

Another thing you’ll notice is the background. I gave the ball’s element a linear background and 3 different box shadow levels so it would get the 3D effect. The first box shadow level is for the dark shadowing at the bottom of the ball (see image). Then, we have the second level that is responsible for the blurry glow – again, at the bottom of the ball. Finally the third level is a hardly noticeable blurry shadow behind the contours of the ball.

If you take a look at the ball you’ll notice that there is another small oval shape on top of the ball that gives it a reflection effect. Here is how I created it:

#ball::after {
    content: "";
    width: 80px; 
    height: 40px; 
    position: absolute;
    left: 30px;
    top: 10px;  
    background: linear-gradient(top,  rgba(232,232,232,1) 0%,rgba(232,232,232,1) 1%,rgba(255,255,255,0) 100%);
    border-radius: 40px / 20px; 
}

I used the CSS pseudo element ::after and gave it a linear gradient with an opacity. In addition, I’ve set the border radius to  ’40px / 20px’ so it has an oval shape.
Next, let’s handle the ball’s shadow:

#ballShadow {
    width: 60px;
    height: 75px;
    position: absolute;
    z-index: 0;
    bottom: 0;
    left: 50%;
    margin-left: -30px;
    background: rgba(20, 20, 20, .1);
    box-shadow: 0px 0 20px 35px rgba(20,20,20,.1);
    border-radius: 30px / 40px; 
}

view demo

Again, I used the same properties for centering the shadow, but this time I pinned it to the bottom of ‘#ballWrapper’. I also added a semi-transparent background to it, a fitting box shadow and a border radius.

THE BOUNCING ANIMATION

Now let’s take a look at the fun stuff…

I’ll start by adding the animation property to our ball:

#ball {
    animation: jump 1s infinite;
}

All I did was to define the animation’s name (jump), the animation’s duration (1 second) and how many times the animation will happen – in our case we use ‘infinite’ which means that it will run forever.
The animation itself:

@keyframes jump {
    0% {
        top: 0;
    }
    50% {
        top: 140px;
        height: 140px;
    }
    55% {
        top: 160px; 
        height: 120px; 
        border-radius: 70px / 60px;
    }
    65% {
        top: 120px; 
        height: 140px; 
        border-radius: 70px;
    }
    95% {
        top: 0;
    }
    100% {
        top: 0;
    }
}

So, basically what I’m doing here is to play with the ‘top’ position property of the ball.  Starting from 0, through 160 and back to 0. You’ll notice that in the middle of the animation I’m also playing with the ‘border-radius’ property – that way I handle the “impact” of the ball on the ground.

And now the ball’s shadow; first let’s add the shadow’s relevant animation property:

#ballShadow {
    animation: shrink 1s infinite;
}

I used the same values that I used with the ball, only with a different keyframes animation called shrink which looks as follows:

@-keyframes shrink {
    0% {
        bottom: 0;
        margin-left: -30px;
        width: 60px;
        height: 75px;
        background: rgba(20, 20, 20, .1);
        box-shadow: 0px 0 20px 35px rgba(20,20,20,.1);
        border-radius: 30px / 40px;
    }
    50% {
        bottom: 30px;
        margin-left: -10px;
        width: 20px;
        height: 5px;
        background: rgba(20, 20, 20, .3);
        box-shadow: 0px 0 20px 35px rgba(20,20,20,.3);
        border-radius: 20px / 20px;
    }
    100% {
        bottom: 0;
        margin-left: -30px;
        width: 60px;
        height: 75px;
        background: rgba(20, 20, 20, .1);
        box-shadow: 0px 0 20px 35px rgba(20,20,20,.1);
        border-radius: 30px / 40px;
    }
}

In the shadow’s animation I played with different properties then in the ball’s animation. In order to give it all a realistic effect when it comes to the ball’s distance from the floor, I needed to animate the shadow width, height and opacity. While the ball is close to the floor, the shadow needs to be darker and smaller. When the ball jumps up, the shadow should be lighter and bigger.

Last, but not least, let’s add the “click effect” to the ball which makes it appear as if it moves away from us when we click and hold. To achieve this effect, all we have to use is the ‘:active’ pseudo-class, add a transition and play with the CSS3 transform ‘scale’ property like this:

#ballWrapper {
    transform: scale(1);
    transition: all 5s linear 0s;
}

#ballWrapper:active {
    transform: scale(0);
}

The transition from a transform value of scale(1) to scale(0) will make it look as if the element is moving away from you.

view demo

That’s it!

I hope you enjoyed this article and if you have questions, comments, or suggestions, let me know! Thanks for reading.

Posted by: Dhiraj kumar

CSS3 Transitions Effects on Background Gradients

CSS transitions do not have any effect on background gradients. As far as I know, the thing is that something similar would be quite difficult to achieve considering the multitude of possible gradients that can be created using a color palette.

Though, there are some simple ways you can simulate smooth transitions on gradients and below you’ll see how to do that.

faking-transitions-on-gradients

Before writing this article, I was thinking this new article will hopefully be more useful to you as It contains one more extra technique that can help you faking transitions on background gradients.

So, what is this about and why would you care about transitions on gradients? The answer is very simple: just think about the situation when you’re designing some CSS3 icons/buttons. To make them look awesome, it’s almost mandatory to use shadows, rounded corners and gradients.

Read the workarounds described below and you’ll be able to greatly improve your gradient buttons, especially their :hover state.
view demo

Initial styles

For this demo, we’re using three colored boxes to whom are applied the following workarounds.

I extracted only the important styles needed and as you can see, the background-color has the most important role, as it’s the one who’s actually being transitioned here.

.boxes li{
	transition: background-color .2s ease-out;
}

.boxes .red{
	background-color: #da232a;
}

.boxes .red:hover{
	background-color: #e75f64;
}	

.boxes .green{
	background-color: #72b01a;
}

.boxes .green:hover{
	background-color: #9ed354;
}	

.boxes .blue{
	background-color: #269ce9;
}

.boxes .blue:hover{
	background-color: #70b9e8;
}

1. Background-image

Having already a transitioned background-color, you just need to set a semi transparent background using background-image and the result will be a smooth gradient transition for the element to whom these styles are applied to.

background-image: linear-gradient(top, rgba(255,255,255,.5), rgba(255,255,255,0));

2. Box-shadow

Perhaps this is a bit dirtier, but it’s still a fully working technique. Instead of a semi transparent background as above, this assume using an inset box-shadow:

box-shadow: 0 60px 50px -30px rgba(255, 255, 255, .5) inset;

view demo

Conclusion

As you can see, the workarounds above are quite simple and easy to implement. Also, the big advantage is that they don’t require any additional markup element to work.

Thanks for reading and feel free to share your thoughts!

Posted by: Dhiraj kumar

An Awesome CSS3 Animated Dropdown Menu

It’s a sure thing that CSS3 features like transitions, animations and transforms can add extra spice to your designs.

In this article you will see how you can build an awesome CSS3 animated dropdown menu with some of these cool features.  This is something I wished to do for a while and I finally made it. I just added support for smartphones / mobile devices and fixed the navigation for iPad and iPhone also.

css3-animated-dropdown-menu-preview

Here’s a quick preview for the CSS3 animated dropdown menu that we’re going to create today:

css3-menu-animation

The HTML

The HTML structure hasn’t changed at all, simple and minimal. Here’s an excerpt:

<ul id="menu">
        <li><a href="#">Home</a></li>
        <li>
                <a href="#">Categories</a>
                <ul>
                        <li><a href="#">CSS</a></li>
                        <li><a href="#">Graphic design</a></li>
                        <li><a href="#">Development tools</a></li>
                        <li><a href="#">Web design</a></li>
                </ul>
        </li>
        <li><a href="#">Work</a></li>
        <li><a href="#">About</a></li>
        <li><a href="#">Contact</a></li>
</ul>

The CSS

I revised and improved the styles in order to create this unique CSS3 animated dropdown menu. So, below you can find the commented pieces of styles:

Mini reset

Reset the default ul styles.

#menu, #menu ul {
        margin: 0;
        padding: 0;
        list-style: none;
}

Main level

The #menu is basically the main ul for this menu. CSS3 things like gradientsshadows and rounded corners help us to create the below:

css3-menu-wrapper

#menu {
        width: 960px;
        margin: 60px auto;
        border: 1px solid #222;
        background-color: #111;
        background-image: linear-gradient(#444, #111);
        border-radius: 6px;
        box-shadow: 0 1px 1px #777;
}

Clear floats

Here is Nicolas Gallagher‘s clearing method I’ve been using lately:

#menu:before,
#menu:after {
        content: "";

        display: table;
}

#menu:after {
        clear: both;
}

#menu {
        zoom:1;
}

List elements

css3-menu-elements

Please notice the #menu li:hover > a  selector. This is perhaps the most important CSS trick for this CSS3 dropdown menu.

So, this is how this works: Select an “a” element that is child of a “li” ; the “li” element must be a descendant of the “#menu”. Read more here.

#menu li {
        float: left;
        border-right: 1px solid #222;
        box-shadow: 1px 0 0 #444;
        position: relative;
}

#menu a {
        float: left;
        padding: 12px 30px;
        color: #999;
        text-transform: uppercase;
        font: bold 12px Arial, Helvetica;
        text-decoration: none;
        text-shadow: 0 1px 0 #000;
}

#menu li:hover > a {
        color: #fafafa;
}

*html #menu li a:hover { /* IE6 only */
        color: #fafafa;
}

Submenus

With CSS3 transitons we can animate changes to CSS properties like margin or opacity. This is very cool and I’ve used this for animating the CSS3 sub-menus. The result is great if you ask me:

css3-menu-animation

#menu ul {
        margin: 20px 0 0 0;
        _margin: 0; /*IE6 only*/
        opacity: 0;
        visibility: hidden;
        position: absolute;
        top: 38px;
        left: 0;
        z-index: 1;
        background: #444;
        background: linear-gradient(#444, #111);
        box-shadow: 0 -1px 0 rgba(255,255,255,.3);
        border-radius: 3px;
        transition: all .2s ease-in-out;
}

#menu li:hover > ul {
        opacity: 1;
        visibility: visible;
        margin: 0;
}

#menu ul ul {
        top: 0;
        left: 150px;
        margin: 0 0 0 20px;
        _margin: 0; /*IE6 only*/
        box-shadow: -1px 0 0 rgba(255,255,255,.3);
}

#menu ul li {
        float: none;
        display: block;
        border: 0;
        _line-height: 0; /*IE6 only*/
        box-shadow: 0 1px 0 #111, 0 2px 0 #666;
}

#menu ul li:last-child {
        box-shadow: none;
}

#menu ul a {
        padding: 10px;
        width: 130px;
        _height: 10px; /*IE6 only*/
        display: block;
        white-space: nowrap;
        float: none;
        text-transform: none;
}

#menu ul a:hover {
        background-color: #0186ba;
        background-image: linear-gradient(#04acec, #0186ba);
}

First and last list elements styles

css3-dropdown-first-last-items

#menu ul li:first-child > a {
        border-radius: 3px 3px 0 0;
}

#menu ul li:first-child > a:after {
        content: '';
        position: absolute;
        left: 40px;
        top: -6px;
        border-left: 6px solid transparent;
        border-right: 6px solid transparent;
        border-bottom: 6px solid #444;
}

#menu ul ul li:first-child a:after {
        left: -6px;
        top: 50%;
        margin-top: -6px;
        border-left: 0;
        border-bottom: 6px solid transparent;
        border-top: 6px solid transparent;
        border-right: 6px solid #3b3b3b;
}

#menu ul li:first-child a:hover:after {
        border-bottom-color: #04acec;
}

#menu ul ul li:first-child a:hover:after {
        border-right-color: #0299d3;
        border-bottom-color: transparent;
}

#menu ul li:last-child > a {
        border-radius: 0 0 3px 3px;
}

The jQuery

As you already get used to, IE6 gets some extra attention:

$(function() {
  if ($.browser.msie && $.browser.version.substr(0,1)<7)
  {
        $('li').has('ul').mouseover(function(){
                $(this).children('ul').css('visibility','visible');
                }).mouseout(function(){
                $(this).children('ul').css('visibility','hidden');
                })
  }
});

While the :hover pseudo-class does not work for other elements than anchor, we just need to add this small jQuery snippet to fix it. It’s pretty self-explanatory.

Update: Mobile navigation support

css3-mobile-dropdown

This is something I wished to do for a while and I finally made it. I just added support for mobile devices and fixed the navigation for iPad.

You know how much I love CSS only solutions, but this time we’ll be using some jQuery to enhance this menu. To view the result, you can narrow your browser window or browse it with your smartphone.

The viewport meta tag

To maintain everything at the correct scale, the first thing added is the viewport meta tag:

<meta name="viewport" content="width=device-width, initial-scale=1.0">

Small HTML update

You need to wrap the above HTML structure using something like: <nav id="menu-wrap">. This will be our relative holder for the mobile navigation.

The jQuery add

After page loads, we’ll add the #menu-trigger element which does exactly what you think: will trigger the mobile menu when it will be clicked. Further, in the CSS, you’ll see that this element is displayed using CSS3 media queries.

Another thing here is the iPad device detection. As you can see below, we’ll remove the fancy transition effect and stick to toggling display: none/block. This way, the functionality will be maintained also on the iPad.

/* Mobile */
$('#menu-wrap').prepend('<div id="menu-trigger">Menu</div>');
$("#menu-trigger").on("click", function(){
        $("#menu").slideToggle();
});

// iPad
var isiPad = navigator.userAgent.match(/iPad/i) != null;
if (isiPad) $('#menu ul').addClass('no-transition');

The mobile CSS

Here, the CSS3 media queries do the trick. We’ll add CSS rules to override the initial styles:

#menu-trigger { /* Hide it initially */
        display: none;
}

@media screen and (max-width: 600px) {

        #menu-wrap {
                position: relative;
        }

        #menu-wrap * {
                box-sizing: border-box;
        }

        #menu-trigger {
                display: block; /* Show it now */
                height: 40px;
                line-height: 40px;
                cursor: pointer;
                padding: 0 0 0 35px;
                border: 1px solid #222;
                color: #fafafa;
                font-weight: bold;
                background-color: #111;
                /* Multiple backgrounds here, the first is base64 encoded */
                background: url(data:image/png;base64,iVBOR...) no-repeat 10px center, linear-gradient(#444, #111);
                border-radius: 6px;
                box-shadow: 0 1px 1px #777, 0 1px 0 #666 inset;
        }

        #menu {
                margin: 0; padding: 10px;
                position: absolute;
                top: 40px;
                width: 100%;
                z-index: 1;
                display: none;
                box-shadow: none;
        }

        #menu:after {
                content: '';
                position: absolute;
                left: 25px;
                top: -8px;
                border-left: 8px solid transparent;
                border-right: 8px solid transparent;
                border-bottom: 8px solid #444;
        }       

        #menu ul {
                position: static;
                visibility: visible;
                opacity: 1;
                margin: 0;
                background: none;
                box-shadow: none;
        }

        #menu ul ul {
                margin: 0 0 0 20px !important;
                box-shadow: none;
        }

        #menu li {
                position: static;
                display: block;
                float: none;
                border: 0;
                margin: 5px;
                box-shadow: none;
        }

        #menu ul li{
                margin-left: 20px;
                box-shadow: none;
        }

        #menu a{
                display: block;
                float: none;
                padding: 0;
                color: #999;
        }

        #menu a:hover{
                color: #fafafa;
        }       

        #menu ul a{
                padding: 0;
                width: auto;
        }

        #menu ul a:hover{
                background: none;
        }

        #menu ul li:first-child a:after,
        #menu ul ul li:first-child a:after {
                border: 0;
        }               

}

@media screen and (min-width: 600px) {
        #menu {
                display: block !important;
        }
}       

/* iPad */
.no-transition {
        transition: none;
        opacity: 1;
        visibility: visible;
        display: none;
}

#menu li:hover > .no-transition {
        display: block;
}

view demo

Your turn

I hope you enjoyed this article and the techniques I used. Please share your comments and questions below!

Posted by: Dhiraj kumar