Tutorial Details
- Program: WordPress
- Version: 3.2+
- Difficulty: Intermediate to Advanced
- Estimated Completion Time: 60 minutes
- Displaying WordPress Site Data Via jQuery Charts
- 12 Useful Customization and Branding Tweaks for the WordPress Dashboard
- Customizing the WordPress Dashboard For Your Clients
- How to Create Custom WordPress Write/Meta Boxes
- Three Practical Uses for Custom Meta Boxes
- Attaching Files To Your Posts Using WordPress Custom Meta Boxes, Part 1
Last week we introduced how to create custom meta boxes inside the post-editor and save the data you put in them. But what are some practical applications of this technique? Today, the goal is to go over three real world examples of using custom meta boxes to improve the post page.
In the introduction article, you learned all about how to implement meta boxes and save/clean the data the goes into them. That great! But it’s time to go beyond the conceptual information and put those custom meta boxes to work.
Example 1. Adding a Quote to the Top of Posts
The scenario: You run a website that primarily publishes inspirational content. One of the things you do consistently is put quotes at the top of each post. To separate these quotes from the content, you want to move them into a custom meta box.
In the “how to” article, you learned how to actually implement meta boxes, but here’s a quick review.
1. Add the Meta Box
Hook a function into the add_meta_boxes that contains a call to the add_meta_box function.
<?php
add_action( 'add_meta_boxes', 'cd_add_quote_meta' );
function cd_add_quote_meta()
{
add_meta_box( 'quote-meta', __( 'Inspirational Quote' ), 'cd_quote_meta_cb', 'post', 'normal', 'high' );
}
?>
2. Render the Meta Box
The create a function with the same name as the $callback specified in add_meta_box. This is the piece that actually displays meta box content.
<?php
function cd_quote_meta_cb( $post )
{
// Get values for filling in the inputs if we have them.
$quote = get_post_meta( $post->ID, '_cd_quote_content', true );
$author = get_post_meta( $post->ID, '_cd_quote_author', true );
$date = get_post_meta( $post->ID, '_cd_quote_date', true );
// Nonce to verify intention later
wp_nonce_field( 'save_quote_meta', 'quote_nonce' );
?>
<p>
<label for="quote-content">Quote</label>
<textarea class="widefat" id="quote-content" name="_cd_quote_content"><?php echo $quote; ?></textarea>
</p>
<p>
<label for="quote-author">Author</label>
<input type="text" class="widefat" id="quote-author" name="_cd_quote_author" value="" />
</p>
<p>
<label for="quote-date">Author Dates</label>
<input type="text" class="widefat" id="quote-date" name="_cd_quote_date" value="" />
</p>
<?php
}
?>
3. Save the Data
Hook a function into save_post that first handles verifying permissions and intention and then cleans and saves the data.
<?php
add_action( 'save_post', 'cd_quote_meta_save' );
function cd_quote_meta_save( $id )
{
if( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) return;
if( !isset( $_POST['quote_nonce'] ) || !wp_verify_nonce( $_POST['quote_nonce'], 'save_quote_meta' ) ) return;
if( !current_user_can( 'edit_post' ) ) return;
$allowed = array(
'p' => array()
);
if( isset( $_POST['_cd_quote_content'] ) )
update_post_meta( $id, '_cd_quote_content', wp_kses( $_POST['_cd_quote_content'], $allowed ) );
if( isset( $_POST['_cd_quote_author'] ) )
update_post_meta( $id, '_cd_quote_author', esc_attr( strip_tags( $_POST['_cd_quote_author'] ) ) );
if( isset( $_POST['_cd_quote_date'] ) )
update_post_meta( $id, '_cd_quote_date', esc_attr( strip_tags( $_POST['_cd_quote_date'] ) ) );
}
?>

