tinyMce線上編輯器內JavaScript實現按Ctrl+S無重新整理儲存

來源:互聯網
上載者:User

以前也用過幾個編輯器拉,如FCK,CUTEDTOR等,它們大都實現了很不錯了的功能,也有豐富的外掛程式使用。不過我還是覺得TinyMCE線上編輯器好用,它是採用純JS用戶端指令碼技術構建,是一個輕量級載入速度非常快的WEB的文本編輯控制項,並且TinyMCE是一個根據LGPL license發布的自由軟體,你可以把它用於商業應用。

由於最進在做一個部落格系統需要有線上編輯器,於是便找了TinyMCE線上編輯器,以前用過Google的GMail,裡面就有一個按Ctrl+S的快速鍵儲存郵件的功能,因為當時還不太清楚那些編輯器的一些功能實現,對編輯器結構不清楚,也不知道用IE Developer Toolbar和Firebug等調試工具來看,所以那時候感覺Google特別牛B,而且Ctrl+S儲存那個功能在FF裡面運行,而FF瀏覽器按下Ctrl+S預設是彈出修改網頁的對話方塊的,這讓我更好奇了,難道JavaScript還能阻止瀏覽器裡面Ctrl+S儲存網頁的快速鍵,真的太神氣了!下面我們就使用TinyMCE編輯器來實現一個按Ctrl+S使用Ajax非同步儲存文章的功能吧,這也是我的部落格系統的需要。

線上編輯器的原理一般是建立一個ifrmae,這樣便可相當於一個頁面來進行單獨控制,並且設定這個ifrmae的designMode="On"處於設定模式。TinyMCE是通過初使化配置一些參數,主要是傳遞一個textarea對象,並且在初始化的時候隱藏掉這些textarea,擷取原來textarea的寬高在原來的新建立一個ifrmae對象。我們先用IE Developer Toolbar來看一下這個編輯器它建立的一些結構。

紅色框標記的就是我們頁面裡面放置的textare文本輸入控制了,這裡是放的Asp.Net伺服器控制項,而綠色框裡面標記的內容就是TinyMCE自動產生的東西了,可以看到這裡面就是一個IFRAME,裡面的BODY就是我們編輯器的內容了,它會自動初始話指定的textare的內容。這個IFRAsME的編號為我們指定的textare控制項ID加上'_ifr',而且designMode="On"。所以我們要線上編輯器內按Ctrl+S實現儲存就是要監聽這個IFAME裡面的事件了,關聯到我們自訂的一個方法,可以是AJax請求伺服器儲存s,也可以執s行其他動作,那下面我就給出一個完成的DEMO。

在這裡面按下Ctrl+S試試?

上面所示就是一個完成的例子了,由於TinyMCE可以支援JavaScript,所以我就在編輯器裡面用指令碼再初始化一個編輯器,這個也是我部落格裡面所有的編輯器了,還有一些功能外掛程式沒能用上。我們先來看它的指令碼是要如何來寫的吧,先貼出它的代碼:

<script type="text/javascript" src="/tiny_mce/tiny_mce.js"></script>
<script type="text/javascript">
    var editorId = "txtContentEditor"
    tinyMCE.init({
        mode : "exact",
        elements : editorId,
        theme : "advanced",
        language : "zh",
    content_css : "/tiny_mce/css/content.css",    plugins : "safari,pagebreak,style,layer,table,advhr,advimage,advlink,emotions,iespell,inlinepopups,insertdatetime,preview,media,searchreplace,print,contextmenu,paste,directionality,fullscreen,noneditable,visualchars,nonbreaking,xhtmlxtras,template,insertCode,uploadImage",
        theme_advanced_buttons1:"formatselect,fontselect,fontsizeselect,separator,forecolor,backcolor,separator,bold,italic,underline,strikethrough,separator,bullist,numlist,separator, justifyleft, justifycenter, justifyright",
        theme_advanced_buttons2:"undo,redo,cut,copy,paste,separator,justifyleft,justifycenter,justifyright,separator,outdent,indent,removeformat,separator,link,unlink,image,uploadImage,media,separator,insertCode,separator,code,fullscreen",
        convert_fonts_to_spans:true
    });
    
    addEvent(window,"load",function (){
        setTimeout(function (){
            var content = tinyMCE.getInstanceById(editorId).getBody();
            var editorDocument = document.all ? content : document.getElementById(editorId+"_ifr").contentDocument;
            addEvent( editorDocument ,"keydown",function (e){editorKeyDown(e)});
        },1000);
    });
    
    function editorKeyDown(e)
    {
        
        var num = e.which?e.which:e.keyCode;
        if( e.ctrlKey && num == 83 )
        {
            //postArticle();這裡類比Ajax儲存文章
            InsertToEditor("<br />正在儲存中。。。");
            setTimeout(function (){
                InsertToEditor("<br />儲存成功!!!");
            },1000);
            if (document.all)
            {
                return false;
            }else e.preventDefault();
        }
    }
    
    function InsertToEditor(content)
    {
        tinyMCE.execCommand('mceInsertContent',false,content);  
    }
    
    function addEvent(target,eventType,func){
        if(target.attachEvent)
        {
            target.attachEvent("on"+eventType,func);
            
        }else if(target.addEventListener)
        {
            target.addEventListener(eventType,func,false);
        }
        return this;
    }
