Last time I wrote about using the Theme Customizer to supplant/add to your existing options. But what if you’re writing a new theme entirely?

Do you even need an options page?

How many options does your theme have, anyway? Would it not make more sense to eschew those complex options pages in favor of just allowing the user to do it all “live”? With the Theme Customizer, this becomes entirely possible. As an added bonus, it also gives us a really handy use for the theme_mod system.

Step 1: Surfacing the Customizer

One thing I don’t like about the theme customizer is how hidden it is. It’s in the Themes selection space, under the strangely worded “Live Preview” option. Let’s bring that to the forefront and make it more visible for our example theme. In our functions.php file:

There we go. Now we have a “Customize” link in the Appearance menu that loads up the customizer. Nice.

(Note, using the “customize.php” link works with the currently active theme only. Adding ?theme=themedemo to it would allow links to customize non-active themes, but this makes no real sense in the theme functions.php file of a theme. But if you were doing a plugin that needed to load the customizer, that might be good to know.)

Don’t do this anymore, kids. WordPress brought the Customize link to the surface in a later version.

Step 2: Adding some options

Let’s add some simple options to the theme customizer. How about a text field and, say, a color picker. Why not?

We now have “some_setting” and “some_other_setting”. You can tell that I’m being very creative with my naming scheme here.

Note that I didn’t define the “type” for these settings. This means they’ll be the default type, which is “theme_mod”, and that’s perfect for this case. Since we’re providing no other way than the customizer to change these settings, then it’s nice and easy to use them.

The header and footer are pretty standard. Nothing special. You can find them in the download. What we’re really concerned with here is how the theme uses the settings themselves.

Notice the use of get_theme_mod. It’s pretty darned easy to use, really. It just gets the settings and uses them however the theme needs to. For this demo, I’m just outputting their contents for demonstration purposes. I also added in a non-existent setting to show that it works and outputs the default value when nothing is set for the theme in the theme_mod system.

The nice thing about theme_mod is that it automatically stores the information in a nice packed way, unique to the theme itself. If you have multiple copies of the same theme on the site, but with different names, each will have its own settings. Easy and handy.

Step 4: There is no step 4.

Seriously, that’s it. You can go further and make the settings work “live” using the postMessage methods I explained in the previous post, but for the most part, there’s nothing more to do. This is a simple and easy way of making settings, using them, and not worrying about complex options pages, settings in the database, where they’re stored… Why do all that extra code if you don’t have to?

Here’s a link to a working theme using the above concepts. For fun, it also supports custom background colors.

50 Comments

I love the fact that I can add my custom options to the customize.php page, it’s much more intuitive for people to use than a custom theme options page. One question… is there any way to allow the WP_Customize_Image_Control function to choose pre-existing images from the media library?

I had to extend WP_Customize_Image_Control class and add my own tab_uploaded() function to filter the attachments.

If you want to use a context for your uploaded images (e.g. you’re creating a favicon uploader and only need to return already uploaded favicons), seems that all you have to do is to define a ‘context’ when you create a control. If you do this, WP will create a _wp_attachment_context meta key with the value provided inside your add_control()</code. Then you'll be able to use get_posts() the same way it's used in WP_Customize_Background_Image_Control.

@Eduardo,
Thank You for this code snippet. I see how this adds the uploaded media library to custom image controllers, but for some reason, the only images that show are the background images previously uploaded. Is there something i’m missing to make sure that the previously uploaded images that display are from that specific custom image upload controller?

I have to say this has a lot of promise instead of using theme option plugins, scripts, or even the settings API to create option pages. Is this customizer to replace the settings api ?
Also, I discovered something…if you code this with the add_control before the add_setting, the customizer window goes blank. Apparently it does not like this sequence.

IF this customizer is the way to start doing theme settings and options for customizing, I’m definitely in!

I got the Customizer working the way I want for the most part, but one thing seems odd to me: in order for WordPress to register a particular theme mod setting to the database, I need to first make some kind of change on the Customize page and click “Save & Publish”. Querying for a setting using get_theme_mod() before clicking “Save & Publish” returns a null value, unless I specify a default value in the function call.

What seems weird is that, unless I go to the Customize page and make a nominal change so that all theme mod settings are saved to the database, I effectively then have to specify a default value for a setting twice: once when adding the setting in the $wp_customize->add_setting() call, and once again when querying for the setting using get_theme_mod().

I’d rather just force WordPress to write all the settings to the database using the same default I set in the $wp_customize->add_setting() call, so that I don’t have to specify a default value for the setting again the the get_theme_mod() call. (I tried forcing WordPress to write the settings to the database by default using the set_theme_mod() function, but I wasn’t able to get it to work.)

Perhaps I’m missing something? I’d really appreciate any help you could provide. Thanks again for a great tutorial!

These are two different defaults. One is for the place you retrieve it, and the other is for telling the customizer what the default should be if it’s not in the database. These usually would be the same value, and yes, you’re specifying it twice.

Writing the defaults to the database is always a bad idea, because then they’re not really “defaults” any more. Down this path leads confusion and weird results that you’re not expecting.

My advice: Get over it, and specify the default twice. Really. You’ll save yourself a whole lot of hassle in the long run. If you want to define an array of defaults somewhere and then just reference it twice, that’s fine, do that.

I’m trying to get the Background Color control, which is in the Colors section by default, to have a priority 1 – as I’m adding color controls for a number of other areas in my theme. I have all the other controls in this section respecting a priority order – but the default background_color is stumping me. I used your add_theme_support in my functions file to set the default color, thank you. Is there something similar I can do in my functions file to set the priority on the color control for this setting?

OK. Great Start. Can you please finish a litte more on the Step 3? It doesn’t really wrap things up enough to be able to implement properly into page elements. Also, not sure why, but when using custom id’s I get a php error on the site. I was hoping for a step 4 to mirror the controls on a custom admin panel as well as how the CSS is cued or generated. I am very interested in relying only on the existing WordPress API’s and js files. I’ve attempted to use Options Framework and OptionTree, but I’m extremely afraid to sell a theme that will have a conflict when updating. It seems that every source I can find online about creating custom wordpress admin panels are incomplete, and no offer little to no support…

I’ve been using the Theme Customizer in some themes and loving it. So I’m wondering if we could also use the Theme Customizer in plugins if they have some styling that needs to be customized? Or if we can, should we?

The controls and the live preview are incredible, and I could see how I could use them to provide some flexibility to a plugin. But would that make sense to an end user, to have this under the same place where they customize a theme? Or is it better to keep plugins into their own option / setting pages?

When i add the “Customize” link to the admin panel as described in the intro it also appears under “Options” in the “Themes” panel. So in the end “Customize” appears twice in the themes panel. How can i avoid that or delete one entry?

In this case, commenting out get_theme_supports() has the expected behavior. Since I like to provide a lot of functionality that requires configuration and styling when added by a child theme (conditionally adding a lot of JS and CSS stuff is much better than just adding unused junk to a theme), this is an AWESOME feature to have at my command.

Otto, thank you for a great tutorial. I have a question, though: is it possible to have 2 different customizers in the same theme? I mean, I want to customize the main page AND an inner page, and no matter what I try, I can’t do it. I mean in Live mode, it works like a charm if I reload, just can’t make it work in live mode, even if I navigate to the page I want to edit

The team over at Redux Framework recently added the ability to add a customizer: true flag to options. It’s in beta but it’s quite effective at duplicating things like color & typography options right into the customizer without a scrap of extra programming. It’s a good project, as several top admin frameworks (including SMOF) have converged on this one standard: http://reduxframework.com/