2015年2月8日 星期日

讓 Blogger 支援程式碼上色

像我這樣的程式撰寫者,在發佈文章時難免會用到程式碼,如果沒有使用什麼特殊設定,效果大概就像下面這樣:

function foo()
{
    if (counter <= 10)
    return;
}

感覺超...醜的!

可是,如果使用了程式碼上色(這叫做 syntax highlight)工具,結果就可以出現下面這種效果:
是不是美觀很多啊!這邊我所使用的,是名為 SyntaxHighlighter 的網頁工具,當前版本是 3.0.83 ,官方網站是 http://alexgorbatchev.com/SyntaxHighlighter/,而為了讓 Blogger 能自動把這個工具套用到每篇網誌中,我參考了「如何在Blogger上安裝高亮程式碼 - SyntaxHighlighter?」的設定(雖然最後我的方法跟他差很多),並把心得總結在這裡。

注意:SyntaxHighlighter 是屬於贊助式的工具,像下面所描述的方法,實際上在每次瀏覽時,是從官方網站上下載需要的程式碼。這種方法也有助於載入的速度(與瀏覽器的快取機制有關),所以如果有能力,不妨贊助一下作者吧!作者的贊助網頁在這裡

自動執行程式碼上色的步驟

  1. 在範本(template)中引入 SyntaxHighlighter 所需檔案:
    先在 Blogger 所提供的設定介面中找到「範本→網誌即時狀態→編輯HTML」來進行 HTML 範本的編輯

    接著,找到 </head> 標籤(不是 <head>),並且將下面這段程式碼複製到 </head> 的上面

    其中,第二行的 shThemeDefault.css 檔案代表的是上色時使用的風格,如果不滿意,官方網站在這裡還有其他的風格可以挑,只要變更這個檔名就可以了。

    改完後,要記得儲存,下面是我改好的樣子

  2. 加入呼叫上色函式的程式碼:
    引入函式之後我們必須在適當的時間點呼叫 SyntaxHighlighter 進行格式調整及上色,這個時間點通常是在 </body> 之前,也就是整個網頁載入完畢的時候。

    所以,接下來一樣在範本 HTML 內,尋找 </body> 標籤,並將以下這段程式碼加到 </body> 之前。
    當然,完成之後要記得存檔,可是,當你下次再回來編輯範本 HTML 的時候,你會發現:「我的程式碼怎麼多了很多奇怪的符號?」以我為例,我看到的是以下的樣子
    不必緊張,這是正常的現象。為了避免我們的語法影響到正常的範本內容,Blogger 會把凡是不屬於任何標籤屬性的 XML 節點文字,全部以跳脫字元的方式處理。反正總而言之,免驚啦!

    做完這些,我們就已經賦予了 Blogger 自動為程式碼上色的能力了。不過要注意的是,一旦你重設了網誌使用的範本,這些步驟就要重做一次。

如何使用

在撰寫網誌的時候,如果遇到需要需要進行格式調整的程式碼,如果你想獲得下面這種效果
那麼就要切換至 HTML 的撰寫模式,下圖是本文撰寫時的情況

然後,有兩種加入程式碼的方式。不過,要先提醒的是,無論哪種方法,在「預覽」中是看不出效果的,甚至可能是一片空白

利用 <pre><code> 的標籤對

第一種是利用 <pre><code>程式碼</code></pre> 的模式,像下面這樣
其實,以預設值來說,應該是只有「<pre>」標籤的。然而,在上述第二步驟添加程式碼的第 37 行,我把預設值改成 <code> 了,原因是在 HTML5 的規格中,明確建議利用 <pre><code> 的一對標籤來放置程式碼,以符合其真正的語意(規格書參見這裡)。

而關於第二行中的「brush: js; highlight:[3,4]」,「brush: js」代表這段程式碼要根據 JavaScript 的語法規則來進行格式調整,實際上詳細的支援語言清單請看這裡;而「highlight:[3,4]」則表示要對第三行、第四行(這是指最終顯示在螢幕時的行數)進行強化標記。

這種標記方法的優點是符合 HTML5 語意、即使在不支援 JavaScript 的瀏覽器上也有最基本的顯示;缺點是原始碼中每個「<」符號都要以跳脫字元標記成「&lt;

利用 <script> 標籤

第二種標記方法是借用 XML 語法中的 CDATA 標記,像下面這樣
利用「<![CDATA[」與「]]>」將程式碼包起來。其中關於 class 屬性的設定與上面相同。

這種方法的優點是不用管跳脫字元,只有遇到「</script>」時要把「<」取代為「&lt;;缺點是在預覽時完全空白,如果遇到停用 JavaScript 的瀏覽器,也是完全空白

我想讓程式碼自動換行要怎麼做?

SyntaxHighlighter 本身並沒有提供這樣的設定,可是可以藉由修改其顯示的方式來達成,我在「SyntaxHighLighter: auto line break with pre wrap」這篇文章中找到了一種做法。然而,一旦用了這種方法,就必須把行號的顯示關掉,因為 SyntaxHighlighter 不會意識到內容被換行了,就會導致行號計算的錯亂。對我而言,行號非常重要,只好忍痛捨棄換行了 T_T

沒有留言 :

張貼留言