Now the Fun Part: Using the Data
We could use the data saved in our meta boxes by editing our theme’s template files. But that’s too easy. To keep our quote code modular (one plugin file), we’ll use filter hooks, part of the Plugin API. Filter hooks are a bit different from actions. When you hook into a filter, the purpose is, most of the time, to alter how a piece of content appears on a page. In our case, we’re going to hook into the_content, and if we’re on a single post page that has a quote we’ll add it above.
Another way to think of action vs. filter hooks is that you echo things out in actions (eg. wp_head, see section 2), but with filters you take in one or more variables, alter them, then return them.
To display our quote, we’ll hook into the_content, which passes one variable by default: the content of a given post. Inside our hooked function, we’ll make sure we’re on a single post and, if we’re not, return the content right way (no alterations).
<?php
add_filter( 'the_content', 'cd_display_quote' );
function cd_display_quote( $content )
{
// We only want this on single posts, bail if we're not in a single post
if( !is_single() ) return $content;
}
?>
Next up, we’ll get our $post variable. Because we’re in the loop, we just call global $post. Then we’ll get our quote, if no value comes back, we know that no quote was entered and we return the content once again without alteration.
<?php
add_filter( 'the_content', 'cd_display_quote' );
function cd_display_quote( $content )
{
// We only want this on single posts, bail if we're not in a single post
if( !is_single() ) return $content;
// We're in the loop, so we can grab the $post variable
global $post;
$quote = get_post_meta( $post->ID, '_cd_quote_content', true );
// Bail if we don't have a quote;
if( empty( $quote ) ) return $content;
}
?>
Now that we’ve made sure we’re on a single post and we actually have a quote, we an take care of putting things together. First we’ll call our author and her dates via get_post_meta(), then we can start constructing a string in the $out variable. First we’ll add a <blockquote> and our quote. Then we check to see if the author field was filled out. If it was we’ll start a paragraph for the author then check to see if there was a date and add that to the paragraph as well. Finally, we’ll add our closing </blockquote> tag.
<?php
add_filter( 'the_content', 'cd_display_quote' );
function cd_display_quote( $content )
{
// We only want this on single posts, bail if we're not in a single post
if( !is_single() ) return $content;
// We're in the loop, so we can grab the $post variable
global $post;
$quote = get_post_meta( $post->ID, '_cd_quote_content', true );
// Bail if we don't have a quote;
if( empty( $quote ) ) return $content;
// Assemble our quote
$author = get_post_meta( $post->ID, '_cd_quote_author', true );
$date = get_post_meta( $post->ID, '_cd_quote_date', true );
$out = '<blockquote>' . $quote;
if( !empty( $author ) )
{
$out .= '<p class="quote-author">-' . $author;
if( !empty( $date ) )
$out .= ' (' . $date . ')';
$out .= '</p>';
}
$out .= '</blockquote>';
}
?>
Now the most crucial step: returning the combination of our newly made $out string which contains the quote and the original content found in $content.
<?php
add_filter( 'the_content', 'cd_display_quote' );
function cd_display_quote( $content )
{
// We only want this on single posts, bail if we're not in a single post
if( !is_single() ) return $content;
// We're in the loop, so we can grab the $post variable
global $post;
$quote = get_post_meta( $post->ID, '_cd_quote_content', true );
// Bail if we don't have a quote;
if( empty( $quote ) ) return $content;
// Assemble our quote
$author = get_post_meta( $post->ID, '_cd_quote_author', true );
$date = get_post_meta( $post->ID, '_cd_quote_date', true );
$out = '<blockquote>' . $quote;
if( !empty( $author ) )
{
$out .= '<p class="quote-author">-' . $author;
if( !empty( $date ) )
$out .= ' (' . $date . ')';
$out .= '</p>';
}
$out .= '
';
// Return the values: quote first, then the content
return $out . $content;
}
?>
That’s it! You can see the result.

