WordPress WP_Query: Get Posts by Meta Values

As you know all the posts have the metadata you can fill in “Custom fields” metabox (it can also be hidden). So, for example, if you want to get a post with meta key show_in_slider and meta value true, you can do it in the following way:

<?php
$args = array(
	'meta_key' => 'show_in_slider',
	'meta_value' => 'true'
);
 
$allRecords = new WP_Query( $args );
?>

Otherwise, if you need to query all posts except the ones with this pair of meta key and value, you can use the following parameters:

<?php
$args = array(
	'meta_key' => 'show_in_slider',
	'meta_value' => 'true',
	'meta_compare' => '!='
);
 
$allRecords = new WP_Query( $args );
?>

Do not forget that all examples in this post are simplified, so, some of WP_Query parameters are missing, e.g posts_per_page or post_type.

This was very simple examples, just an introdution. But this post is about meta_query parameter. This parameter allows us to create a really cool post filters and search scripts.

meta_query Usage Examples

Get Posts with a Specific Custom Field Value

This is a simple example. Let’s get all the posts with custom field name “color” and custom field value “white”.

<?php 
// the meta_key 'blog_type' with the meta_value 'clasic'
$args = array(
	'meta_query' => array(
		array(
			'key' => 'blog_type',
			'value' => 'clasic'
		)
	)
);
 
$allRecords = new WP_Query( $args );
?>

Get all the posts except the ones with meta key “blog_type” and meta value “clasic”:

<?php
$args = array(
	'meta_query' => array(
		array(
			'key' => 'blog_type',
			'value' => 'clasic',
			'compare' => '!='
		)
	)
);
 
$allRecords = new WP_Query( $args );
?>

Now let’s get all the posts with clasic OR regular type custom field value:

<?php
// custom field name is blog_type and custom field value is 'clasic' OR 'regular'
$args = array(
	'meta_query' => array(
		array(
			'key' => 'blog_type',
			'value' => array('clasic','regular'),
			'compare' => 'IN'
		)
	)
);
 
$allRecords = new WP_Query( $args );
?>

Get all the posts except clasic and regular posts:

<?php
$args = array(
	'meta_query' => array(
		array(
			'key' => 'blog_type',
			'value' => array('clasic','regular'),
			'compare' => 'NOT IN'
		)
	)
);
 
$allRecords = new WP_Query( $args );
?>

Get Posts Within a Given Range of Numeric Meta Values

For example, let’s filter the post by hit’s rang:

<?php
// The post hit's is more than 9000 and less than 10000
$args = array(
	'meta_query' => array(
		array(
			'key' => 'hits',
			'value' => array( 9000, 10000 ),
			'type' => 'numeric',
			'compare' => 'BETWEEN'
		)
	)
);
 
$allRecords = new WP_Query( $args );
?>

Numeric Comparison

The post hit’s in this example is 9999 or more than 9999:

<?php 
$args = array(
	'meta_query' => array(
		array(
			'key' => 'hits',
			'value' => 9999,
			'type' => 'numeric',
			'compare' => '>='
		)
	)
);
 
$allRecords = new WP_Query( $args );
?>

The post hit’s less than 100:

<?php
$args = array(
	'meta_query' => array(
		array(
			'key' => 'hits',
			'value' => 100,
			'type' => 'numeric',
			'compare' => '<'
		)
	)
);
 
$allRecords = new WP_Query( $args );
?>

Query Posts by Two Or More Custom Field Values

Let’s combine some of the previous examples:

<?php
// the 'blog_type' is 'clasic' AND the 'hits' is more than 9900 and less than 10000
$rd_args = array(
	'meta_query' => array(
		'relation' => 'AND',
		array(
			'key' => 'blog_type',
			'value' => 'clasic'
		),
		array(
			'key' => 'hits',
			'value' => array( 9900, 10000 ),
			'type' => 'numeric',
			'compare' => 'BETWEEN'
		)
	)
);
 
$rd_query = new WP_Query( $rd_args );
?>

I think, all above examples are sufficient. If any one have any issue then put your comments bellow.

How to Integrate responsive-nav.js into WordPress Navigation

