I'm having quite a lot of trouble trying to hook an event listener to WordPress's Gutenberg Editor. There is very little documentation on this, and ChatGPT doesn't give very good answers too. What I want to do is to detect whenever a user makes changes to the post content, then scanning the content to convert all --
into —
(an em dash).
Ideally, it only fires when a user types a -, and it checks forward and backward to see if there is another -, and if there is, it replaces both. Here is what I have at the moment, and it just scans the entire post to replace all --
with —
, and even this is not working.
(function(wp) {
// Wait for the editor to initialize
wp.domReady(function() {
wp.data.subscribe(function() {
var editor = wp.data.select('core/editor');
var core = wp.data.select('core');
if (editor && core.getPostType(editor.getEditedPostAttribute('type'))) {
var postContent = editor.getEditedPostContent();
var modifiedContent = postContent.replace(/(?<=\s)--(?=\s)/g, '—');
wp.data.dispatch('core/editor').editPost({ content: modifiedContent });
}
});
});
})(window.wp);
The problem is that subscribe()
fires whenever the post content is changed, and editPost()
changes the content, which causes an infinite recursion and a Maximum Call Stack Exceeded error (i.e. stack overflow).
Even when I try to add a flag to check this, the same stack overflow error happens:
(function(wp) {
// Wait for the editor to initialize
wp.domReady(function() {
var ignoreSubscribe = false;
wp.data.subscribe(function() {
// If this is true, ignore this subscribe call.
if(ignoreSubscribe) {
ignoreSubscribe = false;
return;
}
var editor = wp.data.select('core/editor');
var core = wp.data.select('core');
if (editor && core.getPostType(editor.getEditedPostAttribute('type'))) {
var postContent = editor.getEditedPostContent();
var modifiedContent = postContent.replace(/(?<=\s)--(?=\s)/g, '—');
wp.data.dispatch('core/editor').editPost({ content: modifiedContent });
ignoreSubscribe = true;
}
});
});
})(window.wp);
I don't know what is wrong here, so some help will be greatly appreciated. Also, if you can help me figure out how to only detect the event when a user types a -
and only scan that character, that will be even better.
Preferrably, I would like to do this without having to set up React too, but I'm not sure if this is possible.