Example 2. Adding Open Graph Meta Tags
The scenario: You have an active community of readers who regularly share your articles on Facebook. This is awesome, and it sends a lot of traffic your way. But you start noticing that the images showing up with your articles on Facebook are less than ideal. You’re also not happy with how your posts titles are coming out. The solution is to add Open Graph meta tags to control how your articles display. Rather than let this get taken care of automatically, you decide to implement a custom meta box to take care of it.
Set up the Meta Box
You probably have this down by now, but here’s the code for getting your meta box going.
<?php
add_action( 'add_meta_boxes', 'cd_add_opengraph_meta' );
function cd_add_opengraph_meta()
{
add_meta_box( 'opengraph-meta', 'Opengraph', 'cd_opengraph_meta_cb', 'post', 'normal', 'high' );
}
function cd_opengraph_meta_cb( $post )
{
// Grab our data to fill out the meta boxes (if it's there)
$title = get_post_meta( $post->ID, '_cd_opengraph_title', true );
$desc = get_post_meta( $post->ID, '_cd_opengraph_desc', true );
$image = get_post_meta( $post->ID, '_cd_opengraph_image', true );
// Add a nonce field
wp_nonce_field( 'save_opengraph_meta', 'opengraph_nonce' );
?>
<p>
<label for="og-title">Title</label>
<input type="text" id="og-title" class="widefat" name="_cd_opengraph_title" value="<?php echo esc_attr( $title ); ?>" />
</p>
<p>
<label for="og-desc">Description</label>
<textarea id="og-desc" class="widefat" name="_cd_opengraph_desc"><?php echo esc_attr( $desc ); ?></textarea>
</p>
<p>
<label for="og-image">Image</label><br />
<input type="text" id="og-image" style="width:300px" name="_cd_opengraph_image" value="<?php echo esc_url( $image ); ?>" />
<input type="button" id="cdog-thickbox" value="Upload Image" /><br/>
<em>Small, square images work best.</em>
</p>
<?php
}
add_action( 'save_post', 'cd_opengraph_save' );
function cd_opengraph_save( $id )
{
// No auto saves
if( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) return;
// Check our nonce
if( !isset( $_POST['opengraph_nonce'] ) || !wp_verify_nonce( $_POST['opengraph_nonce'], 'save_opengraph_meta' ) ) return;
// make sure the current user can edit the post
if( !current_user_can( 'edit_post' ) ) return;
// strip all html tags and esc attributes here
if( isset( $_POST['_cd_opengraph_title'] ) )
update_post_meta( $id, '_cd_opengraph_title', esc_attr( strip_tags( $_POST['_cd_opengraph_title'] ) ) );
// same as above
if( isset( $_POST['_cd_opengraph_desc'] ) )
update_post_meta( $id, '_cd_opengraph_desc', esc_attr( strip_tags( $_POST['_cd_opengraph_desc'] ) ) );
// make sure we get a clean url here with esc_url
if( isset( $_POST['_cd_opengraph_image'] ) )
update_post_meta( $id, '_cd_opengraph_image', esc_url( $_POST['_cd_opengraph_image'], array( 'http' ) ) );
}
?>

