carousel style post navigation with Parallax

Posted on 7th February, 2014 1 Comment

Recently I noticed the BBC’s really super sweet category navigation, in the form of a slider that is the full screen width, that shows the current categories articles, with the next and previous article being displayed behind an opaque overlay.

BBC home page

Looks awesome right? Well I thought so, and this tickled my developer funny-bone and inspired me to create this article.

I instantly thought it would work perfectly if I created a similar style of carousel navigation to navigate through all the single posts of a site. Of course this will be full width and thanks to a few CSS media queries, is also fully responsive! So lets begin.

  • Uses the default featured image for the slide
  • The post title will be displayed as the caption
  • Continues next and previous post navigation
  • Responsive and mobile friendly

Create a new php document

Let’s create a new document and save it as post-carousel-navigation.php
We’re going to add about 70 lines of code to make this function, Check the comments for more information.

Include support for thumbnails to your theme

The theme I’m building this for has a maximum width for the content of 1150px so that’s the size that I’m going to set the images to be cropped at using add_image_size. We’re also adding a default image for when you forget to add on to your post also included in the zip are the chevrons for the navigational thumbs…

Download the default thumb/chevrons here wptricks-carousel-images.zip and add them to your current themes images folder.

if ( function_exists( 'add_theme_support' ) ) {
	add_theme_support( 'post-thumbnails' ); 
	add_image_size('slider-thumb', 1150, 350, true ); // SLIDER THUMB
}
function default_thumbnail(){
	if ( has_post_thumbnail() ) {
	  the_post_thumbnail('slider-thumb');
	} else { ?>
      <img src="<?php bloginfo('template_directory'); ?>/images/default-slide.png" alt="<?php the_title(); ?>" />
	<?php }
}

Include the previous posts link and featured image

The backbone part of this is taken from this article at tutsplus.com.
I’ve modified it quite a bit to suite what I needed it to do, by creating a continuous loop of posts that include; currentpost, next and previous posts titles, publish dates, and featured images.
+ It’s responsive
+ Has a parallax effect
+ Has a sticky navigation, activated when the viewport meets the div to stick.

Like we would normally have a previous and next link below our posts, we’re going to check that they exist, but we’re going to pull the featured image as well as the link to that post.

<div id="post-carousel" class="outer-wrapper">
	<ul id="post-carousel-nav">  
        <?php /* Get the previous posts featured image 
		--------------------------------------------------*/
			 $prevPost = get_previous_post(true);  
            if($prevPost) {  
                $args = array(  
                    'posts_per_page' => 1,  
                    'include' => $prevPost->ID  
                );  
                $prevPost = get_posts($args);  
                foreach ($prevPost as $post) {  
                    setup_postdata($post);  
        ?>  
		<?php /* Display the PREVIOUS featured image */ ?>
            <li class="previous">  
                <a href="<?php the_permalink(); ?>" class="previous"><i class="chevron-left"></i></a>
                <a href="<?php the_permalink(); ?>" class="prev-thumb"><?php default_thumbnail(); ?>
				<div class="slider-date"><?php the_time('M d, Y'); ?></div>
				<div class="slider-title"><?php the_title(); ?></div></a>
            </li>  
			        <?php  
                    wp_reset_postdata();  
                } //end foreach  
				
			} else { /* Loop back to the end */
			$first = new WP_Query('posts_per_page=1&order=DESC'); $first->the_post();
	?>	
			<li class="previous"> 
				<a href="<?php the_permalink(); ?>" class="previous"><i class="chevron-left"></i></a>
				<a href="<?php the_permalink(); ?>" class="prev-thumb"><?php default_thumbnail(); ?>
				<div class="slider-date"><?php the_time('M d, Y'); ?></div>
				<div class="slider-title"><?php the_title(); ?></div></a>
			</li>
	<?php
	wp_reset_query();
	
            } // end if  
        ?>   

Then Include our current post

The current post is super simple, we just need to pull the slider-thumb attached to the current open post.

			<?php /* Display the current posts featured image 
			-----------------------------------------------------*/	 ?>
					<li class="current"><?php default_thumbnail(); ?>
					<div class="slider-date"><?php the_time('M d, Y'); ?></div>
					<div class="slider-title"><?php the_title(); ?></div>
					</li>
			

