Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Custom styles/scripts are not loaded inside the preview iframe #38673

Closed
NenadObradovic opened this issue Feb 9, 2022 · 27 comments
Closed

Custom styles/scripts are not loaded inside the preview iframe #38673

NenadObradovic opened this issue Feb 9, 2022 · 27 comments
Labels
[Feature] Extensibility The ability to extend blocks or the editing experience [Focus] Blocks Adoption For issues that directly impact the ability to adopt features of Gutenberg.

Comments

@NenadObradovic
Copy link

Description

Hello guys,

Is there any issue with styles/scripts loading inside iframe (responsive editor)?

I enqueued 3 scripts with default function and that scripts are loaded fine initial but when I clicked on the tablet or mobile preview button, some scripts disappeared/did not load inside the head tag.

Please check the attachment and screenshots inside.

Thanks for your time.

Best regards,
Nenad Obradovic

Step-by-step reproduction instructions

I also tested with the default Twenty Twenty-One theme, I just enqueued Google Font link and I got the same issue

/**
 * Enqueue block editor script.
 *
 * @since Twenty Twenty-One 1.0
 *
 * @return void
 */
function twentytwentyone_block_editor_script() {
	wp_enqueue_style( 'google-fonts', 'https://fonts.googleapis.com/css?family=DM+Sans%3A400%2C500%2C600%2C700&subset=latin-ext&display=swap&ver=1.0.0' );
	wp_enqueue_script( 'twentytwentyone-editor', get_theme_file_uri( '/assets/js/editor.js' ), array( 'wp-blocks', 'wp-dom' ), wp_get_theme()->get( 'Version' ), true );
}

add_action( 'enqueue_block_editor_assets', 'twentytwentyone_block_editor_script' );

Screenshots, screen recording, code snippet

https://imgur.com/a/SPIPNvZ

Environment info

  • WordPress 5.9
  • Chrome
  • Window 11

Please confirm that you have searched existing issues in the repo.

Yes

Please confirm that you have tested with all plugins deactivated except Gutenberg.

Yes

@NenadObradovic
Copy link
Author

Hello again,

Unfortunately, you messed a lot of things with the new iframe editor preview, conditional you set are "crazy" and work only for your cases otherwise you blocked or removed any custom/external/3rd party scripts.

In this file src/components/iframe/index.js you made function styleSheetsCompat and that function has 2 problems:

  1. If we include any external CSS file that file will not be loaded because of this case
try {
	// May fail for external styles.
	// eslint-disable-next-line no-unused-expressions
	styleSheet.cssRules;
} catch ( e ) {
	return;
}

External files on Chrome browser will be blocked and cssRules result will be "Failed to read the 'cssRules' property from 'CSSStyleSheet': Cannot access rules at CSSStyleSheet" - https://stackoverflow.com/questions/48753691/cannot-access-cssrules-from-local-css-file-in-chrome-64/49160760#49160760

  1. The Second problem is 3rd party styles or theme custom styles. In the same file -> same function -> you can find this piece of code
const isMatch = Array.from( cssRules ).find(
	( { selectorText } ) =>
		selectorText &&
		( selectorText.includes( `.${ BODY_CLASS_NAME }` ) ||
			selectorText.includes( `.${ BLOCK_PREFIX }` ) )
);

where

const BODY_CLASS_NAME = 'editor-styles-wrapper';
const BLOCK_PREFIX = 'wp-block';

If we have for example 3rd party style - Swiper.css you will block it because inside that file there is no editor-styles-wrapper or wp-block classes as selector https://www.screencast.com/t/YxASDqA97u0 and that file will not be executed/loaded.

The same issue is with any custom theme or plugin styles that don't contain these classes. In my case, I have several CSS files which don't contain these classes and all files are blocked.

Could you please consider changing this logic or adding some hooks/JS variables so we can be able to extend/change or add our items?

Best regards,
Nenad Obradovic

@github-actions
Copy link

Help us move this issue forward. This issue is being marked stale since it has no activity after 15 days of requesting more information. Please add info requested so we can help move the issue forward. Note: The triage policy is to close stale issues that need more info and no response after 2 weeks.