Add Some JavaScript
To make that “Upload Image” button work, we’ll have to add a bit of javascript that hijacks the built in WordPress uploader. This means we’re going to use yet another action hook. This time its admin_print_script-{$page}.
When adding scripts and/or styles to the admin area of WordPress, there is one golden rule: only add the scripts/styles where you need them. This prevents your plugin/theme from breaking something else on accident. admin_print_scripts-{$page} lets you only insert scripts (via wp_enqueue_script function) only on the $page specified. In this case, we need to add our script to the post.php and post-new.php screens. This requires hook the same function into both.
<?php
add_action( 'admin_print_scripts-post.php', 'cd_opengraph_enqueue' );
add_action( 'admin_print_scripts-post-new.php', 'cd_opengraph_enqueue' );
function cd_opengraph_enqueue()
{
wp_enqueue_script( 'cdog-thickbox', plugin_dir_url( __FILE__ ) . 'thickbox-hijack.js', array(), NULL );
}
?>
And the javascript.
jQuery(document).ready(function()
{
var ogfield = null;
jQuery( '#cdog-thickbox' ).click(function()
{
ogfield = jQuery( 'input#og-image' ).attr( 'name' );
tb_show( '', 'media-upload.php?type=image&TB_iframe=true' );
return false;
});
window.send_to_editor_old = window.send_to_editor;
window.send_to_editor = function( html )
{
var ogimg;
if( ogfield != null )
{
ogimg = jQuery( 'img', html ).attr( 'src' );
jQuery( 'input#og-image' ).val( ogimg );
tb_remove();
ogfield = null;
}
else
{
window.send_to_editor_old( html );
}
};
});
First we make sure the thickbox uploader pops up when clicking on the button, and we set up a variable that tells WordPress that it was our button that was clicked. Next, we save the window.send_to_editor function with a new name. This is the function that actually inserts the image HTML into the post editing area. We’re going to hijack this function to send on the src attribute to our own form field, but only if the thickbox was brought up by our button.
Add the Open Graph Tags
We’re going to hook into the wp_head action to add our meta tags in the <head> section. First we’ll make sure we’re on a single post page, and then set up our $post variable. $post shouldn’t be empty at this point as WordPress has already decided what sort of object its rendering and what template file it needs to use. But, in case it is, we’ll retrieve post with get_queried_object().
<?php
add_action( 'wp_head', 'cd_opengraph_display' );
function cd_opengraph_display()
{
// If this isn't a single post, bail
if( !is_single() ) return;
global $post, $wp_query;
// if $post is empty, get the queired object
if( empty( $post ) ) $post = $wp_query->get_queried_object();
}
?>
Next up we can go through each Open Graph variable, fetching everything with get_post_custom(), and, if its there, echo it out into the head section of our page.
<?php
add_action( 'wp_head', 'cd_opengraph_display' );
function cd_opengraph_display()
{
// If this isn't a single post, bail
if( !is_single() ) return;
global $post, $wp_query;
// if $post is empty, get the queired object
if( empty( $post ) ) $post = $wp_query->get_queried_object();
$values = get_post_custom( $post->ID );
if( isset( $values['_cd_opengraph_title'] ) )
echo '<meta name="og:title" value="' . esc_attr( $values['_cd_opengraph_title'][0] ) . '" />' ."\n";
if( isset( $values['_cd_opengraph_desc'] ) )
echo '<meta name="og:description" value="' . esc_attr( $values['_cd_opengraph_desc'][0] ) . '" />' . "\n";
if( isset( $values['_cd_opengraph_image'] ) )
echo '<meta name="og:image" value="' . esc_url( $values['_cd_opengraph_image'][0] ) . '" />' . "\n";
}
?>