Then the next post

			<?php /* Get the next posts featured image 
			--------------------------------------------------*/
			
				$nextPost = get_next_post(true);  
				if($nextPost) {  
					$args = array(  
						'posts_per_page' => 1,  
						'include' => $nextPost->ID  
					);  
					$nextPost = get_posts($args);  
					foreach ($nextPost as $post) {  
						setup_postdata($post);  
			?>  
			<?php /* Display the NEXT featured image */ ?>
				<li class="next">  
					<a href="<?php the_permalink(); ?>" class="next"><i class="chevron-right"></i></a> 
					<a href="<?php the_permalink(); ?>" class="next-thumb"><?php default_thumbnail(); ?>
					<div class="slider-date"><?php the_time('M d, Y'); ?></div>
					<div class="slider-title"><?php the_title(); ?></div></a>
				</li>  
			<?php  
						wp_reset_postdata();  
					} //end foreach  
					
				} else { /* Loop back to the beginning */
				$last = new WP_Query('posts_per_page=1&order=ASC'); $last->the_post();
		?>
				<li class="next"> 
					<a href="<?php the_permalink(); ?>" class="next"><i class="chevron-right"></i></a>
					<a href="<?php the_permalink(); ?>" class="next-thumb"><?php default_thumbnail(); ?>
					<div class="slider-date"><?php the_time('M d, Y'); ?></div>
					<div class="slider-title"><?php the_title(); ?></div></a>
				</li>
		<?php
		wp_reset_query();
				
				
            } // end if  
        ?>   

Finally include navigation for smaller screens

These will remain hidden until the screen reaches a minimum width of 1120px;

    <nav class="post-navigation">
				<div class="prev-post"><?php previous_post_link('%link', '<i class="chevron-left"></i>', TRUE); ?></div>
				<div class="next-post"><?php next_post_link('%link', '<i class="chevron-right"></i>', TRUE); ?></div>
			</nav>
</div>

The CSS

These are the base styles you’ll need for this to sit correctly on your page, plus a few small style additions.

/* SINGLE POSTS SLIDER/NAVIGATION */

