How to access Gutenberg Block Text-Selections / Text-Formats and other Mysteries

Gutenberg Documentation

While Gutenberg is becoming more stable with each release, documentation is only growing slowly. Many parts are outdated, superficial or completely undocumented.

For more complex or individual requirements you have to dive deep. Gladly the browser console allows you to easily checkout what is driving the editor.

Open your browser developer console and start exploring wp. / wp.data. / wp.api. .

What each function does, can be read in the Block Editor Handbook.

This is all nice, but how do I actually use these?

At this stage of the development, many things are still changing. So using the API direcly is mostly a matter of reading the documentation, checking the implementation within the core codebase and using trial & error.

Some mysteries have already been solved by others or they provide the right lead. Check Stack Overflow and especially the WordPress Development area for solutions.

Its still like a treasure hunt most of the time LOL Perfect for those that love to solve puzzles :)
Just my cup of tea or better coffee!

Do I need to learn React?

It surely is a benefit, as the whole Gutenberg Editor is build upon React. But for simple tweaks its not a must. But once you start going deeper, you will see the benefit and will learn to love React yourself.

What about ES6, ESNext vs ES5?

ECMAScript 6 is also known as ES6 and ECMAScript 2015.

ES5 is on its way out and ES6 is supported on all modern browsers since end of 2016.

Older browsers can be supported using a polyfill, that augments those browsers and allows them to use the new ES6 features.

React and also Gutenberg builds on the new Javascript functionality, but ES5 examples can also be found.

You can also easily compile ES6 to ES5 using Babel in your development environment or online.

Solving Mysteries!

I will be using the following sections to highlight some things that puzzled me and might help others to get a grip on things. I will be extending this, as I discover or solve more Gutenberg mysteries :)

I will keep the example code in ES5 for now, as that is the easiest way to start tinkering. I will also focus on things that can be used from external code. Most of the small code snippets are connected to each other.

Mystery 1: Text Selection & Formats

These little code snippets are all connected and showcase how to retrieve a selection from a block and change or remove a text format.

Wait for domReady

Make sure the editor has loaded and the DOM can be accessed.

  1. wp.domReady(function() {
  2.   // Your code here
  3. });

Access the active block

  1. wp.data.select('core/block-editor').getSelectedBlock();
  2.  
  3. // Block ID - reference
  4. var blockUID = wp.data.select('core/block-editor').getSelectedBlock().clientId;

Access active block selection

  1. // Start of selection
  2. var selectionStart = wp.data.select('core/block-editor').getSelectionStart();
  3.  
  4. // End of selection
  5. var selectionEnd = wp.data.select('core/block-editor').getSelectionEnd();

The actual offset can be found within the OBJECT.

  1. wp.data.select('core/block-editor').getSelectionEnd().offset;

Get block HTML content

  1. // Get block
  2. var block = wp.data.select('core/block-editor').getSelectedBlock();
  3.  
  4. // Attributes
  5. var blockAttributes = block.attributes;
  6.  
  7. // Content
  8. var blockContent = block.attributes.content;

Create Richtext object

  1.  var richTextContent = wp.richText.create(
  2. {
  3.   blockContent
  4. });

Get active text formats

  1. var activeTextFormats = blockContent.formats;

Check if format is active for selected text

This function is documented, but wont work from the outside that easily. This normally checks the isActive state of the component. Here a small workaround using Lodash.

  1. var formatToCheck = "core/text-color";
  2. var formatToCheckisActive = true;
  3.  
  4. if(_.find(value.formats[selectionStart], { type: formatToCheck }))
  5. {
  6.   formatToCheckisActive = false;                       
  7. }

Formats are saved within the Richtext object under formats and the text formats are stored within arrays that correspond to the actual index + range of the selection. So if a text-color has been applied from index 4 to 8, you will find the corresponding array for that.

Works well and does the trick for now. Here the output from the developer console, showing the arrays for an 18 character long paragraph:

  1. formats: Array(18)
  2. 0: Array(1)
  3. 0: {type: "core/bold"}
  4. length: 1
  5. __proto__: Array(0)
  6. 1: Array(1)
  7. 0: {type: "core/bold"}
  8. length: 1
  9. __proto__: Array(0)
  10. 2: [{}]
  11. 3: [{}]
  12. 4: [{}]
  13. 14: [{}]
  14. 15: [{}]
  15. 16: [{}]
  16. 17: [{}]
  17. length: 18
  18. __proto__: Array(0)

Apply a new text format to selection

I am using the core/text-color format with applyFormat as an example, can be anything.

  1. richTextContent = wp.richText.applyFormat(
  2.     richTextContent,
  3.     { type: 'core/text-color',
  4.         attributes:{class: "some-color-class"}
  5.     },
  6.     selectionStart,
  7.     selectionEnd
  8. );

Insert text at start of selection

insertObject can insert content at the start of the selection, with the rest between selectionStart and selectionEnd getting removed. There is also insert, which allows you to simply add a HTML string into the Richtext value.

  1. richTextContent = wp.richText.insertObject(
  2.     richTextContent,  
  3.     'core/text-color',
  4.     selectionStart,
  5.     selectionEnd
  6. );     

Remove text format from selection

removeFormat allows you to remove a text format from the current selection.

  1. richTextContent = wp.richText.removeFormat(
  2.     richTextContent,  
  3.     'core/text-color',
  4.     selectionStart,
  5.     selectionEnd
  6. );                                     

Would be nice to use toggleFormat here, but that works within native components and not by selection index as the two calls above.

Convert Richtext value to HTML

  1. var prepNewHTML = wp.richText.toHTMLString(
  2.     {richTextContent }
  3. );

Replace current block content

  1. wp.data.dispatch( 'core/block-editor' ).updateBlock( blockUID, {
  2.     attributes: {
  3.       content: prepNewHTML
  4.     }
  5. } );

Whats Next?

I will add some more Gutenberg examples in the future.

Enjoy coding and keep tinkering :)

Alex

I am a full-stack developer. I love programming,  design and know my way around server architecture as well.  I would never feel complete, with one of these missing. I have a broad range of interests, that’s why I constantly dive into new technologies and expand my knowledge where ever required. Technologies are evolving fast and I enjoy using the latest. Apart from that, I am a peace loving guy who tries to have people around him that think the same.  I truly believe in the principle: “If you help someone, someone will help you, when you need it."

Recent Posts

B&B / Hotel Booking Solutions for WordPress | 2024

BOOKING SOLUTIONS 202x This is my take on a subset of booking, appointment, PMS or… Read More

2 weeks ago

WordPress Cron + WP-CLI + Ntfy

THE GOAL Create a system cron for WordPress, that is accessible and can be easily… Read More

2 months ago

2024 is here and now :)

2024, what's cooking? Slowly getting into the 2024 spirit. 3 projects coming to a close… Read More

3 months ago

2023 ends and whats next !

Short look back at 2023 This has been a busy and interesting year. I am… Read More

4 months ago

cubicFUSION Grid Tweaker – Elementor Grid made easy.

Elementor Pro provides grid containers as an experimental feature. The options provided are limited, when… Read More

5 months ago

Archaeology Travel Booth – Travel Innovation Summit 2023

Archaeology Travel is an online travel guide for people who enjoy exploring the world’s pasts.… Read More

6 months ago