Example 3. Change Twenty Eleven Layouts on the Fly
The scenario: You rely heavily on Twenty Eleven’s sidebar page template. But you want to be able to switch between left and right sidebars for each page.
The following code would be something better left in a theme’s functions file. That said, because we’re using a plugin here, we can hook into the init and with our function check to make sure Twenty Eleven is the current theme. If it’s not, we’ll deactivate the plugin. First, however, we’ll define a constant containing the URL of the directory in which our plugin resides.
<?php
define( 'CDSB_URL' , plugin_dir_url( __FILE__ ) );
add_action( 'admin_init', 'cd_test_2011' );
function cd_test_2011()
{
if( get_current_theme() != 'Twenty Eleven' ) deactivate_plugins( __FILE__ );
}
?>
Adding the Meta Box
Same routine as before: add the meta box, render it, and save the data. This time, however, we’re going to display our meta box on the edit screen for pages. We’re also going to use a nifty wordpress function called get_template_directory_uri, which returns a string containing the URI of the directory for the current theme. We’re going to use this to borrow a few images that Twenty Eleven uses on its theme options page. We’re also going to use the constant we defined earlier to add an image of our own.
<?php
add_action( 'add_meta_boxes', 'cd_layout_meta' );
function cd_layout_meta()
{
add_meta_box( 'cd-sidebar-pos', 'Page Layout', 'cd_layout_meta_cb', 'page', 'normal', 'high' );
}
function cd_layout_meta_cb( $post )
{
$layout = get_post_meta( $post->ID, '_cd_post_layout', true );
// Set our layout variable, even on new posts
if( empty( $layout ) ) $layout = 'default';
// Theme directory for borrowing 2011 images
$dir = get_template_directory_uri();
wp_nonce_field( 'save_post_layout', 'layout_nonce' );
?>
<fieldset class="clearfix">
<p>Please note: this only works if you've selected "Sidebar Template" in the Page Attributes section</p>
<div class="cd-layout">
<input type="radio" id="sidebar-default" name="_cd_post_layout" value="default" <?php checked( $layout, 'default' ); ?> />
<label for="sidebar-default">
<img src="<?php echo CDSB_URL ?>default.png" alt="Use the Default Sidebar" />
<span>Use theme default</span>
</label>
</div>
<div class="cd-layout">
<input type="radio" id="sidebar-left" name="_cd_post_layout" value="left" <?php checked( $layout, 'left' ); ?> />
<label for="sidebar-left">
<img src="<?php echo $dir; ?>/inc/images/sidebar-content.png" alt="sidebar then content" />
<span>Sidebar on the left</span>
</label>
</div>
<div class="cd-layout">
<input type="radio" id="sidebar-right" name="_cd_post_layout" value="right" <?php checked( $layout, 'right' ); ?> />
<label for="sidebar-right">
<img src="<?php echo $dir; ?>/inc/images/content-sidebar.png" alt="content then sidebar" />
<span>Sidebar on the right</span>
</label>
</div>
</fieldset>
<?php
}
add_action( 'save_post', 'cd_layout_save' );
function cd_layout_save( $id )
{
if( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) return;
if( !isset( $_POST['layout_nonce'] ) || !wp_verify_nonce( $_POST['layout_nonce'], 'save_post_layout' ) ) return;
if( !current_user_can( 'edit_page' ) ) return;
if( isset( $_POST['_cd_post_layout'] ) )
update_post_meta( $id, '_cd_post_layout', esc_attr( strip_tags( $_POST['_cd_post_layout'] ) ) );
}
?>
To prettify our meta box a bit, we’ll need to add our own stylesheet as well. Remember admin_print_scripts-{$page} from the second scenario above? It has a brother, admin_print_styles-{$page}, which, as the name implies, lets you add stylesheet to the wordpress admin on specific pages. We’ll need to hook into this function for post.php and post-new.php. We’ll also be using wp_enqueue_style(); it works the same was as wp_enqueue_script(), which we used in the second example above.
<?php
add_action( 'admin_print_styles-post.php', 'cd_layout_enqueue' );
add_action( 'admin_print_styles-post-new.php', 'cd_layout_enqueue' );
function cd_layout_enqueue()
{
wp_enqueue_style( 'cdlayout-style', CDSB_URL . 'style.css', array(), NULL, 'all' );
}
?>
And the CSS.
div.cd-layout {
width:200px;
float:left;
}
div.cd-layout input {
display:block;
}
#cd-sidebar-pos .clearfix:after {
clear: both;
content: ' ';
display: block;
font-size: 0;
line-height: 0;
visibility: hidden;
width: 0;
height: 0;
}
#cd-sidebar-pos label span {
display:block;
margin-top:5px;
}

Digging into Twenty Eleven
Twenty Eleven accomplishes its sidebar positioning by hooking into a filter called body_class. This is part of the function called <?php body_class(); ?>, which, if you’ve designed a theme before, you’ve probably used. If the default layout is two column, Twenty Eleven adds one of two additional items to body_class: right-sidebar or left-sidebar. You can see the code for this in the theme’s inc folder in the file theme-options.php.
Our own code is also going to hook into body_class. First, we’ll make sure we’re on a page, and that that page is using the Sidebar Template. Then we’ll get the $post variable or set it if its empty. Notice two additional arguments for add_filter. 99 is the priority. We want this to fire last, so we use a higher number. 1 is the number or arguments to send to our function.
<?php
add_filter( 'body_class', 'cd_change_layout', 99, 1 );
function cd_change_layout( $classes )
{
// If this isn't a page, or we're not using the sidebar template, get out of here
if( !is_page() || !is_page_template( 'sidebar-page.php' ) ) return $classes;
// make sure we have the $post object (the current item )
global $post;
if( empty( $post ) ) $post = get_queried_object();
}
?>
body_class will send an array of all the items that will go into the body_class() output function. From here, we just need to get our own meta values. If our value is ‘right’, we’ll look for “left-sidebar” in the body class array. If it’s there, we’ll unset it and replace it with “right-sidebar”. Vice versa if our value is left.
<?php
add_filter( 'body_class', 'cd_change_layout', 99, 1 );
function cd_change_layout( $classes )
{
// If this isn't a page, or we're not using the sidebar template, get out of here
if( !is_page() || !is_page_template( 'sidebar-page.php' ) ) return $classes;
// make sure we have the $post object (eg. the current item )
global $post;
if( empty( $post ) ) $post = get_queried_object();
$layout = get_post_meta( $post->ID, '_cd_post_layout', true );
// if we're using the right layout, add
if( $layout == 'right' )
{
$key = array_search( 'left-sidebar', $classes );
if( $key )
{
unset( $classes[$key] );
$classes[] = 'right-sidebar';
}
}
elseif ( $layout = 'left' )
{
$key = array_search( 'right-sidebar', $classes );
if( $key )
{
unset( $classes[$key] );
$classes[] = 'left-sidebar';
}
}
return $classes;
}
?>
The above would work, but we’ve left out a little detail. If a user happened to have Twenty Eleven’s theme options set to a one column display, none of the options in our meta box would work. So lets modify out add_meta_box call a bit. First we’ll get Twenty Eleven’s options, then we’ll make sure the theme layout option is not set to one column. If the theme is set to one column, we won’t add the meta box.
<?php
add_action( 'add_meta_boxes', 'cd_layout_meta' );
function cd_layout_meta()
{
$opts = get_option( 'twentyeleven_theme_options' );
if( $opts['theme_layout'] != 'content' )
add_meta_box( 'cd-sidebar-pos', 'Page Layout', 'cd_layout_meta_cb', 'page', 'normal', 'high' );
}
?>
Wrap Up
As you might imagine, there are many other uses for custom meta boxes… these are just a few practical examples to get your mind working. When combined with custom post types, they allow you to create extremely customized editing screens. The real strength of custom meta boxes, however, lies in how theme designers and plugin developers can create more user friendly interfaces for post or page level settings.
We hope you enjoyed the tutorial!

