2

How to get widget options?

I've tried like this, like seen in the other question "Using widget options outside of the widget":

$w=get_option('widget_wp_mywidget');
    $one=$w[2]["myval"];
    $two=$w[2]["myotherval"];

But I am not quite sure why this [2] is dynamic and i can't rely on it, so how to get exact values of the array the right way?

3
  • 2
    Since there may be multiple instances of a widget an index is needed to specify the exact instance. So, is your question given a specific sidebar how to get the index of instance of the widget in that sidebar?
    – user27457
    Commented Mar 29, 2014 at 9:59
  • I think I may understand your problem. Can you do an add_action( 'wp_loaded', 'your_function' ) in the widget's constructor where your_function does what you want. This schedules your_function to run after WP is fully loaded i.e., after all the 'init' actions are done. Also, you may need to use a function closure to pass specific widget data to the action function.
    – user27457
    Commented Mar 29, 2014 at 21:47
  • The function itself (above widget constructor) requires the widget settings, so it doesn't work :( Commented Mar 29, 2014 at 21:52

2 Answers 2

2

Widget data is stored in the options table as a two dimensional array. All data for the same type of widget is stored under the same option key. The key of the outer array is a kind of widget "index"-- the identifier for the particular instance of the widget. The inner arrays contain the individual widget data. Like so:

array(5) {     // outer array
  [3]=>        // the widget instance identifier
  array(3) {   // widget instance data
    ["title"]=>
    string(0) ""
    ["text"]=>
    string(5) "first"
    ["filter"]=>
    bool(false)
  }
  [4]=>        // the widget instance identifier
  array(3) {   // widget instance data
    ["title"]=>
    string(0) ""
    ["text"]=>
    string(6) "second"
    ["filter"]=>
    bool(false)
  }
  // and so on
}

To see what I mean, place the following in your theme header (or somewhere easily visible):

$w=get_option('widget_wp_mywidget');
var_dump($w);

Then drag your widget into the sidebar. You should see that $w array get larger. If you delete some widgets you will notice that the keys don't reset. They are not simple auto-increment numeric indexes.

What this means is to pull the widget data for a particular widget, you need to know the widget's instance identifier, which is really pretty tricky and I don't know exactly what your requirements are.

You could crawl that $w array looking for a clue like a title, or crawl the site sidebars looking for a widget in a particular location. For example, try:

var_dump(wp_get_sidebars_widgets());

You will notice that there is data in that array of the pattern text-7, pages-4. That prefix is the widget type and the suffix matches the "identifiers"-- the keys-- in the array above.

Edit:

After more thought and several comments, I think the best answer is:

There is no best way to get widget options. Widgets are intended to operate within and to be managed by the rather complicated Widget API built into the Core. There is no easy way, and certainly no Core way, to get access to widget data outside of that system. A lot of information has to get juggled around to take widgets apart and to put them back together.

My feeling is that if you think you have the need to use a widget outside of the Widget API you are probably using the wrong tool for the job.

I can understand the need, perhaps, to use the same data in a widget and elsewhere but I would suggest that using the widget as the source of that data is backwards. The more I think about this the more I am convinced that the better way to do it is to use some other form/interface for the data-- Theme Option, Plugin Settings page, something-- and then retrieve that data for use in the widget and outside of it.

5
  • Okay so is there another way of getting the widget options directly from db? The widget gets "cleaned up" after deactivation. And another things i did try the "wp_Get_sidebars_widgets" and I see it but what next? How can i compare it to the widget options? Commented Mar 29, 2014 at 18:51
  • That is how the data is stored in the database. get_option('widget_wp_mywidget') is as direct as it gets.
    – s_ha_dum
    Commented Mar 29, 2014 at 18:54
  • @s_ha_dum: 'There is no easy way, and certainly no Core way, to get access to widget data outside of that system.' - I don't think this is quite correct. Consider - the globals $wp_registered_widgets, $wp_registered_sidebars and the function is_active_widget() these contain all the information you need to get the widget number for a widget in a specific sidebar.
    – user27457
    Commented Mar 29, 2014 at 21:43
  • Try and dump the global $wp_registered_widgets - not the return value of wp_get_sidebars_widgets() and all will be obvious.
    – user27457
    Commented Mar 29, 2014 at 22:07
  • @MagentaCuda : I know how to do this and in broad strokes I explained it. The problem is working out which widget to use. The system is not built for that. If fact, trying to use widget data as reusable data "options" is an abuse of the system. There are better ways.
    – s_ha_dum
    Commented Mar 30, 2014 at 13:31
3

First you need to know the name of the $widget.

In this example our widget's class name is FooBar.

Refer to Wordpress Codex or, plugin docs for the widget class names. https://codex.wordpress.org/Function_Reference/the_widget

Next we want to get $all_instances of the widget.

Widgets are stored as options in the database. We can use the 'get_option()' Wordpress function to retrieve all the widget data associated with a particular widget class.

Widget option names use the prefix 'widget' so, your option name will look something like: 'widget_foobar'

$all_instances = get_option('widget_foobar');

Let's print an array of all the widgets stored in that option

print_r( $all_instances );

// You might get an array that looks something like this:

Array ( [2] => Array ( [title] => Foo Title [text] => Bar Text ) [3] => Array ( [title] => Bar Title [text] => Foo Text ) 

Now let's get the widget $instance we want

We're going to print the 1st widget in the array which has an index of [2].

$instance = $all_instances[2];

the_widget('FooBar', $instance, $default_args );

Omit $default_args to use the theme's default widget 'before and after' arguments.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

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