@github-actions github-actions bot added the [Status] Stale Gives the original author opportunity to update before closing. Can be reopened as needed. label Apr 15, 2022
@ALJ
Copy link

ALJ commented Apr 15, 2022

I tried the reproduction instructions (with https://fonts.googleapis.com/css?family=DM+Sans) and I see the same problem as reported above. I'm using WordPress@5.9.3, no Gutenberg plugin. The DM Sans font successfully loaded and applied in Desktop preview mode, but was missing in either of the two iframed previews.

@NenadObradovic there are other inconsistencies between the iframe preview modes and desktop preview, including this one I reported. Probably something the team will look at when building out the iframe editor more in the future.

@NenadObradovic
Copy link
Author

Hello @ALJ ,

I hope someone will check this issue :) In the meantime I fixed it with a not so good solution, but I can't wait for an answer :)

document.addEventListener(
	'DOMContentLoaded',
	function () {
		gutenbergResponsiveIframe.init();
	}
);

const gutenbergResponsiveIframe = {
	listenerTriggered: false,
	init: function () {
		const isEditorFrameLoaded = setInterval(
			() =>
			{
                                // Check is the current page Gutenberg editor or Full Site Editor
				const editorPage = document.querySelector( '.edit-post-visual-editor__content-area' ) || document.querySelector( '.edit-site-visual-editor' );

				if ( editorPage ) {
					clearInterval( isEditorFrameLoaded );

					gutenbergResponsiveIframe.listenerChanges( editorPage );
				}
			},
			500
		);
	},
	listenerChanges: function ( editorPage ) {

		const observer = new MutationObserver(
			() =>
			{

				if ( ! gutenbergResponsiveIframe.listenerTriggered ) {
					const editorFrame = editorPage.querySelector( 'iframe[name="editor-canvas"]' );

					if ( editorFrame ) {
						gutenbergResponsiveIframe.includeScripts( editorFrame.contentDocument );

						// Prevent function to include scripts only once for the full site editor
						if ( editorPage.classList.contains( 'edit-site-visual-editor' ) ) {
							gutenbergResponsiveIframe.listenerTriggered = true;
						}
					}
				}
			}
		);

		observer.observe(
			editorPage,
			{
				subtree: true,
				childList: true,
			},
		);
	},
	includeScripts: function ( $document ) {
		if ( $document ) {
			const $head  = $document.querySelector( 'head' );
			const styles = [];

			if ( typeof window.additionalIframeScripts === 'object' ) {
				for ( const [key, value] of Object.entries( window.additionalIframeScripts ) ) {
					styles.push( value );
				}
			}

			if ( styles.length > 0 ) {
				styles.forEach(
					styleURL =>
					{
						const link = $document.createElement( 'link' );

						link.setAttribute( 'href', styleURL );
						link.setAttribute( 'rel', 'stylesheet' );
						link.setAttribute( 'type', 'text/css' );

						$head.insertBefore( link, $head.firstChild );
					}
				);
			}
		}
	},
}

and inside functions.php I just localized the main block script for example

if ( is_admin() ) {
	wp_localize_script(
		'wp-block-editor',
		'additionalIframeScripts',
		array(
			'googleFonts' => esc_url_raw( 'https://fonts.googleapis.com/css?family=DM+Sans' ),
			'swiper'           => plugin_dir_url( __FILE__ ) ) . '/assets/plugins/swiper.min.css',
		)
	);
}

Best regards,
Nenad Obradovic

@github-actions github-actions bot removed the [Status] Stale Gives the original author opportunity to update before closing. Can be reopened as needed. label Apr 16, 2022
@talldan talldan added [Feature] Extensibility The ability to extend blocks or the editing experience Needs Testing Needs further testing to be confirmed. and removed [Status] Needs More Info Follow-up required in order to be actionable. labels Apr 19, 2022
@StasNemy
Copy link

I've added class "wp-block" to my custom style, and now it's work. Thank you!

@wpsoul
Copy link

