Add a custom logo uploader to the WordPress theme customizer

The WordPress theme customizer is famous for being able to change your theme colors in real time, but did you know it can handle almost any type of theme option?

You can add layout options, image uploaders, text fields, and lots more. The possibilities are endless!

There is almost no need for theme options pages anymore. I personally like the idea of having no theme options page, and limiting everything to the theme customizer.

I’m going to show you how to add a custom logo uploader to your theme customizer, then display it in place of the site title and tagline.

Create the logo uploader setting

This may be review for some of you, but I’ll go over my basic setup for using the theme customizer. In my custom theme folder most of the code is going into /inc/customizer.php, and then we will include that file via functions.php. You could put all the code into functions.php and it will work, but it’s nice to keep functions.php uncluttered.

First, we create our function to register the new settings. I’ve prefixed my function name with m1, but you can use whatever you want:

function m1_customize_register( $wp_customize ) {
	// All the code in this tutorial goes here
add_action( 'customize_register', 'm1_customize_register' );

Inside our function we need to register a setting. This saves the logo url in the database so we can use it in our theme.

function m1_customize_register( $wp_customize ) {
	$wp_customize->add_setting( 'm1_logo' ); // Add setting for logo uploader
add_action( 'customize_register', 'm1_customize_register' );

Next, we add the uploader and assign it to a section. You could create a new section, but I think it goes nicely with the title and tagline. If you are using a different name for your setting, make sure you change all instances of m1_logo to something else.

function m1_customize_register( $wp_customize ) {
	$wp_customize->add_setting( 'm1_logo' ); // Add setting for logo uploader
	// Add control for logo uploader (actual uploader)
	$wp_customize->add_control( new WP_Customize_Image_Control( $wp_customize, 'm1_logo', array(
    	'label'    => __( 'Upload Logo (replaces text)', 'm1' ),
    	'section'  => 'title_tagline',
    	'settings' => 'm1_logo',
	) ) );
add_action( 'customize_register', 'm1_customize_register' );

That’s it for the code in customizer.php. To make sure our theme uses this file, simply add this one line of code in functions.php:

require get_template_directory() . '/inc/customizer.php';

That’s it! We kept our functions.php file clean as a whistle.

Next we need to display our logo.

Displaying the logo

We are going to work in our theme’s header.php file to display the logo. If there is no logo, we’ll just display the site title and description.

To get the logo url from our theme customizer, you use this code:

get_theme_mod( 'm1_logo' )

You can store that in a variable if you want, or echo it out as is. Since we are only using this value once in our theme, we don’t need to store it in a variable.

Wherever your site title is displayed in header.php, you’ll want to replace it with this code:

<?php if ( get_theme_mod( 'm1_logo' ) ) : ?>
	<a href="<?php echo esc_url( home_url( '/' ) ); ?>" id="site-logo" title="<?php echo esc_attr( get_bloginfo( 'name', 'display' ) ); ?>" rel="home">

		<img src="<?php echo get_theme_mod( 'm1_logo' ); ?>" alt="<?php echo esc_attr( get_bloginfo( 'name', 'display' ) ); ?>">


	<?php else : ?>
		<h1 class="site-title"><a href="<?php echo esc_url( home_url( '/' ) ); ?>" title="<?php echo esc_attr( get_bloginfo( 'name', 'display' ) ); ?>" rel="home"><?php bloginfo( 'name' ); ?></a></h1>
		<p class="site-description"><?php bloginfo( 'description' ); ?></p>
<?php endif; ?>

So let’s talk through that chunk of code. First, we create an if statement that says, “if a theme logo has been uploaded, display this logo code. Otherwise, display the site title and site description.”

The logo is linked to the homepage, it has some alt text, blah blah blah. The important part is this:

src="<?php echo get_theme_mod( 'm1_logo' ); ?>"

That calls the file url for the uploaded logo, and sets it as the image source.

Make sure to tell the user a recommended logo size, otherwise they can upload a huge file that doesn’t fit quite right. You might also want to give the container around the logo a constrained width, so it will fit no matter what.

That about does it, have fun!

Further reading:

Get more content like this

Get valuable insight on business and money in your inbox once per week.

Posted by Scott

  1. Its not work 🙁
    Displaying, but dont uploading.


    1. Same problem here.


    2. Does any one find solution of this?


  2. How to display logo witdth and height?


  3. Hi

    Same as above. When trying to load customizer.php I’m getting this error
    ” Fatal error: Call to undefined method WP_Customize_Manager::get_etting() in” …


  4. Super article, works like a charm, Thanks!


  5. awesome code, works supper. Thanks!


  6. works great! thanks very much very easy to follow method 🙂


  7. It’s works for me too.

    Keep it up!


  8. awesome code! it’s work good.


    1. I did you getting it working everytime I get this message –> Warning: call_user_func_array() expects parameter 1 to be a valid callback, function ‘m1_customize_register’ not found or invalid function name in /Users/brandonpowell/sites/valet/wordpress-development/web/wp/wp-includes/class-wp-hook.php on line 298


  9. Thanks Scott – just what I needed 🙂


  10. Great article, works like a charm, thanks! Let move our stuff from theme options to Customizer!


  11. Doesn’t work; it crashes my site.


  12. It works! Thank you so much for this article.


  13. Thanks man works really well!
    for those of you who asked above how to add width height, you can add that in the display logo code, by adding a css class maybe.


  14. Great help! Thanks heaps!


  15. Nice Article


  16. Thank you so much for this! I’m nowhere near a programmer and have tried lots of different tutorials for adding a logo upload to themes, but this is the only one I’ve been able to get to work! 🙂


  17. Great Tutorial Work Awesume


  18. Code Worked great!
    Thanks ^_^


  19. Thank you so much for this! just what I needed ?


Leave a Reply

Your email address will not be published. Required fields are marked *