Take the 2-minute tour ×
WordPress Development Stack Exchange is a question and answer site for WordPress developers and administrators. It's 100% free, no registration required.

I'm learning about meta boxes and have gotten them to appear on my local dev, but I can't figure out how to avoid creating new functions for saving multiple meta boxes.

I assume that I could call an array and reuse the same functions for generating the meta box content and saving it, but I keep getting errors when trying so. Here is the code I have now in my functions file:

    /**
     * Home Page Custom Meta Content
     *
    **/

    // Add the Meta Box  
    function add_home_meta_box() {  
        add_meta_box(  
            'home_meta_box', // $id  
            'Home Page Content', // $title   
            'show_home_meta_box', // $callback  
            'page', // $page  
            'normal', // $context  
            'high'); // $priority
        add_meta_box(  
            'home_meta_box_lower_1', // $id  
            'Home Lower Left', // $title   
            'show_home_meta_box_lower_left', // $callback  
            'page', // $page  
            'normal', // $context  
            'high'); // $priority    
    }
    add_action('add_meta_boxes', 'add_home_meta_box');  


    // Creating Array for Fields
    $prefix = 'home_';
    $home_meta_fields = array(
        array(
            'label' => 'Caption Title',
            'desc' => 'Upper section H2 caption title.',
            'id' => $prefix.'title',
            'type' => 'text'
        ),
        array(
            'label' => 'Caption Sub Title',
            'desc' => 'Upper section H3 caption title.',
            'id' => $prefix.'sub_title',
            'type' => 'text'
        ),
      array(  
          'label'=> 'Caption',  
          'desc'  => 'Caption text block.',  
          'id'    => $prefix.'caption',  
          'type'  => 'textarea'  
      ),
        array(  
            'name'  => 'Caption Image',  
            'desc'  => 'Upload a pre-cropped 1140px wide x 530px tall web-optimized image.',  
            'id'    => $prefix.'image',  
            'type'  => 'image'  
        )
    );// end caption array

    $prefix2 = 'home_lower_left';
    $home_meta_fields_lower_left = array(
        array(
            'label' => 'Column Title',
            'desc' => 'H2 title for column.',
            'id' => $prefix2.'title',
            'type' => 'text'
        ),
        array(  
            'name'  => 'Column Image',  
            'desc'  => 'Upload a pre-cropped 360px wide x 300px tall web-optimized image.',  
            'id'    => $prefix2.'image',  
            'type'  => 'image'  
        ),
        array(
            'label' => 'Column Sub-Title',
            'desc' => 'H3 sub-title above text block.',
            'id' => $prefix2.'sub_title',
            'type' => 'text'
        ),
      array(  
          'label'=> 'Text block',  
          'desc'  => 'Caption text block.',  
          'id'    => $prefix2.'caption',  
          'type'  => 'textarea'  
      ),
        array(
            'label' => 'Button Label',
            'desc' => 'Button link label (what user reads on button).',
            'id' => $prefix2.'btn_label',
            'type' => 'text'
        ),
        array(
            'label' => 'Button URL',
            'desc' => 'URL where button links to. Enter http:// to work.',
            'id' => $prefix2.'btn_url',
            'type' => 'text'
        )
    );// end lower left array


    //The Callback
    function show_home_meta_box() {
    global $home_meta_fields, $post;
    // Using nonce for verification
    echo '<input type="hidden" name="home_meta_box_nonce" value="'.wp_create_nonce(basename(__FILE__)).'" />';

        //Begin field table and loop
        echo '<table class="form-table">';
        foreach ($home_meta_fields as $field) {
            // get value of this field if it exists for this page
            $meta = get_post_meta($post->ID, $field['id'], true);
            // begin a table row with
            echo '<tr>
                            <th><label for="'.$field['id'].'">'.$field['label'].'</label></th>
                            <td>';
                            switch($field['type']) {
                                // case items will go here
                                // text  
                                case 'text':  
                                    echo '<input type="text" name="'.$field['id'].'" id="'.$field['id'].'" value="'.$meta.'" size="30" /> 
                                        <br /><span class="description">'.$field['desc'].'</span>';  
                                break;
                                // textarea  
                                case 'textarea':  
                                    echo '<textarea name="'.$field['id'].'" id="'.$field['id'].'" cols="60" rows="4">'.$meta.'</textarea> 
                                        <br /><span class="description">'.$field['desc'].'</span>';  
                                break;
                                case 'image':  
                                    $image = get_template_directory_uri().'library/images/img-preview-blank.png';    
                                    echo '<span class="custom_default_image" style="display:none">'.$image.'</span>';  
                                    if ($meta) { $image = wp_get_attachment_image_src($meta, 'medium'); $image = $image[0]; }                 
                                    echo    '<input name="'.$field['id'].'" type="hidden" class="custom_upload_image" value="'.$meta.'" /> 
                                                <img src="'.$image.'" class="custom_preview_image" style="max-width:300px" alt="" /><br /> 
                                                    <input class="custom_upload_image_button button" type="button" value="Choose Image" /> 
                                                    <small> <a href="#" class="custom_clear_image_button">Remove Image</a></small> 
                                                    <br clear="all" /><span class="description">'.$field['desc'].'';  
                                break;  
                            } // end switch
            echo '</td></tr>';
        } // end foreach
        echo '</table>'; // end table
    }

    // Save the Data
    function save_home_meta($post_id) {  
        global $home_meta_fields;  

        // verify nonce  
        if (!wp_verify_nonce($_POST['home_meta_box_nonce'], basename(__FILE__)))   
            return $post_id;  
        // check autosave  
        if (defined('DOING_AUTOSAVE') && DOING_AUTOSAVE)  
            return $post_id;  
        // check permissions  
        if ('page' == $_POST['post_type']) {  
            if (!current_user_can('edit_page', $post_id))  
                return $post_id;  
            } elseif (!current_user_can('edit_post', $post_id)) {  
                return $post_id;  
        }  

        // loop through fields and save the data  
        foreach ($home_meta_fields as $field) {  
            $old = get_post_meta($post_id, $field['id'], true);  
            $new = $_POST[$field['id']];  
            if ($new && $new != $old) {  
                update_post_meta($post_id, $field['id'], $new);  
            } elseif ('' == $new && $old) {  
                delete_post_meta($post_id, $field['id'], $old);  
            }  
        } // end foreach  
    }  
    add_action('save_post', 'save_home_meta');
    // Lower Left
    //The Callback
    function show_home_meta_box_lower_left() {
    global $home_meta_fields_lower_left, $post;
    // Using nonce for verification
    echo '<input type="hidden" name="home_meta_box_left_nonce" value="'.wp_create_nonce(basename(__FILE__)).'" />';

        //Begin field table and loop
        echo '<table class="form-table">';
        foreach ($home_meta_fields_lower_left as $field) {
            // get value of this field if it exists for this page
            $meta = get_post_meta($post->ID, $field['id'], true);
            // begin a table row with
            echo '<tr>
                            <th><label for="'.$field['id'].'">'.$field['label'].'</label></th>
                            <td>';
                            switch($field['type']) {
                                // case items will go here
                                // text  
                                case 'text':  
                                    echo '<input type="text" name="'.$field['id'].'" id="'.$field['id'].'" value="'.$meta.'" size="30" /> 
                                        <br /><span class="description">'.$field['desc'].'</span>';  
                                break;
                                // textarea  
                                case 'textarea':  
                                    echo '<textarea name="'.$field['id'].'" id="'.$field['id'].'" cols="60" rows="4">'.$meta.'</textarea> 
                                        <br /><span class="description">'.$field['desc'].'</span>';  
                                break;
                                case 'image':  
                                    $image = get_template_directory_uri().'library/images/img-preview-blank.png';    
                                    echo '<span class="custom_default_image" style="display:none">'.$image.'</span>';  
                                    if ($meta) { $image = wp_get_attachment_image_src($meta, 'medium'); $image = $image[0]; }                 
                                    echo    '<input name="'.$field['id'].'" type="hidden" class="custom_upload_image" value="'.$meta.'" /> 
                                                <img src="'.$image.'" class="custom_preview_image" style="max-width:300px" alt="" /><br /> 
                                                    <input class="custom_upload_image_button button" type="button" value="Choose Image" /> 
                                                    <small> <a href="#" class="custom_clear_image_button">Remove Image</a></small> 
                                                    <br clear="all" /><span class="description">'.$field['desc'].'';  
                                break;  
                            } // end switch
            echo '</td></tr>';
        } // end foreach
        echo '</table>'; // end table
    }

    // Save the Data
    function save_home_meta_lower_left($post_id) {  
        global $home_meta_fields_lower_left;  

        // verify nonce  
        if (!wp_verify_nonce($_POST['home_meta_box_left_nonce'], basename(__FILE__)))   
            return $post_id;  
        // check autosave  
        if (defined('DOING_AUTOSAVE') && DOING_AUTOSAVE)  
            return $post_id;  
        // check permissions  
        if ('page' == $_POST['post_type']) {  
            if (!current_user_can('edit_page', $post_id))  
                return $post_id;  
            } elseif (!current_user_can('edit_post', $post_id)) {  
                return $post_id;  
        }  

        // loop through fields and save the data  
        foreach ($home_meta_fields_lower_left as $field) {  
            $old = get_post_meta($post_id, $field['id'], true);  
            $new = $_POST[$field['id']];  
            if ($new && $new != $old) {  
                update_post_meta($post_id, $field['id'], $new);  
            } elseif ('' == $new && $old) {  
                delete_post_meta($post_id, $field['id'], $old);  
            }  
        } // end foreach  
    }  
    add_action('save_post', 'save_home_meta_lower_left');

