Ask your WordPress questions! Pay money and get answers fast! Comodo Trusted Site Seal
Official PayPal Seal

Finish custom post type WordPress

  • SOLVED

I've been writing a custom post type based on several tutorials I've seen. Problem is that all the tutorials seem to be different. Another thing I've found is that the couple of tutorials I've read that show a custom field or option only show "one" custom field or option so it is unclear how to save or update multiple fields. This post type has multiple custom fields that will be in a "side" meta box.

What I need finished is this.

1. Please correct any errors I have made.

2. Add the save/update/delete function (to include the options)

3. This post uses a different single template called tevideo.php. Please add the redirect.

Here is my code This displays correctly but does not save or update the custom fields.

add_action('init', 'te_video');
function te_video() {
$labels = array(
'name' => _x('Videos', 'post type general name'),
'singular_name' => _x('Video', 'post type singular name'),
'add_new' => _x('Add New', 'Video'),
'add_new_item' => __('Add New Video'),
'edit_item' => __('Edit Video'),
'new_item' => __('New video'),
'all_items' => __('All Videos'),
'view_items' => __('View Videos'),
'search_items' => ('Search Videos'),
'not_found' => __('No Videos Found'),
'not_found_in_trash' => __('No Videos Found in Trash'),
'menu_name' => 'videos'
);
$args = array(
'labels' => $labels,
'public' => true,
'publicly_queryable' => true,
'show_ui' => true,
'show_in_menu' => true,
'menu_position' => 5,
'rewrite' => true,
'capability_type' => 'post',
'hierarchical' => false,
'has_archive' => true,
'query_var' => true,
'supports' => array('title', 'editor', 'thumbnail')
);

register_post_type('video',$args);
}

function video_options(){
global $post;
$custom = get_post_custom($post->ID);
$audio_available = $custom["audio_available"][0];
$film_available = $custom["film_available"][0];
$hd_available = $custom["hd_available"][0];
$camera_action = $custom["camera_action"][0];
$camera_location = $custom["camera_location"][0];
$camera_shot = $custom["camera_shot"][0];
$camera_speed = $custom["camera_speed"][0];
$location = $custom["location"][0];
$Time = $custom["time"][0];
$aspect = $custom["aspect"][0];
$rights = $custom["rights"][0];
$vidcategories = $custom["vidcategories"][0];
$color = $custom["color"][0];

}

add_action("admin_init", "add_video");
add_action('save_post', 'update_video');

function add_video(){
add_meta_box(
'tevideo_details',
'Video Options',
'te_video_options',
'video',
'side',
'high'
);
}
function update_video(){
global $post;
update_post_meta($post->ID, "video_options", $_POST["video"]);
}


This is the first time I've done this and is a learning process. So your assistance is greatly appreciated.

Answers (1)

2011-10-08

Luis Abarca answers:

OK, im working on that !


Luis Abarca comments:


<?php
/**
Plugin Name: Test ├Člot
*/

register_activation_hook(__FILE__, 'te_video_activate');

// call flush rewrite just on plugin activation
function te_video_activate()
{
te_video();
flush_rewrite_rules();
}

register_deactivation_hook(__FILE__, 'te_video_deactivate');

function te_video_deactivate()
{
flush_rewrite_rules();
}

add_action('init', 'te_video');

function te_video ()
{
$labels = array(
'name' => _x('Videos', 'post type general name'),
'singular_name' => _x('Video', 'post type singular name'),
'add_new' => _x('Add New', 'Video'), 'add_new_item' => __('Add New Video'),
'edit_item' => __('Edit Video'), 'new_item' => __('New video'),
'all_items' => __('All Videos'), 'view_items' => __('View Videos'),
'search_items' => ('Search Videos'), 'not_found' => __('No Videos Found'),
'not_found_in_trash' => __('No Videos Found in Trash'),
'menu_name' => 'videos'
);

$args = array(
'labels' => $labels,
'public' => true,
'publicly_queryable' => true,
'show_ui' => true,
'show_in_menu' => true,
'menu_position' => 5,
'rewrite' => true,
'capability_type' => 'post',
'hierarchical' => false,
'has_archive' => true,
'query_var' => true,
'supports' => array('title', 'editor', 'thumbnail')
);

register_post_type('video', $args);
}

