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.

Note: This is not the popular question about how to create multiple instances of a widget. I have a text widget that I am using to display "business hours". This text needs to go in multiple sidebars and is likely to change often enough to be a nuisance to change it in multiple places. Is there a way to use the same instance of a text widget on more than one sidebar?

Any alternatives that use tokens or some other kind of pointer would also be a solution.

share|improve this question

2 Answers 2

up vote 1 down vote accepted

A possible solution would be to enable shortcodes in the Text Widget.

add_filter( 'widget_text', 'do_shortcode', 11 );

Then put the same shortcode (i.e.: "[business_hours]") in all text widgets, and all of them will display the same content.

It's even possible to add some Conditionals Tags inside the shortcode definition to show different things according to the context where it is being displayed.

share|improve this answer
    
I'm guessing that's most likely the path of least resistance for what I'm trying to do. Thanks! –  Shane Nov 29 '12 at 22:42

I searched for a hook or filter that might help achieve that but could not find any. There is however dynamic_sidebar action but it will be fired after each widget display making its use not practical. So I wrote this helper function which mimics the way Wordpress outputs widgets in the sidebar, call this function after the call of dynamic_sidebar() where you want a copy of the widget to appear in your the theme:

/*
 * Duplicate Widget in Dynamic Sidebar.
 *
 * Make a copy of selected widget and display it in a selected sidebar, help make
 * edits to multiple identical widgets easier.
 *
 * @param string $widget_id Required, the ID of the widget to duplicate.
 * @param int|string $sidebar_index Optional, default is 1. Name or ID of dynamic sidebar.
 * @param string $copy Optional, default to the order the function was called, custom html id
 *  for the widget element.
*/

function ad_duplicate_widget($widget_id, $sidebar_index = 1, $copy = '') {
    global $wp_registered_widgets, $wp_registered_sidebars;
    static $i = 0;
    $i++;
    if ($copy == '')
        $copy = $i;
    //$sidebars_widgets = wp_get_sidebars_widgets();
    if (is_int($sidebar_index)) {
        $sidebar_index = "sidebar-$sidebar_index";
    } else { 
        $sidebar_index = sanitize_title($sidebar_index);
        foreach ($wp_registered_sidebars as $key => $value) {
            if ( sanitize_title($value['name']) == $sidebar_index ) {
                $sidebar_index = $key;
                break;
            }
        }
    }
    $sidebar = $wp_registered_sidebars[$sidebar_index];
    $widget = $wp_registered_widgets[$widget_id];
    $def_params = array(
        'widget_id' => $widget_id,
        'widget_name' => $widget['name']
    );
    $params = array_merge(array(array_merge($sidebar, $def_params)), $widget['params']);
    $classname = $widget['classname'];
    $classname_ = '';
    if ( is_string($classname) )
        $classname_ .= '_' . $classname;
    elseif ( is_object($classname) )
        $classname_ .= '_' . get_class($classname);
    $new_id = $widget_id . '-' . $copy;
    $params[0]['before_widget'] = sprintf($params[0]['before_widget'], $new_id, $classname_);
    $callback = $widget['callback'];
    if ( is_callable($callback) ) {
        call_user_func_array($callback, $params);
    }
}

Usage

Place this function in functions.php file and then call ad_duplicate_widget($widget_id, $sidebar_index, $copy) right after the call of dynamic_sidebar() where you want to copy your widget. $widget_id is the html id attribute of the widget element. $sidebar_index can be either the index of the sidebar (number) or the sidebar name (string). $copy is the custom html id appended to widget id.

Example

If you have a text widget of id 'text-5' that is displayed in the main sidebar of the blog and you want to display it in Sidebar Right sidebar, call this function after the dynamic_sidebar('Sidebar Right') call, which maybe called from sidebar.php or sidebar-right.php file:

dynamic_sidebar('Sidebar Right');

ad_duplicate_widget('text-5', 'Sidebar Right');

This will create a copy of the widget in Sidebar Right sidebar, and any edit of the original widget will apply to both widgets.

share|improve this answer
    
That was a lot of effort, thanks! +1, though I don't think I'm going to use it because of the workflows associated with this site (they need to be dead simple for updates, etc.) Hopefully your answer will nail it for someone else. –  Shane Nov 29 '12 at 22:41

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.