kirki
kirki copied to clipboard
Change Preview URL when sections expanded
Hi Ari,
This is more like a feature request. Can you integrate some JS to change the preview URL to specific page that is defined in the section object.
For example, we have these sections in the Customizer:
- Colors
- Typography
- Header
- Footer
- Blog
Now I want to customize the looks of my Blog page, and I click "Blog" section in the Customizer panel. I think it would be very useful if when the "Blog" section expanded, the preview frame would change to the actual Blog page. This way, I can directly see my changes on the blog page without having to find where is my blog page in the preview frame.
When the section is closed (back to upper level), the preview frame could redirect back to the last state (the upper section's preview).
Is it possible?
Ref: https://make.xwp.co/2016/07/21/navigating-to-a-url-in-the-customizer-preview-when-a-section-is-expanded/
The implementation on the array could be something like this:
Kirki::add_section( 'blog', array(
'title' => __( 'Blog' ),
'priority' => 160,
'preview_url' => get_option( 'show_on_front' ) == 'page' ? get_permalink( get_option( 'page_for_posts' ) ) : home_url(),
) );
What do you think?
hmmm... that's a neat feature request... Marking as one and I'll try to do some more research on the subject. 👍
Just bumping this up as I was interested in it as well.
Inspiration came from this post: https://make.xwp.co/2016/07/21/navigating-to-a-url-in-the-customizer-preview-when-a-section-is-expanded/
A built in method for this could be useful.
Implementing this feature will be easy. The reason it has not been done yet is this part:
When the section is closed (back to upper level), the preview frame could redirect back to the last state (the upper section's preview).
It's not as simple as that... Imagine this scenario: You go to the "Blog" section. The preview panel changes to the blog page. At this point we're saving the previous URL in a global JS var. You then want to see what single posts (which hierarchically also belong under the "blog" section) look like, and fine-tune some options that these may have. So you click on a single post. Now the global var we saved previously would have to contain both URLs, because I have to assume that when you exit the "Blog" section, you want to go back to the page you were on before you entered the blog section in the first place. (or maybe not?) So the global var would have to be an array, and we add URLs to it as we go. But at which point do we reset? And what should trigger a reset to the previous URL? What if on my theme, in the "Blog" section I only have settings for the actual blog page, and then I have a button on the top of the section that just says "Click here for single-posts options", and when clicked takes you to another section for the single posts. What should happen then?
It's a logic issue. If we know exactly what we want to do and when we want to do it, implementing this will be a piece of cake.
Contextual controls & sections are already possible, so instead of redirecting the preview pane to the blog page when one opens the blog section, we can only show the blog section when the preview pane is in the blog page.
Realistically the redirect should only be one direction for the exact situation you brought up.
"Blog" Section => blog page "Single Post" Section => first single blog post "Fonts" Section => Why bother redirecting, this is a global section, it applies everywhere.
That's the way I would do it, at least. If a section needs a redirect, do it. If not, don't do anything, because it's likely a global customization.
Yeah, but what happens when you click the "back" button in the "single post" section? Does it change the preview to show the page you were on before you clicked the "single posts" section and got auto-redirected? Or does it leave you on the post?
I can see both behaviours as correct, I can see both of them as bugs. I can see customers saying things like
"Why wouldn't I want to go back to the page I was before? That's what I was editing before you took me somewhere I had no intention of going."
And at the same time
"Will you please stop it with all those annoying redirects? I'm trying to do my job here".
I would say do nothing.
"MyTheme Panel"
- "Blog Archives" section =>redirect
- "Single Posts" section => redirect
- "Fonts" section => do nothing
- "Colors" section => do nothing
- etc...
Hitting "back" from any one section goes back to the panel, which has no redirect. Re-opening a section with a redirect does what it's supposed to do...redirect. If I open a section with a redirect, and then click a link in the preview pane, it follows that link as it should. If I then hit back, it stays on the same page. If I open a new section with a redirect, it redirects. This way it's really only triggering a redirect on section open, nothing to store for history.
It sounds like something that could be grossly abused by someone, yes, but when used properly, it immensely helps the user experience of customization. (in my experience)
Ultimately it would be up to the implementer to use their own judgement to determine what sections need to be (or should be) redirected, you're just providing them the tools.
If we don't want to handle the "back" links in sections and only want to change the preview-pane URL when one enters the section then that will be easy. Adding to the 4.0 milestone and I'll try to get it done this weekend. 👍
That would be awesome. You rock man.
It's been a few years since this thread has been updated. Any progress on this ?
If anyone is interested in unofficially implementing this I've done this with the following code which adds support for "preview_url" to Kirki sections & panels.
Load the preview URLS into globals using hooks
// Loads preview urls from sections into global $kirki_section_preview_urls
function _nok_add_kirki_section_preview_url_support( $section_id, $args ) {
global $kirki_section_preview_urls;
if( !is_array( $kirki_section_preview_urls ) ) {
$kirki_section_preview_urls = array();
}
if( !empty( $args['preview_url'] ) ) {
$kirki_section_preview_urls[] = [
'section_id' => $section_id,
'preview_url' => $args['preview_url']
];
}
}
add_action( 'kirki_section_init', '_nok_add_kirki_section_preview_url_support', 10, 2 );
// Loads preview urls from panels into global $kirki_panel_preview_urls
function _nok_add_kirki_panel_preview_url_support( $section_id, $args ) {
global $kirki_panel_preview_urls;
if( !is_array( $kirki_panel_preview_urls ) ) {
$kirki_panel_preview_urls = array();
}
if( !empty( $args['preview_url'] ) ) {
$kirki_panel_preview_urls[] = [
'panel_id' => $section_id,
'preview_url' => $args['preview_url']
];
}
}
add_action( 'kirki_panel_added', '_nok_add_kirki_panel_preview_url_support', 10, 2 );
Add an inline script that renders the global preview urls as Javascript constants
You'll need to add a new javascript file first using wp_enqueue_script and swap out 'your-customizer-script-handle' for your scripts handle.
function _nok_customizer_enqueue_scripts() {
global $kirki_section_preview_urls;
global $kirki_panel_preview_urls;
// Add variables inline
ob_start(); ?>
const kirkiSectionPreviewUrls = <?= json_encode( $kirki_section_preview_urls ) ?>;
const kirkiPanelPreviewUrls = <?= json_encode( $kirki_panel_preview_urls ) ?>;
<?php
wp_add_inline_script( 'your-customizer-script-handle', ob_get_clean(), 'before' );
}
add_action( 'customize_controls_enqueue_scripts', '_nok_customizer_enqueue_scripts' );
Add JS script source for swapping out preview URLs in the customizer
// ==== IF using typescript
declare var wp: any;
declare var kirkiSectionPreviewUrls: {
section_id: string,
preview_url: string
}[];
declare var kirkiPanelPreviewUrls: {
panel_id: string,
preview_url: string
}[];
// ====
wp.customize.bind( 'ready', function() {
// Loop preview urls for sections
kirkiSectionPreviewUrls.forEach( props => {
// Add event when section expanded
wp.customize.section( props.section_id ).expanded.bind( expanded => {
if( !expanded ) {
return;
}
wp.customize.previewer.previewUrl( props.preview_url )
} )
} );
// Loop preview urls for sections
kirkiPanelPreviewUrls.forEach( props => {
// Add event when section expanded
wp.customize.panel( props.panel_id ).expanded.bind( expanded => {
if( !expanded ) {
return;
}
wp.customize.previewer.previewUrl( props.preview_url )
} )
} );
} );