wpsoul commented Jul 14, 2022

I want to add that problem becomes more and more annoying because Wordpress has FSE priority in all updates. But still, we have no hooks, no functions to inject something inside FSE iframe.

For example, I also found that all hooks for Plugin for Sidebar is not working in FSE. And We also can't inject something in top toolbar of FSE, because it's placed inside iframe. Currently, I didn't find anything in documentation to extend FSE pages

@github-actions github-actions bot added the [Status] Stale Gives the original author opportunity to update before closing. Can be reopened as needed. label Aug 25, 2022
@wpsoul
Copy link

wpsoul commented Sep 13, 2022

This issue is far more than just problem of assets. I found that all scripts which we add in editor (no matter how, with enqueue_block_editor_assets or with importing libraries in blocks) have no access to iframe because they are loaded outside iframe.

Scripts which will not work properly in Mobile preview and FSE:

  1. breakpoints for sliders, carousels - because scripts track general window and not iframe
  2. Custom drag and drop
  3. Any scroll tracking

We need a solution to load scripts in iframe. Currently, only styles are loaded there

@Mamaduka
Copy link
Member

The ability to load custom scripts in the iframed editor should be resolved via #37466.

@wpsoul the Site Editor exports it's own PluginSidebar, PluginSidebarMoreMenuItem and PluginMoreMenuItem components.

import { PluginSidebar, PluginSidebarMoreMenuItem, PluginMoreMenuItem } from '@wordpress/edit-site';

There's also a dev note on how libraries used by blocks can adapt to iframed editors - https://make.wordpress.org/core/2021/06/29/blocks-in-an-iframed-template-editor/.

@Mamaduka Mamaduka removed Needs Testing Needs further testing to be confirmed. [Status] Stale Gives the original author opportunity to update before closing. Can be reopened as needed. labels Sep 13, 2022
@wpsoul
Copy link

wpsoul commented Sep 13, 2022

@Mamaduka Plugin Sidebar was fixed already. It's just missing documentation information.

My message is about scripts in iframe.

https://make.wordpress.org/core/2021/06/29/blocks-in-an-iframed-template-editor/

This is not working. Problem is not in getting document, body, etc, I use Ref there. Problem is that many libraries require to load them in iframe to track iframe's data like breakpoints, scroll position, etc

#37466 this is about styles, I can't see anything related to scripts. Styles already loaded in iframe so they have no problem

@mark-c-woodard
Copy link

Oustside of the work around shown by @NenadObradovic earlier, has anyone arrived at the "official" way to include external styles such as google fonts in the iframe preview?

It seems like there are two methods that are meant for getting styles into the editor. Using the add_editor_style function and enqueueing the style sheet in the enqueue_block_editor_assets hook.

As discussed here, enqueue_block_editor_assets won't work for something like google fonts because the style needs to have a wp-blocks selector to get added to the iframe preview.

#40469 indicates that add_editor_style should work, but it's super unclear from that function's documentation what it's intended to do. I thought that it was just for the old tiny mce editor, but apparently it's also used for the iframe preview? In any case when I've tried to use it to load google fonts it hasn't in the iframe preview.

@Mamaduka mentioned #37466 but it's still open. So I guess we can't use that method yet..

I might just be missing something obvious here but.. How am I suppose to get an external style sheet to load in the block editor iframe preview?

@dingo-d
Copy link
Member

dingo-d commented Mar 19, 2023

Is there going to be a way that we can enqueue custom styles and scripts that will work in the preview iframe? It's especially annoying when patterns don't look like in the editor...

@sitestudioapp
Copy link

I'm surprised that this wasn't thought of from the beginning. I am developing an FSE theme that uses the UIKit framework and ACF Blocks. This limitation has stopped me dead in my tracks. Essentially everything is broken without the ability to load external/3rd party JS libraries inside the editor iframe. I was not expecting that. I will have to revert to a classic theme. Disappointing.

@sitestudioapp
Copy link

I want to add that problem becomes more and more annoying because Wordpress has FSE priority in all updates. But still, we have no hooks, no functions to inject something inside FSE iframe.

