Integrate tinyMCE into a WordPress widget

Digg Muti Delicious

So, the nat­ive WordPress text wid­get is great, right? It allows users to insert vir­tu­ally any form of con­tent into a wid­get, provided they either want plain text or know a bit of HTML. The fact that this wid­get can be used in mul­tiple instances is also awe­some. Recently, I’ve needed to provide a bit more con­trol though. Hence, my integ­ra­tion of tinyMCE.

Before I start, this tutorial assumes that you have a wid­get up and run­ning (multi-​​instance or a con­ven­tional single instance wid­get) that has a text area which will be replaced with a tinyMCE editor. This tutorial is only about the integration. In my research on this topic, I came across a sup­port query where a user was exper­i­en­cing the same issue I was hav­ing: the con­tent of the tinyMCE replaced text area was not sav­ing. After a bit of test­ing, I found the solu­tion.

1. Make sure you have a folder of tinyMCE in your theme or wherever your wid­get code is loc­ated. The loc­a­tion isn’t import­ant, it just helps to keep everything per­tain­ing to the wid­get in the same place.

2. Write a PHP func­tion to ini­tial­ise tinyMCE. This func­tion will include the tinyMCE Javascript file, as well as run the tinyMCE.init() func­tion to setup our editor blocks.

3. Add an action to the admin_​print_​scripts on the widgets.php page. This action will run the func­tion declared in step 2.

4. Customise the editor instance (which theme, which but­tons, etc) to suit your widget’s require­ments. Support on this comes bundled with tinyMCE in the form of example files, and is also avail­able via the sup­port doc­u­ments on the tinyMCE website.

And that’s it, folks. :) I can post up snip­pets of the code for each step in a bit, if it would help. :) The above pro­cess also replaces all tex­tareas on the wid­gets page, with a tinyMCE editor.

Updated

This is what the code struc­ture looks like:

function NAME_OF_INIT_FUNCTION()
{
echo 'INSERT YOUR tinyMCE JAVASCRIPT HERE... CALL THE FILE AND RUN THE init FUNCTION';
}

add_action(‘admin_print_scripts-widgets.php’, ‘NAME_​OF_​INIT_​FUNCTION’);

Other resources on the topic

Use TinyMCE in your WordPress 2.8 Plugin > Brolly

Update– This code was pos­ted in the com­ments by Michael. It has been moved to the post for consistency.

File Paths
define('TMWD_FILE_PATH', dirname(__FILE__), true);
define('TMWD_DIR_NAME', basename(TMWD_FILE_PATH), true);
define('SITE_URL', get_option('siteurl'), true);
#> Plugin Folder and URL to folder
define('TMWD_FOLDER', dirname(plugin_basename(__FILE__)), true);
define('TMWD_URL', SITE_URL.'/wp-content/plugins/' . TMWD_FOLDER, true);
#> hooks
add_action( 'widgets_init', 'tmwd_init' );
add_action('admin_head-widgets.php', 'tinymce');

#> add tinyMCE javas cript to header
func tion tinymce() {
echo ‘<script type=“text/javascript” src=”/jscripts/tiny_mce/tiny_mce.js”>’;
}

#> register wid get
func tion tmwd_​init() {
register_​widget( ‘HTMLContent_​Widget’ );
}