Responsive Web Design is all the rage these days. Clients are asking for it, web developers are expected to know it, and most importantly, mobile devices are more popular than ever. One big area of a website is website navigation. In my post, I talk all about responsive navigation and how to make it work nicely in WordPress.

responsive-nav.js is a fantastic, and more importantly, light-weight, piece of javascript code that will automatically switch out your current, full-width navigation for an animated pull-down section on mobile. In this post, we will:

  1. Define our menu
  2. Enqueue responsive-nav.js and accompanying CSS
  3. Add the javascript that does the heavy lifting to our template

So let’s start with the easy part: defining new menu. In functions.php of current theme:

<?php 
if ( function_exists( 'add_theme_support' ) ) { 
    add_theme_support( 'menus' );
}
?>

Then add this to your header.php (or wherever you want to add the menu):

<nav class="nav-menu">
    <?php wp_nav_menu( array('menu' => 'Main' )); ?>
</nav>

Perfect! Now you can choose the “Main” menu from the WordPress Menu admin section. Next, Enqueue responsive-nav.js. Now head over to responsive-nav.com and download the files. I always place theme-specific javascript and it’s CSS in a folder called /js/ in the theme folder.

Now, Again open up functions.php and add this:

<?php 
function responsive_scripts() {
    wp_enqueue_script('responsive-nav', get_template_directory_uri() .'/js/responsive-nav.js');
    wp_enqueue_style('resnav-css', get_template_directory_uri() .'/css/responsive-nav.css');
}
add_action( 'wp_enqueue_scripts', 'responsive_scripts' );

function responsive_footer_script(){
 echo '<script>
           var navigation = responsiveNav(".nav-menu", {
               label: "- navigate -"
           });
       </script>';
}
add_action( 'wp_footer', 'responsive_footer_script' );
?>

The above code will properly add the script & CSS to the of your theme.

That’s it! Now you have a responsive nav menu in your website.

Taking Control of WordPress 3.8 Admin Bar

What is WordPress Admin Bar?

WordPress admin bar was introduced in WordPress 3.1. The purpose of the WordPress Admin Bar was to connect the backend (dashboard) of a WordPress to the Live. It always shows up right below the browser address bar and looks somewhat like below image:

wordpress admin nav

The WordPress Admin Bar helps webmasters switch to the basic features of the Dashboard directly from their WordPress front-end. Although the presence of the WordPress Admin Bar is a boon, most webmasters don’t like the presence of anything sitting on our sites, I guess the 1-click access to the WordPress Dashboard isn’t what everybody is comfortable with.

Why an Admin Bar?

“First step towards a front-end editor” – Matt Mullenweg, the man who gave birth to WordPress.

The WordPress admin bar has been tagged as the first step towards bringing the WordPress editor right into your site and moving it out of the Dashboard. It will be interesting to see how WordPress incorporates the Dashboard features into our blog’s front end without making it tacky. For now, Admin Bar is here and needs a lot of improvements.

Remove Links from the WordPress Admin Bar

There is lot of things, That you want to remove from the WordPress Admin Bar. Before we start with adding new links to the WordPress Admin Bar (which is a bit complex) we will start removing remove links from the WordPress Admin Bar.

Remove Author Name Menu or just sub-parts

The very first drop down menu in the WordPress Admin Bar is the name of author. It will have two options – Edit Profile and Logout. You can remove this complete menu (or just the sub-parts) by inserting the below code in

functions.php

of your current theme:

<?php

function editMyAdminBar() {
    global $wp_admin_bar;
    $wp_admin_bar->remove_menu('my-account-with-avatar');
    // This will hide the menu item with author name.

    $wp_admin_bar->remove_menu('edit-profile');
    // This will remove the sub-part "Edit My Profile".

    $wp_admin_bar->remove_menu('logout');
    // This will remove the sub-part "Logout".
}

add_action('wp_before_admin_bar_render', 'editMyAdminBar');
?>

Next is the Dashboard link in the WordPress Admin Bar. Insert below code in

functions.php

:

<?php

function editMyAdminBar() {
    global $wp_admin_bar;
    $wp_admin_bar->remove_menu('dashboard');
}

add_action('wp_before_admin_bar_render', 'editMyAdminBar');
?>

