WordPress custom widget remember multiple select options

I’m writing a custom widget for our site to display some chosen posts. In the admin part, I’ve got a multiple select box to let the admin choose multiple posts by their name. This is working fine, but when I select a few different posts and save, nothing is getting saved.

Can anyone shed any light on this?

Read More

Here is my code…

<?php
/* 
Plugin Name: Hot Topics
Plugin URI: http://www.weddingideasmag.com
Description: Use this widget to choose an array of posts snippets to show
Version: 1.0)
Author: James Payne
Author URI: http://www.bluntcreative.co.uk
License: GPL2
*/


class HotTopics extends WP_Widget {

// constructor
function HotTopics() {
    $widget_ops = array( 'name' => 'Hot Topics','classname' => 'widget-hot-topics', 'description' => __( "Use this widget to choose an array of posts snippets to show in the sidebar." ) );
    $this->WP_Widget( 'hottopics', __('Hot Topics'), $widget_ops);
}

// widget form creation
function form($instance) {  
    // Check values
    if( $instance) {
        $select = esc_attr($instance['select']); // Added 
    } else {
         $select ='';
    }
    ?>

    <select multiple="multiple" name="<?php echo $this->get_field_name('select'); ?>[]" id="<?php echo $this->get_field_id('select'); ?>" class="widefat" size="15" style="margin-bottom:15px;">
        <?php
        $args = array( 'offset'=> 1, 'orderby' => 'date', 'order' => 'DESC', 'posts_per_page' => 200, 'post_status' => 'publish' );

        // The Query
        query_posts( $args );

        // The Loop
        while ( have_posts() ) : the_post();

        $title = get_the_title();
        ?>
            <option value="<?php echo get_the_ID();?>" class="hot-topic" <?php $select == $title ? ' selected="selected"' : '';?> style="margin-bottom:3px;">
                <?php echo $title;?>
            </option>
            <?php
        endwhile;

        // Reset Query
        wp_reset_query();
        ?>
    </select>

    <?php
}

// update widget
function update($new_instance, $old_instance) {
      $instance = $old_instance;
      // Fields
      $instance['select'] = strip_tags($new_instance['select']);
     return $instance;
}

// widget display
function widget($args, $instance) {
    /* ... */
    echo 'tetst';
}
}

// register widget
add_action('widgets_init', create_function('', 'return register_widget("HotTopics");'));

?>

Related posts

Leave a Reply

1 comment

  1. When the widget is updated, strip_tags is destroying the array of selected posts. A esc_sql does the job. Also, don’t use query_posts. And finally, storing the post title is not ideal as it may change, the ID is permanent.

    A working sample:

    # PHP 5.3+ anonymous function
    add_action( 'widgets_init', function() {
        register_widget( 'Sample_Widget_SO_19246434' );
    });
    
    class Sample_Widget_SO_19246434 extends WP_Widget 
    {
        function Sample_Widget_SO_19246434() 
        {
            $this->WP_Widget( 
                'hottopics', 
                __('Hot Topics'),
                array( 
                    'name' => 'Hot Topics',
                    'classname' => 'widget-hot-topics', 
                    'description' => __( "Description" ) 
                )
            );
        }
    
        function form( $instance ) 
        {
            if( $instance ) 
                $select = $instance['select'];
            else
                 $select ='';
    
            $get_posts = get_posts( array( 
                'offset'=> 1, 
                'orderby' => 'date', 
                'order' => 'DESC', 
                'posts_per_page' => 200, 
                'post_status' => 'publish' 
            ));
            if( $get_posts )
            {
                printf(
                    '<select multiple="multiple" name="%s[]" id="%s" class="widefat" size="15">',
                    $this->get_field_name('select'),
                    $this->get_field_id('select')
                );
                foreach( $get_posts as $post )
                {
                    printf(
                        '<option value="%s" class="hot-topic" %s style="margin-bottom:3px;">%s</option>',
                        $post->ID,
                        in_array( $post->ID, $select) ? 'selected="selected"' : '',
                        $post->post_title
                    );
                }
                echo '</select>';
            }
            else
                echo 'No posts found :(';
        }
    
        function update( $new_instance, $old_instance ) 
        {
            $instance = $old_instance;
            $instance['select'] = esc_sql( $new_instance['select'] );
            return $instance;
        }
    
        function widget( $args, $instance ) 
        {
            echo 'Hello world';
        }
    }
    

    Related:
    • What’s the difference between esc_* functions?
    • How to sanitize user input?