#> Widget Class
class HTMLContent_​Widget extends WP_​Widget {

#> con struct
func tion HTMLContent_​Widget() {
#> set tings
$widget_​ops = array( ‘class name’ => ‘htm l con tent’, ‘descrip tion’ => __(‘Widget to add HTML con tent to Widget Area.’, ‘htm l con tent’) );
$control_​ops = array( ‘width’ => 600, ‘height’ => 350, ‘id_​base’ => ‘htmlcontent-​​widget’ );

#> cre ate wid get
$this->WP_Widget( ‘htmlcontent-​​widget’, __(‘HTML Content Widget’, ‘htm l con tent’), $widget_​ops, $control_​ops );
}

#> tem plate dis play
func tion wid get( $args, $instance ) {
extract( $args );
#> html con tent
$con tent = $instance[’content’];
echo $before_​widget;
if ( $con tent ) { printf( ‘%1$s’, $con tent ); }
echo $after_​widget;
}

#> save wid get con tents
func tion update( $new_​instance, $old_​instance ) {
$instance = $old_​instance;
$instance[’content’] = $new_instance[’content’];
return $instance;
}

#> dis play wid get in wid gets screen
func tion form( $instance ) {

#> Defaults
$defaults = array( ‘con tent’ => __(‘TODO :: ADD Your HTML here.’, ‘htm l con tent’));
$instance = wp_​parse_​args( (array) $instance, $defaults );
#> TinyMCE Setup Instances
?>

tinyMCE.init({
mode : “tex tareas”,
theme : “advanced”,
editor_selector:“get_field_id( ‘con tent’ ); ?>”,
plu gins : “safari, pagebreak, style, layer, table, save, advhr, advimage, advlink, emotions, iespell, inlinepopups, insertdatetime, preview, media, searchreplace, print, contextmenu, paste, directionality, fullscreen, noneditable, visualchars, nonbreaking, xhtmlxtras, template”,
/​/​ Theme options
theme_​advanced_​buttons1 : “save,newdocument, | ,bold, italic, underline, strikethrough, |, justifyleft, justifycenter, justifyright, justifyfull, styleselect, formatselect, fontselect, fontsizeselect”,
theme_​advanced_​buttons2 : “cut, copy, paste, pastetext, pasteword, |, search, replace, |, bullist, numlist, |, outdent, indent, blockquote, |, undo, redo, |, link, unlink, anchor, image, cleanup, help, code, |, insertdate, inserttime, preview, |, forecolor, backcolor”,
theme_​advanced_​buttons3 : “tablecontrols, |, hr, removeformat, visualaid, |, sub, sup, |, charmap, emotions, iespell, media, advhr, |, print, |, ltr, rtl, |, fullscreen”,
theme_​advanced_​buttons4 : “insertlayer, moveforward, movebackward, absolute, |, styleprops, |, cite, abbr, acronym, del, ins, attribs, |, visualchars, nonbreaking, template, pagebreak”,
theme_​advanced_​toolbar_​location : “top”,
theme_​advanced_​toolbar_​align : “left”,
theme_​advanced_​statusbar_​location : “bot tom”,
theme_​advanced_​resizing : true,
setup : function(ed) {
ed.onChange.add(function(ed) {
tinyMCE.triggerSave();
});
}
});

<tex tarea name=“get_field_name( ‘con tent’ ); ?>” class=“get_field_id( ‘con tent’ ); ?>” id=“get_field_id( ‘con­tent’ ); ?>”>
end class
?>

Thanks for this code, Michael.

Related Posts

31 Comments

  1. Posted 12th June, 2009 at 1:09 am (449 days ago)

    more detailed snip­pets would be great if you can give them :)

    • Posted 12th June, 2009 at 7:32 am (448 days ago) in reply to Jennifer