function video_options ()
{
global $post;

$custom = get_post_custom($post->ID);

$audio_available = $custom["audio_available"][0];
$film_available = $custom["film_available"][0];
$hd_available = $custom["hd_available"][0];
$camera_action = $custom["camera_action"][0];
$camera_location = $custom["camera_location"][0];
$camera_shot = $custom["camera_shot"][0];
$camera_speed = $custom["camera_speed"][0];
$location = $custom["location"][0];
$Time = $custom["time"][0];
$aspect = $custom["aspect"][0];
$rights = $custom["rights"][0];
$vidcategories = $custom["vidcategories"][0];
$color = $custom["color"][0];


wp_nonce_field('video_save', 'video_nonce');
?>

<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="jab_realty_address">Audio Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="audio_available" id="audio_available" value="<?php echo esc_attr($audio_available) ?>" />
</td>
</tr>
</table>
</div>
</div>

<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="jab_realty_address">Film Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="film_available" id="film_available" value="<?php echo esc_attr($film_available) ?>" />
</td>
</tr>
</table>
</div>
</div>

<?php
}

add_action("add_meta_boxes", "add_video");

function add_video ()
{
add_meta_box('tevideo_details', 'Video Options', 'te_video_options', 'video', 'side', 'high');
}

add_action('save_post', 'update_video');

// this works for add and update
function update_video ()
{
global $post;

if ( !isset($_POST['video_nonce']) ) {
return $post_id;
}

if ( !wp_verify_nonce( $_POST['video_nonce'], 'video_save' ) ) {
return $post_id;
}

if ( defined('DOING_AUTOSAVE') && DOING_AUTOSAVE ) {
return $post_id;
}

// you can save one at the time
update_post_meta($post->ID, "video_options", $_POST["audio_available"]);
update_post_meta($post->ID, "film_available", $_POST["film_available"]);

// or you can save all options serialized in an array
$data['audio_available'] = $_POST["audio_available"];
$data['film_available'] = $_POST["film_available"];

update_post_meta($post->ID, "video_options", serialize($data));

}


Luis Abarca comments:

I show you 2 styles of save post meta, one item at the time, or serializing all data and store in just one post meta field.


<?php
/**
Plugin Name: Test ├Člot
*/

register_activation_hook(__FILE__, 'te_video_activate');

// call flush rewrite just on plugin activation
function te_video_activate()
{
te_video();
flush_rewrite_rules();
}

register_deactivation_hook(__FILE__, 'te_video_deactivate');

function te_video_deactivate()
{
flush_rewrite_rules();
}

add_action('init', 'te_video');

function te_video()
{
$labels = array(
'name' => _x('Videos', 'post type general name'),
'singular_name' => _x('Video', 'post type singular name'),
'add_new' => _x('Add New', 'Video'), 'add_new_item' => __('Add New Video'),
'edit_item' => __('Edit Video'), 'new_item' => __('New video'),
'all_items' => __('All Videos'), 'view_items' => __('View Videos'),
'search_items' => ('Search Videos'), 'not_found' => __('No Videos Found'),
'not_found_in_trash' => __('No Videos Found in Trash'),
'menu_name' => 'videos'
);

$args = array(
'labels' => $labels,
'public' => true,
'publicly_queryable' => true,
'show_ui' => true,
'show_in_menu' => true,
'menu_position' => 5,
'rewrite' => true,
'capability_type' => 'post',
'hierarchical' => false,
'has_archive' => true,
'query_var' => true,
'supports' => array('title', 'editor', 'thumbnail', 'custom-fields')
);

register_post_type('video', $args);
}