Next is the Add New link which has lot of sub items too and we have some other menus in our admin bar. Use the below code to remove all or sub items:

<?php

function editMyAdminBar() {
    global $wp_admin_bar;
    $wp_admin_bar->remove_menu('new-content');
    // This removes the complete menu “Add New”. You will not require the below “remove_menu” if you using this line.

    $wp_admin_bar->remove_menu('new-post');
    // This will hide the menu item “Post”.

    $wp_admin_bar->remove_menu('new-page');
    // This will hide the menu item “Page”.

    $wp_admin_bar->remove_menu('new-media');
    // This will hide the menu item “Media”.

    $wp_admin_bar->remove_menu('new-link');
    // This will hide the menu item “Link”.

    $wp_admin_bar->remove_menu('new-user');
    // This will hide the menu item “User”.

    $wp_admin_bar->remove_menu('new-theme');
    // This will hide the menu item “Theme”.

    $wp_admin_bar->remove_menu('new-plugin');
    // This will hide the menu item “Plugin”.

    $wp_admin_bar->remove_menu('comments');
    // This will hide the menu “Comments”.

    $wp_admin_bar->remove_menu('appearance');
    // This removes the complete menu “Appearance”. You will not require the below “remove_menu” if you using this line.

    $wp_admin_bar->remove_menu('new-themes');
    // This will hide the menu item “Themes”.

    $wp_admin_bar->remove_menu('new-widgets');
    // This will hide the menu item “Widgets”.

    $wp_admin_bar->remove_menu('new-menus');
    // This will hide the menu item “Menus”.

    $wp_admin_bar->remove_menu('updates');
    // This will hide the menu “Updates”.

    $wp_admin_bar->remove_menu('get-shortlink');
    // This will hide the menu “Shortlink”.
}

add_action('wp_before_admin_bar_render', 'editMyAdminBar');
?>

Now we are moving to Add Links to WordPress Admin Bar

Most of sites have a link to the homepage, if you want to add one then you can use the below code in your

functions.php

:

<?php
function add_new_item_to_adminbar() {
    global $wp_admin_bar;
    $wp_admin_bar->add_menu(array(
        'id' => 'view-site', //the view-site ID that refers to what we are doing.
        'title' => __('Visit Site'), //the anchor text that links to homepage.
        'href' => site_url())); //the homepage URL to which the anchor text will connect.
}

add_action('wp_before_admin_bar_render', 'add_new_item_to_adminbar');
?>

Add sub-menu item in “Add New” menu

This will be interesting. We will add a new item inside a menu that already exists. The below code will add a My Media option in the menu Add New.

<?php
function add_submenu_to_adminbar() {
    global $wp_admin_bar;
    $wp_admin_bar->add_menu( array(
        'parent' => 'new-content',
        // new-content is the ID for “Add New” menu so we use it as parent ID.
        
        'id' => 'new_media', 
        // You can add any value here as you are adding something very new here.
        
        'title' => __('Media'), // The anchor text.
        
        'href' => admin_url( 'media-new.php') 
        // name of file to which you will link to.
        ));
}
add_action( 'wp_before_admin_bar_render', 'add_submenu_to_adminbar' );
?>

Hope! this is a good tutorial for all my blog reader, If any one have any query’s and error please put your comments bellow.

How to Control WordPress Custom Post Types, Capabilities and Roles

As We all knows about Custom Post Types and how to create them, when we create custom post types without Capabilities all users except subscriber roles can publish, read, edit and delete them by default. What if we wanted to create a custom post type that Author could read, edit and publish but Author Staff could only read? Well here’s were custom post types and capabilities gets interesting! Take the following basic custom post type for registering Article:

<?php 
add_action( 'init', 'register_article_post' );