</script>

TinyMCE.init這個方法不用說了,初始話textare編輯器,然後接著是addEvent方法,這個是後面定義的,之所單獨出來是為了重用併兼容所有瀏覽器,這裡需要注意的是FF內關聯事件需要傳遞一個事件對象,而IE不需要傳也可以直接獲得,為相容全部增加傳遞事件的參數,然後在再裡面判斷擷取鍵盤按下的鍵,如果按下了Ctrl並同步選取了S(keyCode=83)則執行儲存,這裡是用setTimeout類比Ajax請儲存,這裡說一下之所以監聽keydown事件,那是因為在keydown、keypress 、keyup這三個事件裡面keydown是最先觸發的,而且也只能再這個事件裡面阻止事件冒泡和預設行為(FF內),這個事件裡面也是最能擷取鍵盤按下鍵的最詳細的資訊,其他時間就不一定能擷取得到(FF內),有時間再寫一下JS事件的一些文章。接下來看下面keydown裡面最關鍵的代碼了,if(document.all) return false;這裡是判斷是否為IE核心的瀏覽器,不過正規的判斷應該不是這樣,這裡為了簡化就直接這樣寫了。return false是在IE裡面阻止事件最的通用方法了,這裡就不在撰述,後面一句是對非IE核心瀏覽器的處理。使用e.preventDefault()方法來阻止事件的預設行為,這個方法其實並是陌生,早在JQuery裡面就有過介紹:

通過使用 preventDefault() 方法只取消預設的行為。在一些支援標準的DOM瀏覽器裡,如果動態添加關聯表單的submit的事件,唯寫return false是不行的,FF內仍然會submit,加上preventDefault()方法即可阻止表單提交。

jQuery 代碼:

$("form").bind("submit", function(event){
  event.preventDefault();
});

通過使用preventDefault()方法取消事件預設行為,這個應該在所有支援WSC的DOM瀏覽器都可以,不過我還沒有在safari 、opera 瀏覽器內做過測試,但至少在FF2.0和Google瀏覽器下執行沒有問題。FF和Google瀏覽器在頁面裡面按Ctrl+S預設是彈出儲存網頁對話方塊,使用preventDefault()就能夠阻止取消彈出對話方塊,是不是很神奇,呵呵^_^。因為這裡瀏覽器裡面事件的處理機智是先傳遞給網頁再傳遞給瀏覽器,所以在網頁裡面就能通過JavaScript來阻止瀏覽器預設的事件了。不過需要注意的是FF好象關聯body的事件無效,關聯非text或textare可輸入文字物件也無效,按Ctrl+S仍然是會談出儲存的網頁的對話方塊,有點奇怪,好象Ctrl+S只是特別為text或textare預留的快速鍵一樣,最後還是通過關聯架構的document對象contentDocument來搞定的。只要能關聯到事件,又能取消按Ctrl+S預設行為,編輯器內按Ctrl+S就執行自訂的方法,我這裡是使用AJax請求伺服器儲存編輯器內的內容,而且可以很友好的無重新整理按Ctrl+S及時儲存,這樣不需要等到PostBack回伺服器去,避免寫文章到一般而沒有即時儲存而丟失的一些問題。

其他只要是IFRAME編輯器應該使用這種方法都可以實現按Ctrl+S自訂儲存,不過寫到最後面我告訴大家其實要顯示Ctrl+S儲存沒必要這麼複雜,因為TinyMCE線上編輯器裡面提供了一個現成的save外掛程式,我們園子裡面就有用到。plugins :"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,insertCode,uploadImage",其中的save就是儲存了,只要寫指定有save在編輯器內按Ctrl+S就會自動Post回去,不過就是重新整理了頁面-_-。TinyMCE編輯器果然好用夠人性化,連這種功能都預先想好提供了。不過我還是自己來實現了一次,下次碰到其他編輯器說不定也能用上,希望對大家有用。

本篇為作者Jonllen以"現狀"提供,且沒有任何擔保,同時也沒有授予任何權利。原文地址http://www.jonllen.com/Article.aspx?aid=16
相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.