3d-bold-navigation
April 10, 2015 | 43 Feedbacks

3D Bold Navigation

A bold navigation that slides in when active, replacing the current content in a 3D space.
Browser support
  • ie
  • Chrome
  • Firefox
  • Safari
  • Opera
9+

Today’s resource is a strong approach to showing a website navigation. Bear in mind, though, it doesn’t have to be the “main” navigation. You could have, for example, a product gallery and you’d like to create a smooth transition while switching from one product category to the other.

To increase the focus on the menu, we pushed the main content along the z-axis (by using CSS transformations we actually scale down the content size, we don’t use 3D translations, but the result is the same).

The interesting bit: when you select a new category, we switch the content in the background, then move it back to the original position, hiding the navigation.

Now let’s dive into the code!

Inpiration: chulakov.com.

The icons used in the demo are from our Nucleo icons application.

Creating the structure

The HTML is structured in 3 main elements: a .cd-nav-trigger used to create the menu icon, a .cd-section element containing the page main content and a .cd-nav-container for the main navigation.

An additional div.cd-overlay has been used to create a shadow layer, visible only when navigation is active.

Adding style

To realise our animation, we used CSS3 Transformations applied to the <main> and <nav> elements.
By default, the navigation has a position fixed and is translated to the right, outside the viewport (translateX(100%)). When user clicks the menu icon, the class .is-visible is added to the <nav> element which is moved back into the viewport (translateX(0)), while the .scale-down class is added to the <main> element to scale it down (scale(.9)). And of course we have used CSS3 Transitions to achieve a smooth animation!

When user selects an item from the navigation, a new .cd-section element is created and inserted in the DOM (more details in the ‘Events handling’ section).

The .cd-selected class is then assigned to this new inserted .cd-section element, while it is removed from the old .cd-section (the content originally visible in the page). This way the new section element (which is initially translated to the right, outside the viewport) is moved back (translateX(0)), covering the old content (z-index: 2).

One note: during this animation you don’t see the old section moving to the right (translateX(100%)) because we set a delay for the .cd-section transition on transformations (it will move after .4s).

Events handling

The index.html file contains only the ‘Intro’ content. A different html file has been created for each section (projects.html, careers.html, ..) with exactly the same structure, but with different .cd-section content.
When user selects a new item from the navigation, a new <section> element is created and inserted in the DOM (loadNewContent function).
The load() function is then used to load the specific section content (we used a data-menu attribute assigned to the navigation list item to determine the file content to be loaded).
Once the new html content has been inserted, we assign the .cd-selected class to the new section and close the navigation.

One note: we implemented a simple load() function to upload the new html content, but you may wanna replace it with a proper $.ajax call in order to proper handle errors, beforeSend request etc. according to your project.

Changelog

Apr 10, 2015
  • Resource released by CodyHouse

Claudia Romano