      Hey Jennifer. :)

      Thanks for your comment.

      No prob­lem. I’m going to set up syn­tax high­light­ing as well, which will cer­tainly help visu­ally. :)

      Cheers,
      Matt.

  2. Posted 12th June, 2009 at 7:40 am (448 days ago)

    Actually, I think I figured out how to imple­ment what you have there. Unfortunately, it’s still not work­ing :( If I view source, I can see the tinymce code in the header of the wid­gets page (so it’s call­ing my tinymce init func­tion in my widgets/​plugin), but it still isn’t apply­ing the tinymce to my tex­tarea in my wid­get. I can’t fig­ure out what else I’m miss­ing to make it work…

    • Posted 12th June, 2009 at 7:55 am (448 days ago) in reply to Jennifer

      Are you using the WordPress integ­rated tinyMCE? I’m using a ded­ic­ated copy in my theme folder (where the wid­get code is).

      Do you have Firebug installed? If so, does it return any error messages?

      Oh, and is the path to the tinyMCE files an abso­lute path? I cre­ate this path using the get_​bloginfo() function.

  3. Posted 12th June, 2009 at 3:50 pm (448 days ago)

    Ok — so this is how far I’ve got­ten: I was link­ing to the word­press bundled tinymce. The ori­ginal prob­lem was that I had wanted a simple editor — but for some reason only the advanced editor would dis­play. So it shows up in the wid­get, but when I go to save my wid­get, it doesn’t save the text changes, and then reverts the tex­tarea back to the non-​​tinymce view. I’m begin­ning to won­der if this is an issue with the new wid­get class in 2.8 because that just seems par­tic­u­larly odd.

    • Posted 12th June, 2009 at 4:47 pm (448 days ago) in reply to Jennifer

      I ran into the same issues.

      To have con­trol over the editor dis­played in the wid­gets, I decided to go with a fresh non-​​Wordpress instance of the tinyMCE code. This afforded me the con­trol and sim­pli­fic­a­tion of the editor that I sought.

      Due to the integ­ra­tion of the above method I chose, this also resolved the issues of pre­serving the text editor and apply­ing the changes made when using the editor.

      I hope this helps, Jen. Let me know if you require fur­ther assist­ance. :)

  4. Posted 12th June, 2009 at 6:17 pm (448 days ago)

    Ok — I put the tiny­myce folder in folder with my plu­gin, linked to that instead, the editor shows up on the wid­get, but when I go to save the changes/​widget — it doesn’t save the tex­tarea con­tent (saves the other fields I hap­pen to have in the wid­get — just not the tex­tarea field with the tinymce) and again, after that save, the tex­tarea reverts back to the non-​​tinymce view… :(

  5. Posted 12th June, 2009 at 6:20 pm (448 days ago)

    Sorry to spam your thread :) The other weird thing… after it changes to the non-​​tinymce view, any changes I make after that point in that tex­tarea ARE saved… it just doesn’t want to save the tex­tarea con­tent with the tinymce view “on”…

    • Posted 12th June, 2009 at 6:33 pm (448 days ago) in reply to Jennifer

      It’s cool. :)

      I’m not sure about the first issue you’ve men­tioned… about the con­tent not sav­ing when edited with the editor. The only thing I can think of off the top of my head is the tinyMCE “mode” option. I have this set to “tex­tareas”. Do you have this as well?

      I have also exper­i­enced the issue of the editor not com­ing back after the first save. I’ll be look­ing into this and will post if I find a solu­tion. :)

  6. Posted 12th June, 2009 at 6:43 pm (448 days ago)

    Yeah — this is what my tinymce init func­tion looks like:
    tinyMCE.init({
    mode : “tex­tareas”,
    theme : “simple“
    });

    I am using the new 2.8 wid­get class — there was a tutorial here — so not sure if that’s some­how related to the prob­lem: http://justintadlock.com/archives/2009/05/26/the-complete-guide-to-creating-widgets-in-wordpress-28

  7. Posted 12th June, 2009 at 6:58 pm (448 days ago)

    There’s got to be a bet­ter solu­tion than this — but because I have a way-​​to-​​tight dead­line for this, this work­around will have to do… I’m going to use the “add/​remove editor” toggle in tin­myce and just make my changes with the editor — toggle the editor OFF and then save the changes. It works — but it’s kinda stu­pid it has to be that way…

    • Posted 12th June, 2009 at 7:30 pm (448 days ago) in reply to Jennifer

      My first thought is that the issues are unre­lated to the WordPress 2.8 Widgets API, as the tinyMCE integ­ra­tion isn’t dir­ectly modi­fy­ing the code of the wid­gets, per-​​say. It’s tar­get­ing all tex­tareas on the page where the init func­tion is called.

      If I come across a solu­tion to the dis­ap­pear­ing editor bug, I’ll post it as soon as I do. :)

  8. Posted 17th June, 2009 at 7:17 pm (443 days ago)

    Oh — FYI — another solu­tion that’s work­ing bet­ter (and also has solved some ser­i­ous lag on the wid­gets page — I’ve now turned on “access­ib­il­ity mode” — not as slick as before with being able to drag drop wid­gets, etc. — but that wasn’t really work­ing too well for me anyway…

  9. Candice's GravatarCandice
    Posted 7th August, 2009 at 1:31 am (393 days ago)

    … So do you or do you not have TinyMCE suc­cess­fully work­ing on a text wid­get in WP v2.8?

    • Posted 7th August, 2009 at 8:24 am (392 days ago) in reply to Candice

      Hi Candice.
      Thanks for your comment.

      I have not yet attemp­ted integ­ra­tion of a tinyMCE editor with a text wid­get in WordPress 2.8.

      As soon as I have res­ults, I’ll post my find­ings here. :)

      Cheers,
      Matt.

  10. Candice's GravatarCandice
    Posted 7th August, 2009 at 10:14 am (392 days ago)

    Thanks :) Glad I found your post. I think I’m going to take a go at it tomor­row and see what I can come up with.

    • Posted 7th August, 2009 at 11:48 am (392 days ago) in reply to Candice

      Awesome. :) I’ll take a look into it as well soon­est and see what I can come up with. :)

  11. Candice's GravatarCandice
    Posted 7th August, 2009 at 8:17 pm (392 days ago)

    Here.. this will help avoid hav­ing all your tex­tareas become tinyMCE’d

    http://tinymce.moxiecode.com/punbb/viewtopic.php?id=4415

    • Posted 7th August, 2009 at 9:58 pm (392 days ago) in reply to Candice

      Thanks Candice. Switching to “exact” mode would be my next step, after includ­ing and set­ting up the editor. :)

      How is your widget/​plugin to integ­rate tinyMCE into the text wid­get going?

  12. Candice's GravatarCandice
    Posted 7th August, 2009 at 10:29 pm (392 days ago)

    I’ve got it work­ing now.. but only when the Accessibility Mode is turned on. When that’s on, everything works perfectly.

    If AM is off (e.g. the default drag & drop mode) ::
    — then it loads up the tinyMCE thing and lets you edit the text and do all your fancy doodads to it and then when you hit “Save” it switches back to the reg­u­lar text editor (sans tinyMCE) and has lost all the changes you made while the tinyMCE stuff was working.

    • Posted 8th August, 2009 at 8:44 am (391 days ago) in reply to Candice

      Great. :)

      So the next step is to get it work­ing without AM. :)

      I should have a bit of time today to do some research and test­ing into this. :)

  13. Posted 11th August, 2009 at 7:39 pm (388 days ago)

    It seems the issue to this prob­lem is with how word­press is hand­ling the ajax requests. TinyMCE.init is called on load when the wid­gets page is loaded. In order to keep the editor intact it will require recall­ing the init func­tion after the ajax request com­pletes. Maybe using jquery’s live fea­ture to bind to the textarea’s class? I will keep ya’ll updated on my pro­gress if i get this fea­ture to work without the AM.

    • Posted 11th August, 2009 at 8:33 pm (388 days ago) in reply to Michael

      Thanks, Michael. :)

      The use of jQuery’s live() sounds like a pretty solid solu­tion to me. This may pre­vent users using a pre-1.3 ver­sion of jQuery from using this fea­ture as, if I under­stand cor­rectly, live() has been included only since jQuery 1.3. This can, how­ever, eas­ily be resolved by includ­ing the jQuery lib­rary from Google Code instead of rely­ing on the nat­ive WordPress jQuery lib­rary. :)

      Thanks for post­ing, Michael. I look for­ward to read­ing your pro­gress updates. :)

      Cheers,
      Matty.

  14. Posted 11th August, 2009 at 9:48 pm (388 days ago)

    Here’s a cor­rec­tion to my pre­vi­ous post: the live func­tion wouldn’t work in this situ­ation since it handles events such as click, mouseover etc.

    I did how­ever get tinyMCE to load into a wid­get in word­press 2.8.3. For those of you hav­ing trouble get­ting the editor to save in the wid­get form, you must include this code into the tinyMCE.init function :

    setup : function(ed) {
    ed.onChange.add(function(ed) {
    tinyMCE.triggerSave();
    });
    }

    Now the main prob­lem with this situ­ation was that word­press loads the form again after you save. Disabling the editor. What I did was in the update func­tion of the wid­get I pass a vari­able to define that the con­tent has been updated. Then in the form dis­play code I check for this vari­able and recall the init func­tion to get the editor back into the widget.

    After I tidy up my code a bit I will post it and hope­fully it will help a lot of you guys out. =)

    • Posted 11th August, 2009 at 10:12 pm (388 days ago) in reply to Michael

      That’s really awe­some, Michael, thanks for post­ing. Your explan­a­tion is really help­ful as well. :)

  15. Posted 11th August, 2009 at 10:48 pm (388 days ago)

    Here it is cleaned up and fully func­tional … Please note you will need to place the TinyMCE lib­rar­ies into the dir­ect­ory of the plug-​​in. Hope you enjoy =)

    (Code snip­pet moved to main post con­tent, for consistency.)

    • Posted 12th August, 2009 at 9:11 am (387 days ago) in reply to Michael

      Wow! Thanks for post­ing this, Michael. :)

  16. simone's Gravatarsimone
    Posted 3rd November, 2009 at 5:14 pm (304 days ago)

    Great, after a long trip I’ve found the answer to my needs!!!

    Thanks.

    • Posted 7th November, 2009 at 10:08 am (300 days ago) in reply to simone

      Thanks for your com­ment, Simone. I’m glad you found what you were look­ing for. :)

  17. Posted 7th November, 2009 at 6:48 pm (300 days ago)

    Hi all, I had lots of prob­lems try­ing to get WordPress’ TinyMCE code to work with my plu­gin nicely. I kept run­ning into prob­lems try­ing to load the lan­guage trans­la­tions. This res­ul­ted in hav­ing all these ugly titles in the link and image insert menus. I was includ­ing the javas­cript manu­ally because using wp_enqueue_script(‘tinymce’) didn’t seem to work.

    The solu­tion was to simply call the fol­low­ing func­tion in the template_​redirect action (wp_​head might work as well):

    wp_​tiny_​mce();

    Then I simply inser­ted my ini­tial­iz­a­tion code, and everything works, lan­guage trans­la­tion and all!

    /* */

    Here’s my blog post on the sub­ject: [ Link moved to main blog post. Thanks Dan. :) ]

Leave your comment

Your email is never shared. Required fields are marked *

*
*