tinyMCEを使うと textarea を WYSIWYG エディターに変換できます。 Knockout と tinyMCEで Rich Text エディターに変換される textarea のバインディングを実装するメモです。この機能はO'ReillyのKnockout.js という書籍のスクリプトを勉強用に覚書として記載したものです。同じソースを O'Reilly のページからダウンロードできると思います。。

動作確認バージョンは次の通り

  • jQuery 2.1
  • KnockoutJS 3.3
  • tinyMCE 4.1.9

まず tinyMCE のサイトから TinyMCE  jQuery package をダウンロードしてプロジェクトに含めます。

tinyMCEと連携するためのカスタムバインディングを作成します。tinymcebinding.js ファイルを作成して次のようにtinymce カスタムバインディングを実装しました。

ko.bindingHandlers.tinymce = {
    init: function (element, valueAccessor, allBindingsAccessor) {
        var tinymceOptions = {
            setup: function (editor) {
                editor.on('change', function (event) {
                    valueAccessor()(event.target.getContent());
                });
            }
        };
        $(element).text(valueAccessor()());
        setTimeout(function () {
            $(element).tinymce(tinymceOptions);
        }, 0);
        ko.utils['domNodeDisposal'].addDisposeCallback(element, function () {
            $(element).tinymce().remove();
        });
    },
    'update': function (element, valueAccessor, allBindings) {
        var tinymce = $(element).tinymce();
        value = valueAccessor();
        if (tinymce) {
            if (tinymce.getContent() !== value) {
                tinymce.setContent(value);
            }
        }
    }
};

あとは下記サンプルのように して tinyMCE で編集した内容がビューモデルのオブジェクトとバインディングされてリアルタイムにプレビューできることを確認します。

<!DOCTYPE html>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <title></title>
</head>
<body>
    <form>
        <textarea data-bind="tinymce: htmlText"></textarea>
    </form>
    <button type="button" data-bind="click: resetContent">Reset content</button>

    <h2>Preview</h2>
    <div data-bind="html: htmlText"></div>
    <script type="text/javascript" src="../Scripts/jquery-2.1.3.min.js"></script>
    <script type="text/javascript" src="../Scripts/tinymce/jquery.tinymce.min.js"></script>
    <script type="text/javascript" src="../Scripts/tinymce/tinymce.min.js"></script>
    <script type="text/javascript" src="/Scripts/knockout-3.3.0.js"></script>
    <script type="text/javascript" src="./kobinding.js"></script>
    <script type="text/javascript">
        function ViewModel() {
            var self = this;
            self.htmlText = ko.observable();
            self.resetContent = function () {
                self.htmlText('');
            }
        }
        var viewModel = new ViewModel();
        ko.applyBindings(viewModel);
    </script>
</body>
</html>

このような感じで カスタムバインディングを作成してほかのシステムとも連携できるみたいです。