One of the best WP tutorials on this site so far! Thank you so much! I’m gonna learn a lot of useful things.
Thanks!
Really liked the quote idea =)
Great post.
Quick question:
For number 1, why not edit single.php instead of writing a custom function?
I think either way can really work if you’re working directly with a theme – you could write a function that checks for the existence of a quote, then inserts it if it’s there. You can also do it this way and programatically add this in using a hook. I personally usually do it the way that you’ve suggested…
The benefits to using the hook/filter method is that you can do this from a plugin, without having any access at all to the theme files… so if a user switches themes (but still has access to the quotes data on each post – presumably because you’ve stored it using a plugin, not a theme), they can keep the functionality with their new theme.
Exactly. I would probably do this in single.php as well, but, for the purpose of this tutorial it seemed logical to keep it in one place (a plugin).
Great article !
Example #2 is exactly the kind of post/page editing improvement I was looking for ! Thanks !
Thanks for this great tutorial. A lot of useful information that you can use in several scenarios. I will try it out soon!
Nice one guys. Is there a way to upload picture via WP uploader in AJAX style? I mean without clicking publish / update button?
Thanks!
Yes, but that’s actually another tut entirely
I’ll see if we can’t find someone to write that one up for you guys!
Actually, it all depends on where/how you want to implement this. For the purpose of showing that it is possible to use the built in WordPress functions I wrote a tutorial which shows how easy it is to do.
All that is required is including jquery to call the php processing.
While it doesn’t directly answer your question it does show you that you can use the WordPress media functions to upload whatever you want from wherever you want.
Latest liked and amazing the quote idea =) thanks for the share.
Awesome!
Uploading an image w/ custom meta boxes is VERY helpful.
This is a great tutorial. Thank you. And I just want to know which of the following methods is the best to use (about hooks) – what are advantages and disadvantages of both methods, which method is the best practice to use:
Method 1:
Method 2:
add_meta_box( ‘my-meta-box-id’, ‘My First Meta Box’, ‘cd_meta_box_cb’, ‘post’, ‘normal’, ‘high’ );
Ref: Method 1: Ref: http://wp.tutsplus.com/tutorials/plugins/how-to-create-custom-wordpress-writemeta-boxes/
Method 2 is used at: http://wp.tutsplus.com/tutorials/plugins/reel-em-in-understanding-hooks-from-the-inside-out/
This is a great tutorial. Thank you. And I just want to know which of the
following methods is the best to use (about hooks) – what are advantages and
disadvantages of both methods, which method is the best practice to use:
Method 1:
<?php add_action( ‘add_meta_boxes’, ‘cd_meta_box_add’ );
function cd_meta_box_add()
{
add_meta_box( ‘my-meta-box-id’, ‘My First Meta Box’, ‘cd_meta_box_cb’, ‘post’,
‘normal’, ‘high’ );
}
?>
Ref: http://wp.tutsplus.com/tutorials/plugins/how-to-create-custom-wordpress-writemeta-boxes/
Method 2:
<?php function cd_meta_box_add() { ?>
add_meta_box( ‘my-meta-box-id’, ‘My First Meta Box’, ‘cd_meta_box_cb’, ‘post’,
‘normal’, ‘high’ );
<?php
}
add_action( ‘add_meta_boxes’, ‘cd_meta_box_add’ );
?>
Method 2 is used at: http://wp.tutsplus.com/tutorials/plugins/reel-em-in-understanding-hooks-from-the-inside-out/
Awesome stuff and very useful. Adding additional meta data is really handy especially for, as demonstrated, Facebook open graph stuff. Another handy application is for verification on Google Apps and Yahoo! site submission etc.
I’ve done the second example before but to add more than 1 image uploader button I had to change the JS a little:
jQuery(document).ready(function() {
var formfield;
var $image_input;
jQuery(‘.upload_image_button’).click(function() {
jQuery(‘html’).addClass(‘upload_image’);
var $cont = jQuery(this).parent(); // Be sure that the button and the text are within a container like a Paragraph
$image_input = jQuery(‘input[type=text]‘, $cont);
formfield = $image_input.attr(‘name’);
tb_show(”, ‘media-upload.php?type=image&TB_iframe=true’);
tbframe_interval = setInterval(function() {jQuery(‘#TB_iframeContent’).contents().find(‘.savesend .button’).val(‘Use this image’);}, 2000); // Usefull to change the button label from the thickbox uploader
return false;
});
window.original_send_to_editor = window.send_to_editor;
window.send_to_editor = function(html){
clearInterval(tbframe_interval);
if (formfield) {
fileurl = jQuery(‘img’,html).attr(‘src’);
$image_input.val(fileurl);
tb_remove();
formfield = null;
jQuery(‘html’).removeClass(‘upload_image’);
} else {
window.original_send_to_editor(html);
}
};
});
Loved the tutorial!
@Gustavo Where exactly do you add the JS ? Do you create a specific js file or do you add it elsewhere ?
This is such a wonderful tutorial! Thank you so much.
One question: In example #1, what happens when you add a value to the “Quote” field and the “Author” field, but not the “Date” field.
To be more specific, I am hoping to implement these meta boxes on a client’s site to make it easier for them to input specific information that needs to be formatted a certain way without having them have to deal with the html editor. One of these custom meta boxes, within the “Archived Projects” posts, with be “Technical Data” with several fields including “Length,” “Sound,” “Original Master Format,” etc. I would like all of the fields visible on all “Archived Projects” edit pages. However, some of the projects do not have all of the information to fill in all of the fields. All I am curious about is: If a few fields are left blank in some posts and not in others, what issues will this cause?
I would try this out myself, but I figured I would ask first to see if this is the right solution for this site.
Thanks much!
nice piece of code, it really helped me a lot…
i wanna ask one thing about page layout.. didnt try it, but i know that just add class to body, left and right and just float is changed… but what about full width? does add display:none on sidebar or what?
Great tutorial, but I was wondering if there is a way to post the Inspirational Quote in the sidebar instead of the body of a post? I just want the quote, I don’t want ‘$content’ to show since that will appear in the body. Regardless, thank you so much Christopher for your hard work and to the help from everyone in the comments section. Thank you in advance!
acheter propecia moins che k5 finasteride acheter RW propecia pas cher marseille is propecia generique prix ES propecia sur internet fN propecia finasteride avis UF prix propecia paris vs propecia prix suisse 5QY finasteride paris yp propecia pas cher lyon vs acheter propecia k5 propecia prix pharmacie Yo achat propecia france 5QY propecia generique is propecia moins cher lyon yp propecia pas cher marseille Z9 propecia generique prix Nd prix propecia toulouse Z9 propecia moins cher calvitie