.slider-date {
	background: #FFF;
	color: #FF3B12;
	font-size: 18px;
	padding: 8px 12px;
	margin-bottom: 40px;
	position: absolute;
	right: 0;
	top: 0;
}
/* Centralise our carousel */
#post-carousel {
	position: relative;
	width: 3450px; /* width of 3 slides*/
	height: 350px;
	margin-left: -1725px; /* minus half */
	left: 50%; /* position left by 50% */
	overflow: hidden;
}
#post-carousel ul {
	position: absolute;
	padding: 0;
	margin: 0;
}
#post-carousel li {
	position: relative;
	display: inline-block;
	width: 1150px;
	height: 350px;
	float: left;
}
#post-carousel li img {
	display: block;
	height: auto;
	margin: auto;
	max-width: 100%;
}
#post-carousel-nav li a {
	display: block;
}
#post-carousel-nav li a.previous, #post-carousel-nav li a.next {
	position: absolute;
	z-index: 3;
	color: #ff3b12;
	opacity: 0.6;
	font-size: 90px;
	padding: 12px 18px;
	top: 50%;
	margin-top: -61px;
}
#post-carousel-nav a.previous {
	right: -12px;
}
#post-carousel-nav a.next {
	left: -12px;
}
#post-carousel-nav li a.prev-thumb:before, #post-carousel-nav li a.next-thumb:before {
	content: """;
	position: absolute;
	top: 0;
	right: 0;
	bottom: 0;
	left: 0;
 opacity: .8 bckground: #fff;
}
#post-carousel > nav {
	width: 100%;
	max-width: 1150px;
	position: absolute;
	top: 36%;
	margin: 0;
	height: 67px;
	display: none;
}
#post-carousel > nav a {
	position: absolute;
	display: inline-block;
	width: 35px;
	height: 67px;
}
#post-carousel > nav a[rel=next] {
	right: 0;
}
#post-carousel > nav a[rel=prev] {
	left: 0;
}
.slider-title {
	position: absolute;
	bottom: 0;
	left: 0;
	font-size: 32px;
	line-height: 45px;
	color: #fff;
	max-width: 300px;
	background: #ff3b12;
}
i.chevron-left, i.chevron-right {
	background: url(images/sprite.png) transparent;
	width: 35px;
	height: 67px;
	display: inline-block;
}
i.chevron-left {
	background-position: left bottom;
}
i.chevron-right {
	background-position: left top;
}

The Javascript

This super simple parallax effect below is a modified script from this codepen. With added multiple effect.

  1. Create a new document and save it as posts-carousel.js
  2. Place it in a folder called javascript
  3. Place that in folder your main theme folder

Parallax Effect:

function parallax(){
        var scrolled = $(window).scrollTop();
        $('#post-carousel ul').css('bottom', -(scrolled * 0.3) + 'px');
        $('#post-carousel li span').css('marginBottom', +(scrolled * 0.15) + 'px');
    }
$(window).scroll(function(e){
        parallax(); 
});

Sticky Navigation:

Add this below the parallax function that we just added. Select the highlighted section only.

function parallax() {
        var scrolled = $(window).scrollTop();
        $('.parallax ul').css('bottom', -(scrolled * 0.3) + 'px');
        $('.bx-controls-direction a i, #post-carousel > nav').css('marginTop', +(scrolled * 0.3) + 'px');
        $('.parallax li .slider-title').css('marginBottom', +(scrolled * 0.15) + 'px');
    }

var stickynavigation = $('nav').offset().top;
    function stickynav() {
    	if( $(window).scrollTop() > stickynavigation ) {
                        $('nav').addClass('sticky');
                } else {
                        $('nav').removeClass('sticky');
                } // END if
   }

 $(window).scroll(function(e){
        parallax();
	...

Then include a if statement into the .scroll function that will check if we’ve scrolled to our navigation, if have, it’ll apply a class of sticky to the navigation, Select the highlighted section.

    
	function parallax(){
        var scrolled = $(window).scrollTop();
        $('#post-carousel ul').css('bottom', -(scrolled * 0.3) + 'px');
        $('#post-carousel li span').css('marginBottom', +(scrolled * 0.15) + 'px');
    }
    
	var stickynavigation = $('nav').offset().top;
    function stickynav() {
    	if( $(window).scrollTop() > stickynavigation ) {
                        $('nav').addClass('sticky');
                } else {
                        $('nav').removeClass('sticky');
                } // END if
   }
        
    $(window).scroll(function(e){
        parallax(); 
        stickynav();       
    });

Display the Post Carousel in your theme

If you added the post-carousel-navigation.php to your root theme folder, just add this snip to the top of the single.php file, below the if (have_posts()) : while (have_posts()) : the_post(); bit.

<?php include 'post-carousel-navigation.php'; ?>

Now you’ll need to go create three posts, upload a new featured for each post with a width of at least 1150px wide.
With that done refresh your home page and test it all works…

@media Queries

Basically this shows our hidden navigation and makes sure our slider fits the screen by adding 100% width;

@media all and (max-width: 1170px) {
#post-carousel {
	left: 0;
	margin-left: 0;
	width: 100%;
	height: auto;
}
#post-carousel li {
	float: none;
	height: auto;
	width: 100%;
}
#post-carousel .previous, #post-carousel .next {
	display: none;
}
#post-carousel ul {
	position: relative;
}
#post-carousel > nav {
	display: block;
}
}

Please leave a comment or share if you enjoyed this article.

Comments

To preserve code added to a comment you can wrap your code in short tags
by using [square brackets]:

  1. PHP use - [php] <?php code here ?> [/php]
  2. CSS use - [css] #code-here {} [/css]
  3. HTML use - [html] <div> code here </div> [/html]
  4. JS use - [js] $(".codeHere") [/js]

Diah

18th, May, 17

Hello, I’m trying to implement this feature and it’s great! Everything seems to work, except the parallax, I don’t see how the JS is being called anywhere?

How is it being called? Thank you

Leave a Comment

To preserve code added to a comment you can wrap your code in short tags
by using [square brackets]:

  1. PHP use - [php] <?php code here ?> [/php]
  2. CSS use - [css] #code-here {} [/css]
  3. HTML use - [html] <div> code here </div> [/html]
  4. JS use - [js] $(".codeHere") [/js]