Search code examples
javascriptjqueryformsdetection

How to detect html form change when form may contain tinyMCE text areas?


I'd need a generic way to detect html form change. The form may contain textareas having WYSIWYG features through tinyMCE.

The serialize() approach described here will not work, as tinyMCE overrides the textarea tags in html and replaces them with a fancy js editor. The original textarea value will remain unchanged when you make changes in the WYSIWYG editor.

What would be the easiest and most compact way to implement a generic change-detection feature, assuming that I don't have any additional information about the form fields - i.e. I don't know explicitly which form fields might have tinyMCE attached? I'm using jquery 1.4, but any (framework-independent) js approach would be greatly appreciated.


Solution

  • I ended up using the tinyMCE.Editor.save() function before serializing the form.

    Using jQuery, I code looks like this:

    // Unified form serialization, also serializes tinyMCE textarea contents
    $.fn.saveState = function() {
        var $form = $(this);
        $form.find('textarea').each(function() {
            tinyMCE.get($(this).attr('name')).save();
        });
        $form.data('original_value', $form.serialize());
    };
    
    // Unified form change check, also detects tinyMCE textarea changes
    $.fn.formChanged= function() {
        var $form = $(this);
        $form.find('textarea').each(function() {
            tinyMCE.get($(this).attr('name')).save();
        });
        return ($form.data('original_value') !== $form.serialize());
    };
    

    Upon document.ready, I call the saveState() function on each form element in the document. Then I set up a timer, that'll call the formChanged() function to see if there were any changes. If yes, I'll trigger my action (in my case - autosave the current state of the form on the server), and call on saveState() again. This will not work if you have mixed textareas on your page, some of them having tinyMCE attached and some of them not. In that case you could go with a class based identification - like $form.find('textarea.tinyMCEAttached')...

    Kevin Peno's suggestion to use the onChange() was not going to work for me. onChange fires only on blur, and I needed to detect form changes even if the user doesn't leave the editor area. However, it pointed me to the right direction, thanks Kevin!