function register_article_post() {

    $labels = array( 
        'name' => _x( 'Articles', 'article' ),
        'singular_name' => _x( 'Article', 'article' ),
        'add_new' => _x( 'Add New', 'article' ),
        'add_new_item' => _x( 'Add New Article', 'article' ),
        'edit_item' => _x( 'Edit Article', 'article' ),
        'new_item' => _x( 'New Article', 'article' ),
        'view_item' => _x( 'View Article', 'article' ),
        'search_items' => _x( 'Search Articles', 'article' ),
        'not_found' => _x( 'No articles found', 'article' ),
        'not_found_in_trash' => _x( 'No articles found in Trash', 'article' ),
        'parent_item_colon' => _x( 'Parent Article:', 'article' ),
        'menu_name' => _x( 'Articles', 'article' ),
    );

    $args = array( 
        'labels' => $labels,
        'hierarchical' => true,
        'supports' => array( 'title', 'editor' ),
        'public' => true,
        'show_ui' => true,
        'show_in_menu' => true,
        'show_in_nav_menus' => true,
        'publicly_queryable' => true,
        'exclude_from_search' => false,
        'has_archive' => true,
        'query_var' => true,
        'can_export' => true,
        'rewrite' => true,
    );
    register_post_type( 'article', $args );
}
?>

The above example would give all users (above subscriber) full capabilities over the custom post type Article, like all can read, publish, edit and delete them. When we add ‘map_meta_cap, capabilities and capability_type’ to the $args array we can take more control over it.

Lets modify the $args first by adding map_meta_cap capabilities, and capability_type:

<?php 
add_action( 'init', 'register_article_post' );

function register_article_post() {

    $labels = array( 
        'name' => _x( 'Articles', 'article' ),
        'singular_name' => _x( 'Article', 'article' ),
        'add_new' => _x( 'Add New', 'article' ),
        'add_new_item' => _x( 'Add New Article', 'article' ),
        'edit_item' => _x( 'Edit Article', 'article' ),
        'new_item' => _x( 'New Article', 'article' ),
        'view_item' => _x( 'View Article', 'article' ),
        'search_items' => _x( 'Search Articles', 'article' ),
        'not_found' => _x( 'No articles found', 'article' ),
        'not_found_in_trash' => _x( 'No articles found in Trash', 'article' ),
        'parent_item_colon' => _x( 'Parent Article:', 'article' ),
        'menu_name' => _x( 'Articles', 'article' ),
    );

    $args = array( 
        'labels' => $labels,
        'hierarchical' => true,
        'supports' => array( 'title', 'editor' ),
        'public' => true,
        'show_ui' => true,
        'show_in_menu' => true,
        'show_in_nav_menus' => true,
        'publicly_queryable' => true,
        'exclude_from_search' => false,
        'has_archive' => true,
        'query_var' => true,
        'can_export' => true,
        'rewrite' => true,

        'map_meta_cap' => true,
        // map_meta_cap will allow us to remap the existing capabilities with new capabilities to match the new custom post type

        // capabilities are what we are customising so lets remap them
        'capabilities' => array(
            'edit_post' => 'edit_article',
            'edit_posts' => 'edit_articles',
            'edit_others_posts' => 'edit_other_articles',
            'publish_posts' => 'publish_articles',
            'edit_publish_posts' => 'edit_publish_articles',
            'read_post' => 'read_articles',
            'read_private_posts' => 'read_private_articles',
            'delete_post' => 'delete_article'
        ),
        // capability_type defines how to make words plural, by default the
        // second word has an 's' added to it and for 'article' that's fine
        // however when it comes to words like book the plural would become
        // books so it's worth adding your own regardless of the plural.
        'capability_type' => array('article', 'articles'),
    );
    register_post_type( 'article', $args );
}
?>

So now we have a Custom Post Type with Capabilities remapped to our own custom Capabilities with our own plural words. All we have to do now is add the capability to the roles.

Look at bellow example:

<?php 
function manage_capabilities() {
    // gets the role to add capabilities to
    $admin = get_role( 'administrator' );
    $editor = get_role( 'editor' );
	// replicate all the remapped capabilites from the custom post type article
    $caps = array(
    	'edit_article',
    	'edit_articles',
    	'edit_other_articles',
    	'publish_articles',
    	'edit_published_articles',
    	'read_articles',
    	'read_private_articles',
    	'delete_article'
    );
    // give all the capabilities to the administrator
    foreach ($caps as $cap) {
	    $admin->add_cap( $cap );
    }
    // limited the capabilities to the editor or a custom role 
    $editor->add_cap( 'edit_article' );
    $editor->add_cap( 'edit_articles' );
    $editor->add_cap( 'read_articles' );
}
add_action( 'admin_init', 'manage_capabilities');
?>