function te_video_options()
{
global $post;

$custom = get_post_custom($post->ID);

// Saving one post meta at the time
$audio_available = $custom["audio_available"][0];
$film_available = $custom["film_available"][0];
$hd_available = $custom["hd_available"][0];
$camera_action = $custom["camera_action"][0];
$camera_location = $custom["camera_location"][0];
$camera_shot = $custom["camera_shot"][0];
$camera_speed = $custom["camera_speed"][0];
$location = $custom["location"][0];
$Time = $custom["time"][0];
$aspect = $custom["aspect"][0];
$rights = $custom["rights"][0];
$vidcategories = $custom["vidcategories"][0];
$color = $custom["color"][0];

// or using serialized data in an array
$data = unserialize(get_post_meta($post->ID, 'video_options', true));
$audio_available = $data['audio_available'];


wp_nonce_field('video_save', 'video_nonce');
?>

<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="audio_available">Audio Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="audio_available" id="audio_available" value="<?php echo esc_attr($audio_available) ?>" />
</td>
</tr>
</table>
</div>
</div>

<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="film_available">Film Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="film_available" id="film_available" value="<?php echo esc_attr($film_available) ?>" />
</td>
</tr>
</table>
</div>
</div>

<?php
}

add_action("add_meta_boxes", "add_video");

function add_video ()
{
add_meta_box('tevideo_details', 'Video Options', 'te_video_options', 'video', 'side', 'high');
}

add_action('save_post', 'update_video');

// this works for add and update
function update_video ()
{
global $post;

if ( !isset($_POST['video_nonce']) ) {
return $post_id;
}

if ( !wp_verify_nonce( $_POST['video_nonce'], 'video_save' ) ) {
return $post_id;
}

if ( defined('DOING_AUTOSAVE') && DOING_AUTOSAVE ) {
return $post_id;
}

// you can save one at the time
update_post_meta($post->ID, "audio_available", $_POST["audio_available"]);
update_post_meta($post->ID, "film_available", $_POST["film_available"]);

// or you can save all options serialized in an array, under the video_options meta
$data['audio_available'] = $_POST["audio_available"];
$data['film_available'] = $_POST["film_available"];

update_post_meta($post->ID, "video_options", serialize($data));

}


Luis Abarca comments:

umm, i add 'custom-fields' to your register post type function for debugging, you can delete it :D


Luis Abarca comments:

I almost forget the template redirect:


<?php
/**
Plugin Name: Test pilot
*/

add_action("template_redirect", 'te_video_redirect');

// Template selection
function te_video_redirect()
{
global $wp;
global $wp_query;
if ($wp->query_vars["post_type"] == "video")
{
if (have_posts())
{
include(TEMPLATEPATH . '/tevideo.php');
die();
}
else
{
$wp_query->is_404 = true;
}
}
}

register_activation_hook(__FILE__, 'te_video_activate');

// call flush rewrite just on plugin activation
function te_video_activate()
{
te_video();
flush_rewrite_rules();
}

register_deactivation_hook(__FILE__, 'te_video_deactivate');

function te_video_deactivate()
{
flush_rewrite_rules();
}

add_action('init', 'te_video');

function te_video()
{
$labels = array(
'name' => _x('Videos', 'post type general name'),
'singular_name' => _x('Video', 'post type singular name'),
'add_new' => _x('Add New', 'Video'), 'add_new_item' => __('Add New Video'),
'edit_item' => __('Edit Video'), 'new_item' => __('New video'),
'all_items' => __('All Videos'), 'view_items' => __('View Videos'),
'search_items' => ('Search Videos'), 'not_found' => __('No Videos Found'),
'not_found_in_trash' => __('No Videos Found in Trash'),
'menu_name' => 'videos'
);

$args = array(
'labels' => $labels,
'public' => true,
'publicly_queryable' => true,
'show_ui' => true,
'show_in_menu' => true,
'menu_position' => 5,
'rewrite' => true,
'capability_type' => 'post',
'hierarchical' => false,
'has_archive' => true,
'query_var' => true,
'supports' => array('title', 'editor', 'thumbnail')
);

register_post_type('video', $args);
}