Web developer, fan of The Big Bang Theory and good food. Co-founder of CodyHouse and Nucleo. You can follow her on Twitter.

  • Sam

    Looking fantastic as always! Thanks for sharing. :-)

  • vburlak

    inspired from http://chulakov.com/menu ?)

    • http://codyhouse.co Claudia Romano

      True! Forgot to mention it in the article. Fixed :)

  • Amit Kolambikar

    This looks great on mobile phones too.

  • meidanmonot

    perfect and usefull work again! Many thanks

  • Gustavo

    ^^

  • Tumenbayev

    Greeeeeeeeeeat

  • Cyber

    It doesn’t work with safari, can anyone solve this problem?

    • http://codyhouse.co Claudia Romano

      Hi Cyber, I just tested it on Safari (Mac) and it’s working fine. What issue are you experiencing? Thanks

  • Chris Irwin

    Hey peeps,

    I am curious how one can hide the cd-nav-trigger when the cd-nav-container is visible. For instance, I would like to set the height of the cd-nav-container to 75% instead of 100%, and give it more of a cover-flow effect. But, it looks bad with both the X and the cd-nav-trigger visible. Any tips??

    • http://codyhouse.co/ Sebastiano Guerriero

      Hi Chris, you should use javascript to assign a class to .cd-nav-trigger when the menu is visible (just like we assign the class .scale-down to the element). You can use this class to assign visibility: hidden; and maybe play with opacity too if you want a fade out effect.

  • John

    i tried a to implement smooth scroll js but its not working .if i remove modernizr.js, it will work. Is there any other way to implement smoothscrool.js?

  • Alvaro

    from what version of firefox, Chrome, Opera, etc. this will work? (I tried in IE8 and of course it doesn’t work)

  • legolass73

    how to put the menu on the left and therefore the animation is done to the left and not right?

  • legolass73

    how to change svg images ?

    • http://codyhouse.co/ Sebastiano Guerriero

      all svg images have been injected as inline SVG inside the .cd-nav unordered list element

  • Rahul Gupta

    Can you tell which theme do you use?
    I want it for my sublime.. THank

  • http://www.siiiimple.com Justin

    Everything seems to be working great, except the links inside the menu don’t click. Hovering over the links shows the correct link path in the browser, but doesn’t go to the actual link. Any reason you could think of that this would occur?

    • http://codyhouse.co Claudia Romano

      Hi Justin, make sure to test it on a local server! the load() function doesn’t work if you’re not on a server (should be a Chrome only issue).

      • Antonio Barrios Jimenez

        Hello! its a great and wonderfull Work! but i have the same problem that Justin! all is working! menu, jq, css, html, all apparently is fine till i do a click to one “li” the link is not working! if a try like c”copy the link” and then i paste it on the bar of a new blank page, its work! its the right link! BUT when i do a click with the mouse its not work! i stay on the same page!

        i will be very happy if i got a answer how can i do with that! of course the rights will be on the impress of the page ! but it can not be uploaded till this problem ll be done!

        Please HELP!

  • Andrey Silyanov?

    Excuse me, I just changed all files to php, and I have changed all links in files, but the navigation doesn’t work. I can only see the white window, when I change the slide.

  • Andrey Silyanov?

    How can I change the code to change the page addres, not only content

    • http://codyhouse.co Claudia Romano

      Hi Andrey, you can give a look at what we did here: http://codyhouse.co/gem/animated-page-transition

      • Andrey Silyanov?

        Thank you Claudia. If you won’t be busy, could you hel[ me with BackButton? I have changed a script a little bit. Now it can change url too, but back button doesn’t work normaly. It is very hard for me to fix it in this template. So here is my script:

        jQuery(document).ready(function($){

        //open navigation clicking the menu icon

        $(‘.cd-nav-trigger’).on(‘click’, function(event){

        event.preventDefault();

        toggleNav(true);

        });

        //close the navigation

        $(‘.cd-close-nav, .cd-overlay’).on(‘click’, function(event){

        event.preventDefault();

        toggleNav(false);

        });

        //select a new section

        $(‘.cd-nav li, a[rel=”tab”]’).on(‘click’, function(event){

        event.preventDefault();

        var url = $(this).attr(‘href’);

        var target = $(this),

        //detect which section user has chosen

        sectionTarget = target.data(‘menu’);

        if( !target.hasClass(‘cd-selected’) ) {

        //if user has selected a section different from the one alredy visible

        //update the navigation -> assign the .cd-selected class to the selected item

        target.addClass(‘cd-selected’).siblings(‘.cd-selected’).removeClass(‘cd-selected’);

        //load the new section

        loadNewContent(sectionTarget);

        } else {

        // otherwise close navigation

        toggleNav(false);

        }

        if(url!=window.location){

        window.history.pushState({path:url},”,url);

        }

        });

        function toggleNav(bool) {

        $(‘.cd-nav-container, .cd-overlay’).toggleClass(‘is-visible’, bool);

        $(‘main’).toggleClass(‘scale-down’, bool);

        }

        function loadNewContent(newSection) {

        //create a new section element and insert it into the DOM

        var section = $(”).appendTo($(‘main’));

        //load the new content from the proper php file

        section.load(newSection+’.php .cd-section > *’, function(event){

        //add the .cd-selected to the new section element -> it will cover the old one

        section.addClass(‘cd-selected’).on(‘webkitTransitionEnd otransitionend oTransitionEnd msTransitionEnd transitionend’, function(){

        //close navigation

        toggleNav(false);

        });

        section.prev(‘.cd-selected’).removeClass(‘cd-selected’);

        });

        $(‘main’).on(‘webkitTransitionEnd otransitionend oTransitionEnd msTransitionEnd transitionend’, function(){

        //once the navigation is closed, remove the old section from the DOM

        section.prev(‘.cd-section’).remove();

        });

        if( $(‘.no-csstransitions’).length > 0 ) {

        //if browser doesn’t support transitions – don’t wait but close navigation and remove old item

        toggleNav(false);

        section.prev(‘.cd-section’).remove();

        }

        }

        });

      • Andrey Silyanov?

        Thank you Claudia. I worked with it a little bit and I have some problems, but firstly-about the achivments: now it changes the url when you change the page. Back-button works almost as usualy, except one thing: it works only with two clicks, and I can not change the selected “li” element in menu. So, here is the code:

        jQuery(document).ready(function($){
        //open navigation clicking the menu icon
        $(‘.cd-nav-trigger’).on(‘click’, function(event){
        event.preventDefault();
        toggleNav(true);
        });
        //close the navigation
        $(‘.cd-close-nav, .cd-overlay’).on(‘click’, function(event){
        event.preventDefault();
        toggleNav(false);
        });
        //select a new section
        $(‘.cd-nav li, a[rel=”tab”]’).on(‘click’, function(event){
        event.preventDefault();
        var url = $(this).attr(‘href’);
        var target = $(this);
        //detect which section user has chosen
        sectionTarget = target.data(‘menu’);
        if( !target.hasClass(‘cd-selected’) ) {
        //if user has selected a section different from the one alredy visible
        //update the navigation -> assign the .cd-selected class to the selected item
        target.addClass(‘cd-selected’).siblings(‘.cd-selected’).removeClass(‘cd-selected’);
        //load the new section
        loadNewContent(sectionTarget);
        } else {
        // otherwise close navigation
        toggleNav(false);
        }
        if(url!=window.location){
        window.history.pushState({path:url},”,url);
        }
        });

        function toggleNav(bool) {
        $(‘.cd-nav-container, .cd-overlay’).toggleClass(‘is-visible’, bool);
        $(‘main’).toggleClass(‘scale-down’, bool);
        }

        function loadNewContent(newSection) {
        //create a new section element and insert it into the DOM
        var section = $(”).appendTo($(‘main’));
        //load the new content from the proper php file
        section.load(newSection+’.php .cd-section > *’, function(event){
        //add the .cd-selected to the new section element -> it will cover the old one
        section.addClass(‘cd-selected’).on(‘webkitTransitionEnd otransitionend oTransitionEnd msTransitionEnd transitionend’, function(){
        //close navigation
        toggleNav(false);

        });
        section.prev(‘.cd-selected’).removeClass(‘cd-selected’);
        });

        $(‘main’).on(‘webkitTransitionEnd otransitionend oTransitionEnd msTransitionEnd transitionend’, function(){
        //once the navigation is closed, remove the old section from the DOM
        section.prev(‘.cd-section’).remove();
        });

        if( $(‘.no-csstransitions’).length > 0 ) {
        //if browser doesn’t support transitions – don’t wait but close navigation and remove old item
        toggleNav(false);
        section.prev(‘.cd-section’).remove();
        }
        $(window).on(‘popstate’, function() {
        var newPageArray = location.pathname.split(‘/’),
        //this is the url of the page to be loaded
        newPage = newPageArray[newPageArray.length – 1];
        var target = newPage.replace(‘.php’ , ”);
        loadNewContent(target);
        });
        });

  • Web Developer ♥

    Hi Claudia,
    Great navigation, thanks a lot!
    I was wondering if there’s a way to show up the link in the browsers address bar for the current section (e.g. …/services).
    Also, can we show dynamic (php pages) using this method (no page refresh).
    Thanks!
    Regards.

    • Andrey Silyanov?

      For using php, just change ‘html’ to ‘php’ in main.js. (U can find it by using ctrl+f).
      For changing url look for Browser History API in internet.

      • Web Developer ♥

        Oh OK! Thank you! :)

    • http://codyhouse.co Claudia Romano

      Hi, you may try giving a look at what we did here:
      http://codyhouse.co/gem/animated-page-transition-2/

      Hope this helps!

      • Web Developer ♥

        It helps. Thank you! :))))

  • http://jestemrugbysta.tumblr.com rugbysta

    hi, i try add http://codyhouse.co/gem/back-to-top/ to this navigation but it didnt work :(
    back to top work only if i turn off modernizer but then nav didnt work

  • kenny

    How do you adjust this slider to show the panel full screen for ios? I got it to work everywhere else but ios

  • Corey

    What would be the best way of implementing this in WordPress? My question derives from the fact that the index’s content is coming before the nav. So if i were to put the nav html into a header.php, i could potentially just add index’s content to say “front page” on WordPress settings?

  • Goronwy

    Hello. I really like this menu structure and would like to use it in my project. I am however very new to this discipline and would be grateful for some assistance.

    I think I understand the purpose of the 100vh specification in making the menu structure look right but this is causing me problems as the about me page for example has content that is longer than the window height. This is causing the top portion to be chopped off.

    Is there a straight forward way to adapt this? I have tried various methods and in my ignorance I have only managed a workaround by applying a vh top margin to the header once created (.cd-section.about header). This isn’t right though as there is overspill onto the main section that requires both to have the same background colour or it looks a mess.

    Any help or suggestions gratefully received.

  • Jurjen Vos

    It seems that content I’m changing on other pages, be it the about page or anything else, it doens’t get changed.. Only the index.html is changing accordingly. Any idea?

    I can even delete the other pages except index.html and it still gets loaded. What is getting loaded actually?!

  • Ahmed Khatib

    Hi Claudia,
    gr8 tutorial!
    could you please tell me the tests included in the Modernizr.js file,
    thank you

  • Heidi Cone

    This nav looks great, but for the life of me, I can’t get it to work when loading different pages on the website… I’ve already spent two days trying to implement it. I wish there was a working example demonstrating how to use this navigation with loading different pages.

    • Jose Suarez

      It happens to me the same thing, as you have solved ?

  • ArKzag

    I place a slider in the home and then change the content and return where this slider, this does not already appear, help me

  • sergeylukin

    Thank you. It looks awesome. I’ve made CSS only version of your menu activation functionality: http://codepen.io/sergeylukin/pen/dpZQqK

    • Stephen Canning

      How do i change the icons using your version?

      • sergeylukin

        Icons are represented by tags in HTML with class “nc-icon”, just replace those with your SVGs or images or whatever.

        • Stephen Canning

          Thats great, thank you

          Also have you any idea how i get icons to animate like on here: http://chulakov.com/menu