I think this blog post is really helpful for my blog reader’s, if any one have any query’s then please put your comments

Notify WordPress users of newly published post

So you have a post section and each time you publish a new custom post you’d like to notify all your users (subscriber). It could be a post, a product, an event or perhaps a tutorial etc.

Usually the action hook would be ‘publish_post’ or ‘publish_page’ but those hooks only work for Posts and Pages.

The following example shows how this can be done to notify users that a Deputy Head has submitted a lesson for review:

<?php
function notify_users($post_ID)  {
	// a conditional to check that this is a new post
	if( ( $_POST['post_status'] == 'publish' ) && ( $_POST['original_post_status'] != 'publish' ) ) {
		// get all users email addresses
		$wp_user_search = new WP_User_Query( array( 'fields' => array('user_email') ) );
		$usersarray = $wp_user_search->get_results();
		$arrUsers = array();
		// store each email for later use
		for ($arr = $usersarray, $allU = count($arr), $key = 0; $key < $allU; $key++) {
			$arrUsers[] = $arr[$key]->user_email;
		}
		// create the from details 
		$headers[] = 'From: Site Admin<admin@example.net>';
		// lets cc in the head just because we can 
		$headers[] = 'Cc: Site Support <support@example.net>';
		// separate the users array
		$users = implode(",", $arrUsers);
		// concatenate a message together
		$message = 'A new post has been opened for your review on the site ' . get_bloginfo('siteurl') . "\r\n\r\n";
		$message .= 'You can review it now at ' . get_permalink($post_ID) . "\r\n\r\n";
		$message .= 'Feel free to leave a comment and any suggestions.' . "\r\n\r\n";
		$message .= 'Praveen Shekhawat.';
		// and finally send the email
		wp_mail($users, "Blog Title: "  . $_POST['post_title'] , $message, $headers );
	    return $post_ID;
    }
}
// hook on to the custom post type by using 'publish_lesson'
add_action('publish_post', 'notify_users');
?>

These hooks will not work with custom post types! So, what about custom post types?

Please use bellow hook for custom post types.

<?php
/* a custom post type called ‘event’ you can now use ‘publish_event’ to hook your function */
add_action('publish_event', 'notify_users');
?>

It’s really is as simple as that.

How to create a new WordPress array ?

So you have a set of data stored in an array and you want to put aside or create a new array with certain data.

There is a powerful function called wp_list_pluck() and wp_list_filter() that can be used for such tasks with any sort of datasets.

For example consider the following array:

$allUsers = array(
    array(
        'id' => 1,
        'user_name' => 'praveen',
        'email' => 'ravan@example.com',
        'type' => 'admin',
        'status' => 'active',
    ),
    array(
        'id' => 2,
        'user_name' => 'dinesh_silwani',
        'email' => 'silwani@example.com',
        'type' => 'guest',
        'status' => 'disabled',
    ),
    array(
        'id' => 3,
        'user_name' => 'ronak',
        'email' => 'ronak@example.com',
        'type' => 'host',
        'status' => 'disabled',
    ),
    array(
        'id' => 4,
        'user_name' => 'ravi',
        'email' => 'ravi@example.com',
        'type' => 'guest',
        'status' => 'disabled',
    ),
    array(
        'id' => 5,
        'user_name' => 'gopal',
        'email' => 'gopal@example.com',
        'type' => 'host',
        'status' => 'active',
    ),
);

First of all we are going to use wp_list_pluck() with 2 parameters, the array to pluck and the key to be plucked. So to create another array that contains just the key for the “user_name” we would do the following:

$allUserName = wp_list_pluck($allUsers, 'user_name'); // New array with all user names.
// would produce the following
// array('praveen', 'dinesh_silwani', 'ronak', 'ravi', 'gopal');

The same could be done to collate the id’s for later loops:

$allIDs = wp_list_pluck($allUsers, 'id');
// would produce the following
// array('1', '2', '3', '4', '5');

Now we are moving to another function. wp_list_filter() is another useful and powerful function that can be used to further refine your new array, say for instance you’d like to create a new array with just guest that are disabled, this is how you can go about it:

$filter_to_use = array('type' => 'guest', 'status' => 'disabled');
$allGuest = wp_list_filter($allUsers, $filter_to_use); // $allUsers = "all disabled guest user."
// this would end up creating an array like so
// array(
//    array(
//        'id' => 2,
//        'user_name' => 'dinesh_silwani',
//        'email' => 'silwani@example.com',
//        'type' => 'guest',
//        'status' => 'disabled',
//    ),
//    array(
//        'id' => 4,
//        'user_name' => 'ravi',
//        'email' => 'ravi@example.com',
//        'type' => 'guest',
//        'status' => 'disabled',
//    )
//);

Both of these functions are very useful when is comes to creating new arrays.

Improve loading, Remove unnecessary scripts and styles in WordPress

Some of the plugins, when installed, add 2 or 3 scripts and stylesheets to every page on website. This isn’t necessarily a problem but it would be nice to have scripts loaded only on pages that actually need them.

Let’s take a example of the most popular Contact Form 7 plugin. Most likely, only pages that contain the

 [contact-form-7] 

shortcode will need the extra scripts and styles.

The following code will check your post content to see if it contains the contact form 7 shortcode. If it doesn’t, it will dequeue the styles and scripts so they will not be loaded.

function pv_dequeue_scripts() {
    
    $load_scripts = false;

    if( is_singular() ) {
    	$post = get_post();

    	if( strstr($post->post_content, '[contact-form-7 ') ) {
        	$load_scripts = true;
    	}

    }

    if( ! $load_scripts ) {
        wp_dequeue_style( 'contact-form-7' );
        wp_dequeue_script( 'contact-form-7' );
    }

}

add_action( 'wp_enqueue_scripts', 'pv_dequeue_scripts');

You can, of course, add more logic to the function to detect the necessity of scripts for other plugins as well. You will need to know the handles used to identify the scripts and styles of the plugin and the shortcode.

Be careful when implementing this though. If you’re rendering a contact form using a widget or template function (for example), the code above won’t detect it and will still dequeue the scripts and styles.

Show Custom Post Types on the Homepage

Custom post types are commonly used in WordPress sites, but they don’t show on the homepage or in the archive pages unless you write code to do that. I’ve put together some code that is smart about detecting your public custom post types and automatically adding them to your homepage and archive pages:

/**
 * Show WordPress custom post types on the main blog and archive pages
 **/
function show_my_post_types( $query ) {

  // Show all custom post types on main blog and archive pages
  if ( $query->is_main_query() && ( is_home() || ( is_archive() && !is_post_type_archive() ) ) ) {

    $custom_post_types = get_post_types( array(
       'public' => true,
       '_builtin' => false,
    ) );

    $post_types = array_merge( array('post'), $custom_post_types );
    $query->set( 'post_type', $post_types );
   }

   return $query;
}

add_filter( 'pre_get_posts', 'show_me_post_types' );

How to track Post Hits by Using WordPress Post Meta without plugin.

This is a small trick, any one can use this trick in wordpress theme.

Just open your wordpress thme function file “function.php”. And put bellow functions into your function file.

//Track your post views without a plugin using 
function getPostViews($postID){
    $meta_key = 'post_views_count';
    $count = get_post_meta($postID, $meta_key, true);
    if($count==''){
        delete_post_meta($postID, $meta_key);
        add_post_meta($postID, $meta_key, '0');
        return "0 View";
    }
    return $count.' Views';
}
function setPostViews($postID) {
    $meta_key = 'post_views_count';
    $count = get_post_meta($postID, $meta_key, true);
    if($count==''){
        $count = 0;
        delete_post_meta($postID, $meta_key);
        add_post_meta($postID, $meta_key, $count);
    }else{
        $count++;
        update_post_meta($postID, $meta_key, $count);
    }
}

The above functions’ will create a custom field called ‘post_views_count’ attached to the ID of a post that will record the data but, if we have no data a then it will create it as zero (0).

To take advantage of the function we need to add the function into wordpress post detail page or custom post type detail page.

setPostViews(get_the_ID());

To show the post hits please put bellow code with post ID, where you want to post hits.

getPostViews(get_the_ID());