function te_video_options()
{
global $post;

$custom = get_post_custom($post->ID);

// Saving one post meta at the time
$audio_available = $custom["audio_available"][0];
$film_available = $custom["film_available"][0];
$hd_available = $custom["hd_available"][0];
$camera_action = $custom["camera_action"][0];
$camera_location = $custom["camera_location"][0];
$camera_shot = $custom["camera_shot"][0];
$camera_speed = $custom["camera_speed"][0];
$location = $custom["location"][0];
$Time = $custom["time"][0];
$aspect = $custom["aspect"][0];
$rights = $custom["rights"][0];
$vidcategories = $custom["vidcategories"][0];
$color = $custom["color"][0];

// or using serialized data in an array
$data = unserialize(get_post_meta($post->ID, 'video_options', true));
$audio_available = $data['audio_available'];


wp_nonce_field('video_save', 'video_nonce');
?>

<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="audio_available">Audio Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="audio_available" id="audio_available" value="<?php echo esc_attr($audio_available) ?>" />
</td>
</tr>
</table>
</div>
</div>

<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="film_available">Film Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="film_available" id="film_available" value="<?php echo esc_attr($film_available) ?>" />
</td>
</tr>
</table>
</div>
</div>

<?php
}

add_action("add_meta_boxes", "add_video");

function add_video ()
{
add_meta_box('tevideo_details', 'Video Options', 'te_video_options', 'video', 'side', 'high');
}

add_action('save_post', 'update_video');

// this works for add and update
function update_video ()
{
global $post;

if ( !isset($_POST['video_nonce']) ) {
return $post_id;
}

if ( !wp_verify_nonce( $_POST['video_nonce'], 'video_save' ) ) {
return $post_id;
}

if ( defined('DOING_AUTOSAVE') && DOING_AUTOSAVE ) {
return $post_id;
}

// you can save one at the time
update_post_meta($post->ID, "audio_available", $_POST["audio_available"]);
update_post_meta($post->ID, "film_available", $_POST["film_available"]);

// or you can save all options serialized in an array, under the video_options meta
$data['audio_available'] = $_POST["audio_available"];
$data['film_available'] = $_POST["film_available"];

update_post_meta($post->ID, "video_options", serialize($data));

}


Luis Abarca comments:

Sorry, the last code has a bug on arhive, so use this one. http://pastebin.com/RVtqeHkf


<?php
/**
Plugin Name: Test pilot
*/


function is_te_video()
{
$post_type = get_query_var('post_type');
return $post_type == 'video' ? true : false;
}

function get_te_video_template()
{
global $wp_query;

$object = $wp_query->get_queried_object();

$templates = array( 'tevideo-'. $object->ID .'.php',
'tevideo.php',
'single-'. $object->post_type .'.php',
'single.php' );

$page_template = get_post_meta( $object->ID , '_wp_page_template', true );

if ( !empty( $page_template ) ) {
$templates = array( $page_template ) + $templates;
}

return locate_template( $templates );
}

function set_te_video_template( $template )
{
if ( is_te_video() ) {
$template = get_te_video_template();
}

return $template;
}

add_filter('template_include', 'set_te_video_template');



register_activation_hook(__FILE__, 'te_video_activate');

// call flush rewrite just on plugin activation
function te_video_activate()
{
te_video();
flush_rewrite_rules();
}

register_deactivation_hook(__FILE__, 'te_video_deactivate');

function te_video_deactivate()
{
flush_rewrite_rules();
}

add_action('init', 'te_video');

function te_video()
{
$labels = array(
'name' => _x('Videos', 'post type general name'),
'singular_name' => _x('Video', 'post type singular name'),
'add_new' => _x('Add New', 'Video'), 'add_new_item' => __('Add New Video'),
'edit_item' => __('Edit Video'), 'new_item' => __('New video'),
'all_items' => __('All Videos'), 'view_items' => __('View Videos'),
'search_items' => ('Search Videos'), 'not_found' => __('No Videos Found'),
'not_found_in_trash' => __('No Videos Found in Trash'),
'menu_name' => 'videos'
);

$args = array(
'labels' => $labels,
'public' => true,
'publicly_queryable' => true,
'show_ui' => true,
'show_in_menu' => true,
'menu_position' => 5,
'rewrite' => true,
'capability_type' => 'post',
'hierarchical' => false,
'has_archive' => true,
'query_var' => true,
'supports' => array('title', 'editor', 'thumbnail')
);

register_post_type('video', $args);
}

