The Advanced Custom Fields plugin offers a plethora of possibilities for enhancing WordPress functionality. The following is an example of one such possibility.
In the process of building a new WordPress theme for a client, I wanted a way for administrators to dynamically create new widgetized sidebars and then select which sidebar to use on a per-page or post basis.
Notice: This project requires the repeater field available as a premium add-on in ACF 4.X or included with ACF Pro.
Lets start with the basic “register_sidebar” function in the functions.php file
/* * Register Sidebars */ function sidebar_widgets_init() { //Register the default sidebar register_sidebar( array( 'name' => 'Sidebar', 'id' => 'default-sidebar', 'before_widget' => '<aside id="%1$s" class="widget %2$s">', 'after_widget' => '</aside>;', 'before_title' => '<h1 class="widget-title">', 'after_title' =>; '</h1>', ) ); include_once( ABSPATH . 'wp-admin/includes/plugin.php' ); if (is_plugin_active('advanced-custom-fields/acf.php')){ //Check to see if ACF is installed if (get_field('sidebars','option')){ while (has_sub_field('sidebars','option')){ //Loop through sidebar fields to generate custom sidebars $s_name = get_sub_field( 'sidebar_name', 'option' ); $s_id = str_replace(' ', '-', $s_name); // Replaces spaces in Sidebar Name to dash $s_id = strtolower( $s_id ); // Transforms edited Sidebar Name to lowercase register_sidebar( array( 'name' => $s_name, 'id' => $s_id, 'before_widget' => '<aside id="%1$s" class="widget %2$s">', 'after_widget' => '</aside>', 'before_title' => '<h1 class="widget-title">', 'after_title' => '</h1>', ) ); }; }; }; }; add_action( 'widgets_init', 'sidebar_widgets_init' );
What we’re doing here is initiating the standard Default Sidebar as well as looping through a repeater field that we will be setting up in our ACF Options.
To set up those options, create a new repeater field in our Options field group with the following settings…
Now we have the ability to dynamically register new sidebars in our options like this…
Now that’s only half the battle! Now, we want users to be able to select which sidebar they’d like to use when create a new page or (optionally) a post.
We do this by first creating a new ACF field group called “Select Sidebar”. This group only has a single select field. In this case we’ll label it “Select A Field” and make sure it has a name of “select_a_filed”. Add field instructions if you wish and leave everything else default. Make sure to leave the Choices field empty. We will be populating this dynamically based off of the sidebars we register on out options page.
Add the following code to our functions.php file…
/* * ACF Sidebar Loader */ function my_acf_load_sidebar( $field ){ // reset choices $field['choices'] = array(); $field['choices']['default-sidebar'] = 'Default Sidebar'; $field['choices']['none'] = 'No Sidebar'; // load repeater from the options page if(get_field('sidebars', 'option')) { // loop through the repeater and use the sub fields "value" and "label" while(has_sub_field('sidebars', 'option')) { $label = get_sub_field('sidebar_name'); $value = str_replace(" ", "-", $label); $value = strtolower($value); $field['choices'][ $value ] = $label; } } // Important: return the field return $field; } add_filter('acf/load_field/name=select_a_sidebar', 'my_acf_load_sidebar');
This code populates our “Select A Sidebar” field using the add_filter function. It starts by creating two options by default. A “Default Sidebar” and a “None” option. These should be self explanitory, but just in case, the Default Sidebar is the standard WordPress sidebar available from the start. The “None” is exactly that. No sidebar will appear on the page.
We’re almost done, but depending on your template, chances are you’ll need to make some modifications to the sidebar.php file.
This is what mine looks like…
/* * sidebar.php */ <div id="secondary" class="widget-area span4" role="complementary"> <?php do_action( 'before_sidebar' ); ?> <?php $sidebar = get_field('select_a_sidebar'); if($sidebar != 'none'){ dynamic_sidebar($sidebar); }; ?> <?php do_action( 'after_sidebar' ); ?> </div><!-- #secondary .widget-area -->
What we’re doing here is calling back to our “Select a Sidebar” field to see what the user has chossen for his sidebar. If “None” was selected, then no sidebar will be returned.
And that’s it! Now we have given our users a way to create new sidebar containers and select which conaiter they’d like to use on their pages on a per-page basis.
I hope this helped, and if you see a way to improve this process, I’m all ears.
Perfect perfect perfect! Thanks so much for writing this. HUGE help!
“To set up those options, create a new repeater field in our Options field group” — “Repeater” is not a field type.
A Repeater field type is available as a premium add-on to ACF.
Absolutely love it! Wish I found this a few projects ago. Have just implemented it and it works perfectly. Thank you