WordPress.org

Make WordPress Core

Opened 14 months ago

Last modified 6 weeks ago

#35760 new enhancement

Provide API for TinyMCE editor to be dynamically instantiated via JS

Reported by: westonruter Owned by:
Milestone: 4.8 Priority: normal
Severity: normal Version:
Component: Editor Keywords:
Focuses: javascript Cc:

Description

There is apparently no easy way currently to bootstrap the TinyMCE content editor dynamically via JS, that is to initialize one or more editors after page load. There is a PHP API to embed an editor into a page statically via wp_editor( $content, $editor_id, $settings ) but this does not work with JS (see #26295).

It would be great if there was a proper JS API for spinning up new TinyMCE editors with all of the WordPress extensions and plugins. For example: var editor = new wp.Editor( container, settings );

Ideally the required assets for the editor could be lazy-loaded instead of being loaded all up-front with the initial request.

With an API for initializing an editor with JS, it would then be greatly simplified to do things like:

  • Create a Customizer control for a rich text editor.
  • Add rich text editing to a Text widget (#35243)
  • General content in the Customizer (#34923)
  • General frontend editing.

For more background, see conversation: https://wordpress.slack.com/archives/core/p1454615457001581

Attachments (1)

black-studio-tinymce-widget.png (369.3 KB) - added by westonruter 3 months ago.

Download all attachments as: .zip

Change History (12)

This ticket was mentioned in Slack in #core-customize by westonruter. View the logs.


7 months ago

This ticket was mentioned in Slack in #core-editor by westonruter. View the logs.


7 months ago

#3 @westonruter
3 months ago

  • Milestone changed from Awaiting Review to Future Release

@azaozz @iseulde thoughts on this?

#4 follow-up: @azaozz
3 months ago

Yeah, it's a good idea to be able to (lazy) load and initialize the editor from JS. The current wp_editor() is quite a few years old, and will need to be rewritten to support that.

There are three main components for TinyMCE: the core or the concatenated core + plugins, the translation, and the init / settings. The last two will have to be generated from PHP so a "pure" JS solution is not possible.

There is also the wplink modal (HTML) that will probably need refactoring to make is easily loadable from JS.

Create a Customizer control for a rich text editor.

I'm not sure it will be possible to use the current TinyMCE in the customizer sidebar. There is simply not enough space in there. Also the user experience will be quite bad, trying to "preview" something in the sidebar? Thinking it will be much better after the customizer UI is fixed/updated and (hopefully) moves away from the current layout.

There is also another option: to make a completely different function/mini-API for loading the editor only for use in JS. The translated strings will still need to be outputted from PHP, but the editor init object can be filterable only from JS. This will not contain any settings from existing plugins, but will be a better option for making editor instances with different configuration, minimal UI, etc.

#5 in reply to: ↑ 4 ; follow-up: @westonruter
3 months ago

Replying to azaozz:

I'm not sure it will be possible to use the current TinyMCE in the customizer sidebar. There is simply not enough space in there. Also the user experience will be quite bad, trying to "preview" something in the sidebar? Thinking it will be much better after the customizer UI is fixed/updated and (hopefully) moves away from the current layout.

I agree. However, I think that a TinyMCE control could be a suitable drop-in replacement for the current textarea in the sidebar *if* the controls were very stripped-down to just have the most essential buttons (like bold, italics, and link). Otherwise the editor would indeed need to be located somewhere else. The Customize Posts plugin addresses this by sliding the TinyMCE editor in from the bottom as a separate pane: https://www.youtube.com/watch?v=QJsEl0gd7dk

One other option would be to consider switching to a “wide widget” configuration for the Text widget and that would allow for more horizontal space, although the widget would expand over the preview (which can block previewing of the element you want to see). This is what can be seen in the Black Studio TinyMCE Widget: black-studio-tinymce-widget.png

The other option to move toward is inline editing within the preview itself. This needs to be explored regardless, but it doesn't really help solve the space constraint problem since text widgets would commonly appear in a theme sidebar location that is no wider than the customizer controls are, so there wouldn't be any extra room for the toolbars.

#6 in reply to: ↑ 5 @azaozz
3 months ago

Replying to westonruter:

The other option to move toward is inline editing within the preview itself. This needs to be explored regardless, but it doesn't really help solve the space constraint problem since text widgets would commonly appear in a theme sidebar location that is no wider than the customizer controls are, so there wouldn't be any extra room for the toolbars.

Thinking this is the best option. It's true the space in the widget may be small/narrow, but that is exactly how it will look after saving. Then if the editor is in inline mode, it will be the "perfect" preview (or rather "no preview needed" as the perception is that the "real thing" is being changed, not that there is an editor and separate preview) :)

There are couple of UI options when the editor is inline even when the actual edited area is quite small. A "pop-out" toolbar or a side or inline toolbar, etc. This is somewhat easier as the toolbar can be wider than the edited area without making it look odd.

Second best imho is the "wide widget" from the above screenshot, if it doesn't cover the actual widget area. Then the editor would not need to be WYSIWYG and can probably have more streamlined UI / toolbars.

TinyMCE control could be a suitable drop-in replacement for the current textarea in the sidebar *if* the controls were very stripped-down to just have the most essential buttons (like bold, italics, and link).

Yeah, that would work for places that need very "slimmed down" editor UI and/or support only few HTML tags. Then the editor configuration will have to be separate/JS only, as running the default PHP filters will add a lot of stuff from plugins that is intended for the Edit Post screen.

Last edited 3 months ago by azaozz (previous) (diff)

#7 @celloexpressions
3 months ago

For most places that a full editor makes sense (in terms of what it does on the front end), inline editing would be the best route for UX I think. Combining that with something like the customize sidebar becomes useful when looking to edit things like custom post meta, taxonomies, etc., as well as for providing a unified place for publishing-type options. I recall working with the "teeny" mode in the past; a modern take on that could be useful for things like widgets (in a sidebar/admin or inline depending on context).

In general, making the editor component more modular and making it instantiable with JS makes a lot of sense to me.

This ticket was mentioned in Slack in #core-customize by westonruter. View the logs.


2 months ago

#9 @westonruter
2 months ago

  • Milestone changed from Future Release to 4.8

#10 @azaozz
2 months ago

Been thinking what would work best. As this is going to be "pure JS" way to load the needed parts for the editor, skipping most (all?) PHP filters that are currently in class-wp-editor.php seems better. This will avoid interference from current plugins.

Instead of the PHP filters, we can fire custom jQuery events before initializing each editor instance, passing the settings. This will allow plugins to modify them similarly to using the PHP filters. To make it easier for the plugins, we would need to add another PHP filter or action to trigger loading of these scripts.

The plan is to make another function similar to wp_editor() which will either output the script tags or return the src and scripts as strings so they can be lazy-loaded (we still have to output the translations and the settings from PHP). Then on the JS side will have a small function to load the scripts and CSS (if not already loaded) then initialize the editor firing the above events.

This ticket was mentioned in Slack in #core-customize by westonruter. View the logs.


6 weeks ago

Note: See TracTickets for help on using tickets.