I've read about Selective Refresh and I understand it. It completely rewrites the element targeted by the specified selector
. For example:
$wp_customize->get_setting( 'nav_type' )->transport = 'postMessage';
$wp_customize->selective_refresh->add_partial( 'nav_type', array(
'selector' => '#container nav',
'render_callback' => 'change_body_class',
) );
This will remove the <nav>
inside an element with id container
and replace it with whatever happens in the change_body_class
function. As the name of the function suggests, though, I just want to change the class of the <body>
element. Why? Well, in my CSS, I have different layouts for the navigation that are toggled through a <body>
class.
Question
I want a selective refresh that shows the shortcut icon next to Element A while changing the class of Element B. Is this possible? If yes, how do I do it?
I've read about Selective Refresh and I understand it. It completely rewrites the element targeted by the specified selector
. For example:
$wp_customize->get_setting( 'nav_type' )->transport = 'postMessage';
$wp_customize->selective_refresh->add_partial( 'nav_type', array(
'selector' => '#container nav',
'render_callback' => 'change_body_class',
) );
This will remove the <nav>
inside an element with id container
and replace it with whatever happens in the change_body_class
function. As the name of the function suggests, though, I just want to change the class of the <body>
element. Why? Well, in my CSS, I have different layouts for the navigation that are toggled through a <body>
class.
Question
I want a selective refresh that shows the shortcut icon next to Element A while changing the class of Element B. Is this possible? If yes, how do I do it?
Share Improve this question asked Jul 11, 2017 at 8:18 dodovdodov 1971 silver badge9 bronze badges1 Answer
Reset to default 2Yes. This can be accomplished by creating a custom selective refresh Partial
type, and overriding the refresh
method in the JavaScript class.
Here's the relevant JavaScript which should get enqueued in the Customizer preview, with customize-selective-refresh
as its script dependency:
wp.customize.selectiveRefresh.partialConstructor.body_class = wp.customize.selectiveRefresh.Partial.extend({
/**
* Class name choices.
*
* This is populated in PHP via `wp_add_inline_script()`.
*
* @type {Array}
*/
choices: [],
/**
* Refresh partial.
*
* Override refresh behavior to bypass partial refresh request in favor of direct DOM manipulation.
*
* @returns {jQuery.Promise} Resolved promise.
*/
refresh: function() {
var partial = this, setting, body, deferred, className;
setting = wp.customize( partial.params.primarySetting );
className = setting.get();
body = $( document.body );
body.removeClass( partial.choices.join( ' ' ) );
body.addClass( className );
// Do good diligence and return an expected value from the function.
deferred = new $.Deferred();
deferred.resolveWith( partial, _.map( partial.placements(), function() {
return '';
} ) );
return deferred.promise();
}
});
Then you can make use of this custom type when you register the partial in PHP:
$wp_customize->selective_refresh->add_partial( 'nav_body_class', array(
'selector' => 'nav',
'type' => 'body_class',
) );
Here is a full working plugin that demonstrates the technique: https://gist.github/westonruter/731e3106177ce2b067290ddbe602ce05