function te_video_options()
{
global $post;

$custom = get_post_custom($post->ID);

// Saving one post meta at the time
$audio_available = $custom["audio_available"][0];
$film_available = $custom["film_available"][0];
$hd_available = $custom["hd_available"][0];
$camera_action = $custom["camera_action"][0];
$camera_location = $custom["camera_location"][0];
$camera_shot = $custom["camera_shot"][0];
$camera_speed = $custom["camera_speed"][0];
$location = $custom["location"][0];
$Time = $custom["time"][0];
$aspect = $custom["aspect"][0];
$rights = $custom["rights"][0];
$vidcategories = $custom["vidcategories"][0];
$color = $custom["color"][0];

// or using serialized data in an array
$data = unserialize(get_post_meta($post->ID, 'video_options', true));
$audio_available = $data['audio_available'];


wp_nonce_field('video_save', 'video_nonce');
?>

<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="audio_available">Audio Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="audio_available" id="audio_available" value="<?php echo esc_attr($audio_available) ?>" />
</td>
</tr>
</table>
</div>
</div>

<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="film_available">Film Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="film_available" id="film_available" value="<?php echo esc_attr($film_available) ?>" />
</td>
</tr>
</table>
</div>
</div>

<?php
}

add_action("add_meta_boxes", "add_video");

function add_video ()
{
add_meta_box('tevideo_details', 'Video Options', 'te_video_options', 'video', 'side', 'high');
}

add_action('save_post', 'update_video');

// this works for add and update
function update_video ()
{
global $post;

if ( !isset($_POST['video_nonce']) ) {
return $post_id;
}

if ( !wp_verify_nonce( $_POST['video_nonce'], 'video_save' ) ) {
return $post_id;
}

if ( defined('DOING_AUTOSAVE') && DOING_AUTOSAVE ) {
return $post_id;
}

// you can save one at the time
update_post_meta($post->ID, "audio_available", $_POST["audio_available"]);
update_post_meta($post->ID, "film_available", $_POST["film_available"]);

// or you can save all options serialized in an array, under the video_options meta
$data['audio_available'] = $_POST["audio_available"];
$data['film_available'] = $_POST["film_available"];

update_post_meta($post->ID, "video_options", serialize($data));

}


Connie Taylor comments:

Good morning and thank you for your hard work. I have a few questions on your code.
First: Is this necessary?, can I rename it?
<?php
/**
Plugin Name: Test pilot
*/

For this section you only show two fields - do I plug in my whole form?
<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="audio_available">Audio Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="audio_available" id="audio_available" value="<?php echo esc_attr($audio_available) ?>" />
</td>
</tr>
</table>
</div>
</div>

<div class="jaxtag" style="border-bottom: 1px solid #DFDFDF; padding: 5px 0">
<div class="ajaxtag hide-if-no-js">
<table style="width: 100%">
<tr>
<td width="25%">
<label for="film_available">Film Available:</label>
<label class="screen-reader-text" for="jab_realty_address">Item description:</label>
</td>
<td width="75%">
<input style="width: 100%" width="60" type="text" name="film_available" id="film_available" value="<?php echo esc_attr($film_available) ?>" />
</td>
</tr>
</table>
</div>
</div>


And on this section, if I want them saved separately? Do I fill in the rest and delete the serialized part?
// you can save one at the time
update_post_meta($post->ID, "audio_available", $_POST["audio_available"]);
update_post_meta($post->ID, "film_available", $_POST["film_available"]);

// or you can save all options serialized in an array, under the video_options meta
$data['audio_available'] = $_POST["audio_available"];
$data['film_available'] = $_POST["film_available"];

update_post_meta($post->ID, "video_options", serialize($data));


Let me know and I will finish it up and plug it into my test install.


Connie Taylor comments:

Got it and it's all working. Thank you.