I’m trying to restrict the number of widgets from the “wp_inactive_widgets” sidebar to maximum 10, because the widgets admin page is incredibly slow:
add_filter('pre_update_option_sidebars_widgets', 'cleanup_inactive_widgets', 10, 2);
function cleanup_inactive_widgets($new, $old){
if(!empty($new['wp_inactive_widgets']) && count($new['wp_inactive_widgets']) > 10)
$new['wp_inactive_widgets'] = array_slice($new['wp_inactive_widgets'], -10, 10);
return $new;
}
This works apparently, but the problem is that the widget instance options still remain in the database, regardless if the widget instance exists or not inside a sidebar…
Does anyone know a way to remove the widget options too?
I found out a solution:
Edit: in certain situations it seems to remove widgets from other sidebars too, I’m not sure what’s causing this…
if(!empty($new['wp_inactive_widgets']) && count($new['wp_inactive_widgets']) > 10){
// find out which widget instances to remove
$removed_widgets = array_slice($new['wp_inactive_widgets'], 0, -10);
// remove instance options
foreach($removed_widgets as $widget_id)
if(isset($GLOBALS['wp_registered_widgets'][$widget_id])){
$instance = $GLOBALS['wp_registered_widgets'][$widget_id]['callback'][0]->number;
$option_name = $GLOBALS['wp_registered_widgets'][$widget_id]['callback'][0]->option_name;
$options = get_option($option_name); // get options of all instances
unset($options[$instance]); // remove this instance's options
update_option($option_name, $options);
}
// keep only the last 10 records from the inactive widgets area
$new['wp_inactive_widgets'] = array_slice($new['wp_inactive_widgets'], -10, 10);
}
return $new;
Tested under v3.2.1:
The above code limits the inactive sidebar to the last 10 widgets, and only the inactive sidebar. It also removes the options for the widgets that have been deleted.