Thanks for helping me out! Much appreciated.

share|improve this question
    
What errors are you getting? Edit your question to include the complete text of the messages. –  s_ha_dum Feb 16 '13 at 0:22
    
Hey @s_ha_dum, I get a 500 error trying to wrap the [pre]$home_meta_fields[/pre] and [pre]$home_meta_fields_lower_left[/pre] arrays together. –  Rick Pickett Feb 16 '13 at 2:03
    
Trying to wrap the arrays together? What does that mean? –  s_ha_dum Feb 16 '13 at 4:27
    
Meta Box plugin's demo.php has a good example of bundling arrays for multiple meta boxes, but I'm not where to start with his approach and what I'm trying to achieve. –  Rick Pickett Feb 16 '13 at 4:28

1 Answer 1

I've sort of done this with using the same function to save the meta on the post screen and also on the quickedit. In your case I think you need to add an or clause to your nonce validation.

if (!wp_verify_nonce($_POST['home_meta_box_nonce'], basename(__FILE__)))   
        return;

as

if (!wp_verify_nonce($_POST['home_meta_box_nonce'], basename(__FILE__)) || !wp_verify_nonce($_POST['home_meta_box_left_nonce'], basename(__FILE__)) )   
       return;

Then you could check if the appropriate meta is posted and update for each box.

share|improve this answer
    
Thanks @helgatheviking for the info... Does the nonce check have to be used for each meta box individually? –  Rick Pickett Feb 16 '13 at 2:04
    
I guess every metabox should have a nonce? I get a little confused there and have definitely used the same nonce on both the posts page and on the quickedit exactly to get around this point. I think WP even had its own default nonce for posts saving. –  helgatheviking Feb 16 '13 at 2:34
    

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.