For example, I also found that all hooks for Plugin for Sidebar is not working in FSE. And We also can't inject something in top toolbar of FSE, because it's placed inside iframe. Currently, I didn't find anything in documentation to extend FSE pages

The lack of urgency around fixing this issue/limitation is infuriating. They want us to develop for FSE but how exactly are we supposed to do that? It's essentially unusable.

@landwire
Copy link

Could someone clearly say if and how I can add CSS and JS files to the FSE iframe?
Is that possible by now?

@dingo-d
Copy link
Member

dingo-d commented May 21, 2023

@annezazu This issue is the one I meant in #35852

@annezazu annezazu added the [Focus] Blocks Adoption For issues that directly impact the ability to adopt features of Gutenberg. label May 22, 2023
@annezazu
Copy link
Contributor

Just a quick note saying that I've added the blocks adoption label here to better track the impact of this problem!

@porg
Copy link

porg commented Jul 3, 2023

This affects also the plugin JVM Gutenberg Rich Text IconsBlock Editor shows whitespace instead of inline icon due to CSS not being loaded properly within the Editor environment:

WordPress JVM Gutenberg Rich Text Icons - Block Editor shows whitespace instead of inline icon

@sitestudioapp
Copy link

sitestudioapp commented Jul 5, 2023

Could someone clearly say if and how I can add CSS and JS files to the FSE iframe? Is that possible by now?

That is all I'm looking for. Can we load JavaScript in the FSE iframe? A simple yes or no would be great.

It's been a year and six months. SMH.

@wpsoul
Copy link

wpsoul commented Jul 5, 2023

That is all I'm looking for. Can we load JavaScript in the FSE iframe?

You can't load currently. I believe that next WP update will introduce new action which can be used if you want to load something in iframe

@ellatrix
Copy link
Member

ellatrix commented Jul 6, 2023

@sitestudioapp Only blocks could previously add script handles to load into the iframe. From WP 6.3, you can use the enqueue_block_assets action to load any asset into the iframe that is also loaded on the front-end. See #49655.

@wpsoul
Copy link

wpsoul commented Jul 14, 2023

@ellatrix Is any documentation about style and script loading?

I see that I have a lot of "... was added to the iframe incorrectly. Please use block.json or enqueue_block_assets to add styles to the iframe" I tried both, block.json and enqueue_block_assets and styles are not working and I still see this message

@ellatrix
Copy link
Member

This has been fixed since #49655 (which is in WP 6.3). There's more information in this post: https://make.wordpress.org/core/2023/07/18/miscellaneous-editor-changes-in-wordpress-6-3/#post-editor-iframed

If there's any remaining issues, let's open new issues and feel free to ping me. :)

@ellatrix
Copy link
Member

Also some script issues have been fixed in #52405 (also in WP 6.3)

@porg
Copy link

porg commented Aug 17, 2023

In this comment I had reported that JVM Gutenberg Rich Text Icons did not show the icon inline in the Block Editor:

  • ✅ This now works fine under WordPress 6.3 , Gutenberg 16.4.0, JVM Gutenberg Rich Text Icons 1.2.3

@dingo-d
Copy link
Member

dingo-d commented Aug 17, 2023

Can confirm the previews are no longer broken for Eightshift Dev Kit as well 👍🏼

@artypineda
Copy link

artypineda commented Nov 20, 2023

Ran into this issue today and realize Wordpress 6.3 Post editor iframed requires u to add the 'enqueue_block_assets' api call vs the enqueue_block_editor_assets – or use block.json

if ( is_admin() ) { add_action( 'enqueue_block_assets', 'myFunc'); function myFunc(){ // things } }

@annezazu
Copy link
Contributor

In case folks go looking for this issue, here's the documentation on the topic: https://developer.wordpress.org/block-editor/how-to-guides/enqueueing-assets-in-the-editor/

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
[Feature] Extensibility The ability to extend blocks or the editing experience [Focus] Blocks Adoption For issues that directly impact the ability to adopt features of Gutenberg.
Projects
None yet
Development

No branches or pull requests