Usar wp_category_checklist en un widget

8

Estoy tratando de usar wp_category_checklist en un widget para mostrar una lista de casillas de verificación que, cuando se guardan, permanecen marcadas. En este momento estoy teniendo problemas terribles para que ahorren, hasta donde sé que no está guardando (las casillas de verificación no están marcadas):

Aquí está el código editado que tengo en este momento.

function update($new_instance, $old_instance) {
    $instance = $old_instance;
    $instance['widget_categories'] = $new_instance['post_category'];
return $instance;
}


function form($instance) {
    $instance = wp_parse_args( (array) $instance, $default );
    $categories = get_categories();     

    $category_array = $instance['widget_categories'];

    if (!$category_array)
    {
        $category_array = array();
    }
    ?>
    <ul class="categorychecklist">
    <?php wp_category_checklist(0,0, $category_array,false, NULL , false);?>
    </ul>
    <?php
}

¿Algunas ideas? Por favor, hágame saber si necesita algo más.

Gracias :)

Rhys Wynne
fuente

Respuestas:

9

El problema es que para que el updatemétodo de la clase de widget funcione, las entradas de nombre en el formmétodo deben establecerse mediante, $this->get_get_field_name('name_of_the_field');pero wp_category_checklistno tiene ningún argumento para configurar el nombre de las entradas (casillas de verificación).

Sin embargo, wp_category_checklistutiliza una clase de caminante para imprimir las casillas de verificación y permitir personalizarlo. Por defecto, la clase utilizada es Walker_Category_Checklist, y el método que imprime las casillas de verificación es start_el.

Ese método no tiene filtro para permitir la edición de los nombres de entrada, pero podemos crear un andador personalizado, que acepte parámetros para configurar el nombre. Si este andador se extiende Walker_Category_Checklist, solo necesitamos anular el start_elmétodo (principalmente copiando del original).

El código:

// This is required to be sure Walker_Category_Checklist class is available
require_once ABSPATH . 'wp-admin/includes/template.php';
/**
 * Custom walker to print category checkboxes for widget forms
 */
class Walker_Category_Checklist_Widget extends Walker_Category_Checklist {

    private $name;
    private $id;

    function __construct( $name = '', $id = '' ) {
        $this->name = $name;
        $this->id = $id;
    }

    function start_el( &$output, $cat, $depth = 0, $args = array(), $id = 0 ) {
        extract( $args );
        if ( empty( $taxonomy ) ) $taxonomy = 'category';
        $class = in_array( $cat->term_id, $popular_cats ) ? ' class="popular-category"' : '';
        $id = $this->id . '-' . $cat->term_id;
        $checked = checked( in_array( $cat->term_id, $selected_cats ), true, false );
        $output .= "\n<li id='{$taxonomy}-{$cat->term_id}'$class>" 
            . '<label class="selectit"><input value="' 
            . $cat->term_id . '" type="checkbox" name="' . $this->name 
            . '[]" id="in-'. $id . '"' . $checked 
            . disabled( empty( $args['disabled'] ), false, false ) . ' /> ' 
            . esc_html( apply_filters( 'the_category', $cat->name ) ) 
            . '</label>';
      }
}

Ahora, probablemente en el mismo archivo podemos escribir la clase de widget:

/**
 * An example of widget using wp_category_checklist on form
 */
class TestCategoryWidget extends WP_Widget {

    function __construct(){
        parent::__construct( false, 'TestWidget');
    }

    function widget( $args, $instance ) { 
        // Displays the widget on frontend 
    }

    function update( $new_instance, $old_instance ) {
        $instance = $old_instance;
        $instance['widget_categories'] = $new_instance['widget_categories'];
        return $instance;
    }

    function form( $instance ) {
        $defaults = array( 'widget_categories' => array() );
        $instance = wp_parse_args( (array) $instance, $defaults );    
        // Instantiate the walker passing name and id as arguments to constructor
        $walker = new Walker_Category_Checklist_Widget(
            $this->get_field_name( 'widget_categories' ), 
            $this->get_field_id( 'widget_categories' )
        );
        echo '<ul class="categorychecklist">';
        wp_category_checklist( 0, 0, $instance['widget_categories'], FALSE, $walker, FALSE );
        echo '</ul>';
    }

}

Finalmente, registre el widget:

function TestCategoryWidgetInit() {
    register_widget( 'TestCategoryWidget' );
}

add_action( 'widgets_init', 'TestCategoryWidgetInit' );
gmazzap
fuente