2007-01-25

動態調整文章字體大小

Blog 文章的字體大小,大多端看作者對版面和整體的要求,而讀者在看的時候,大多只能強迫接受,反正重點還是在內容上。如果自己眼睛不好、或是螢幕解析度太高,字體太大或太小(通常都是嫌字小吧)只好透過瀏覽器來調整(Ctrl + 滾輪,或是直接選較大的字型)。不過這麼做會有兩個問題:第一:整個頁面所有部分都會強迫被放大,包括 Sidebar、標題甚至留言版(字型可能變醜,而且版面會被破壞),第二:整頁可能要浪費時間強迫重新 Reload 一次。有沒有更簡單快速的方法,讓讀者可以只針對 Blog 本文的部分,來調整文字的大小,在閱讀的時候可以更輕鬆?

後來看見一篇 Blog 文章,用 Javascript 就可以輕鬆做到以上的效果,不過我又加以修改了一下,不用動到文章的架構和模版(就是說,不需要在內文多加 <span> 額外的標籤),也把函示兩個合併成一個,更加精簡、要套用在 Blogger 上面也更簡單,方法和步驟如下:

第一個步驟,把下面的 Javascript 插入模版 <head> 標籤的前面(或,只把函示部分插入自己模版的 Javascript 區段內):

<script type='text/javascript'>
function FontZoom(size)
{
  var element = document.getElementsByTagName("div");
  var components = new Array();
  for(i = 0, j = 0; i &lt; element.length; i++) {
    attribute = element[i].getAttribute("id");
    if(attribute == "main-wrapper") {
      components[j] = element[i];
      j++;
    }
  }
  for (i = 0; i &lt; components.length; i++)
    components[i].style.fontSize = size+'px';
}
</script>

從上面的程式碼來看,原理上呼叫這個函示時,它會去把整個檔案裡標籤是 <div>、屬性 id=main-wrapper 的元素抓出來,然後把該元素的字型大小設成指定的數字。這樣,就可以達到即時動態改變本文字體大小的需求了。(知道 main-wrapper 或下面的 header-wrapper 是什麼意思嗎?可以看我的這篇介紹:Template 的基本內容和結構

第二步驟,把下面的連結程式碼放入你想讓讀者使用的地方(不管是 Sidebar 或是標題區 header-wrapper 裡面都可以,隨自己高興放在版面順眼的地方):

<a href="javascript:FontZoom(16)">16</a>
<a href="javascript:FontZoom(14)">14</a>
<a href="javascript:FontZoom(12)">12</a>

程式碼裡面的 12, 14, 16 數字,代表的是想要改變的字體大小,可以自己做實驗,看看幾號字是你 Blog 本文預設用的大小,如果要給讀者使用,你也可以挑幾個自己覺得不會破壞頁面感覺的尺寸當作連結。(像我預設頁面字型大小是 13, 我放大用 16, 縮小用 11)

參考文章:
[Javascript]Selectable Post Font Size for your best view!

回應: 29

Cyril 提到...

請問一下,
我只想要文章內容做字體變化,
最後那個部份應該放在哪裡?
我試了好多地方,都失敗,
找不到應該放哪。

另外,
像你的blog右上方的 -Font+,
語法應該怎麼寫?

謝謝!

Abin 提到...

變化字體使用的是一個全域的 Javascript 函示,照理說,只要連結的部分在函示的後面(可以看原始碼檢查),應該都可以呼叫函示成功。
我的自己的連結方式範例,函示是放在 <body> 的前面,而連結放在 <div id='header-wrapper'> 裡面,在 <div class='descriptionwrapper'> 區段的後面,</b:includable> 標籤前面(要"展開小裝置範本"才能這樣改),其實,看我首頁的原始碼也可以知道喔~
只要順序沒錯,也確定你範本裡有 "main-wrapper" 這個 widget (小裝置),也就是文章內容的 id,程式沒錯的話連結放哪裡應該都會作用才是。

Cyril 提到...

還是不行,
只有文章的日期有變化,
文章內容"無動於衷"。

沒關係,不要用這個功能好了。
謝謝你!

Abin 提到...

我替您的首頁「把脈」測試了一下,沒錯,我的方法並不能用..
這可能是樣版之間的差異導致,不過,我替你試了原文的作法,也就是利用額外的標籤,(將 div 換成 span,id 換成 name,main-wrapper 換成 zoom),把自訂的 span 標籤包在 div class=post-body 那行的外面,就可以達到調整字型的效果,缺點就是模版要動到而已,您可以試試看。

Cyril 提到...

成功了,謝謝!

Simon 提到...

謝謝您的分享,字型確實可以自由更換了~
但有個額外的問題,如果要調整字距應該如何做呢?

謝謝喔~

Abin 提到...

如果要動字距,那要修改 Javascript 一下。有注意到,更改字體大小是下面這一行:
components[i].style.fontSize = size+'px';
其中,是透過更改 style 的 fontsize 屬性來變動字型大小,如果你要改字距,屬性是 LetterSpacing,你增加或是替換掉一行就可以了,像是:
components[i].style.LetterSpacing = size+'px';
如果還有其他屬性想變動,也可以參考 CSS 和 Javascript Style 屬性的對照表,找出想改的屬性並修改 Javascript 就可以,自己調整看看囉!

ADCT 提到...

Dear abin,

謝謝你詳細的說明~

Simon 提到...

您的blog內容非常豐富喲,學到很多東西,也感謝您的回答~

Lung-Chang Chien 提到...

請問如果header-wrapper裡面的title是置左的話,照你的程式碼貼上去的"+font-"也是跟著置左。如果讓title置左,但"+font-"置右呢?

Abin 提到...

那個顯示在 header 裡的 font 字樣,要置中置左置右請自己套用 CSS 來達成。我自己的頁面是「標題置中,字樣靠右」,你可以看我頁面的原始碼,參考關於 FontZooming 這個 class 的樣式。

mokotw 提到...

請問我在文章上

分享flash小遊戲

我想讓flash能給網友調整大小
ex:
320x240
800x600
1024x986

原本程式
<embed style="width:400px; height:326px;" id="VideoPlayback" type="application/x-shockwave-flash" src="FLASH 網址" flashvars=""> </embed>

我要如何改呢
style="width:???px; height:???px;"

可以教一下嗎

Sam@自我色彩 提到...

按照Abin 大哥所提供的方式,順利修改了這個內容,可以說是相當的好...這樣在讀者的閱讀上也更加順利了

Bboy Fan 提到...

感謝教學,不過我連你的設計方法都套用囉。
之前就依直覺的想用個條字型的但都懶得用,剛google發現,謝謝了。

RALPH 提到...

我的也不行耶,
只有文章的日期有變化,
文章內容還是沒改變
可以請大大幫我看一下嗎?

Abin 提到...

To ralph:
我不知道你有沒有看懂我原始碼的意思,這個字體變化的 hack,主要是透過 Javascript 動態去更改某個 CSS 樣式,我範例裡是 main-wrapper 這個 div。
我看你的 blog,密密麻麻塞了一堆模組和東西,其中有的都還有自己的樣式,想當然一定會覆蓋掉 hack 裡定義的樣式,因此部份字體不會動態變動,我不可能幫你一個個 debug、找出衝突的部份,你要自己調整樣板的原始碼。

Ralph Huang 提到...

謝謝
版主
我會在調整版面的
還有調整原始碼謝謝

why? 提到...

作者已經移除這則留言。

why? 提到...

前輩您好:
小弟遍尋此功能
終於在您的部落格中尋獲
在開心之餘
立刻做了一個簡單的小試驗
但在我反覆仔細檢查程式碼後
卻發現絲毫無作用
請允許我把完整的原始碼貼上
希望前輩可以幫小弟我"健診"
感激不盡!!!!!!

以下為程式碼
(因blogger不允許張貼標記 因此我刪除了一些"<"符號 我已確定在dw中 這些記號我都有註記)
----------------------------------
html xmlns="http://www.w3.org/1999/xhtml"
script type='text/javascript'
function FontZoom(size)
{
var element = document.getElementsByTagName("div");
var components = new Array();
for(i = 0, j = 0; i < element.length; i++) {
attribute = element[i].getAttribute("id");
if(attribute == "main-wrapper") {
components[j] = element[i];
j++;
}
}
for (i = 0; i < components.length; i++)
components[i].style.fontSize = size+'px';
}
/script
head

title無標題文件/title
/head
body
a href="javascript:FontZoom(16)"16/a
a href="javascript:FontZoom(14)"14/a
a href="javascript:FontZoom(12)"12/a
div id="main-wrapper"
div id="shit" shit /div
/div
/body
/html

-----------------------------------

再一次感謝您~~~~

why? 提到...

前輩您好:
我剛剛發現了問題所在
我直接去拷貝您的原始檔
結果完全沒問題
可以正常使用
比對之下
我才發現問題出在js的第六行
關於for判斷式
for(i = 0, j = 0; i < element.length; i++)

"<"應該是大於符號
不知道什麼原因
變成這個亂碼
下面的判斷式也有出現這問題

不知道是我電腦的編碼問題還是有其他的原因
感謝您的分享
讓我學會了這技巧
謝謝您!

why? 提到...

前輩您好:
還是我
希望你不要以為我是來亂的
因為當我發佈上一篇回覆後
大於符號竟然又正常的出現
搞的我一愣一愣的
但希望有碰到跟我一樣問題的人
不要再花三個小時碰的自己頭破血流
奇怪
鬼門明明都關了....

鐵爸 提到...

謝謝你的分享,我成功的加到了自己的 blogger 上。 ^^

Angel 提到...

您好,我照著您的做法做了 式的確成功了:D
但是因為我不太了解該如何去解決聯結的問題
比如說 如果我想跟您一樣用+,-來做
or利用圖片來做一個連結的話
那這樣又該如何去改呢?
先感謝您的回答!:D

Abin 提到...

To Angel:
上面「第二步驟」的程式碼就是連結的部份,我自己只不過是把</a>前面的 16, 14, 12 分別替換成了 "+", "Font", "-" 而已。至於要替換成圖片,一樣是把 16-12 這幾個數字換成圖片的程式碼,像是 <img src="圖片網址" />就行了。這部份應該是基本的 HTML 語法,如果你沒有概念的話,可能要自己先參考 HTML 相關的教學文章。

烈燄 提到...

您好,我用blogger(新版文章編輯器)或 Windows Live Writer 來寫的文章都不能正常使用這個HACK,但用blogger(舊版文章編輯器)則可以正常,我試找問題所在,原因好像是blogger(新版文章編輯器)fontSize是用英文大中小來表示,Windows Live Writer是用數字來表示,而blogger(舊版文章編輯器)是用百分比表示,請問有方法或改參數來使用這個
HACK嗎?或您是用什麼來寫blogger文章.請大大有空幫我解答一下謝謝?

Abin 提到...

To 烈燄:
首先,文章內的「本文」我從來都不去改字型大小,用的都是預設樣板內的變數,所以其實只要改這個變數的樣式,所有本文的字型大小舊會跟著變動。
但用 Live Writer 或新版編輯器,這類「所視即所得」的工具固然方便,但背地裡的原始碼你並不知道它會幫你加什麼標籤或定義變數(像會強制嵌入字型大小的定義),一旦被塞入一些標籤或變數,本文提到更改文字樣式的 Javascript 就可能會找不到指定物件,要改他們的樣式讓字型變大變小當然就不會動(像你提到 fontsize 用不同方式來定義就是一例)。
我自己都是用 Google Doc 來寫文章,要發表時直接貼入文章的 HTML 原始碼,一方面檢查有沒有被系統塞入的無謂標籤,另一方面如果有特殊要求也可以微調。如果沒有其他樣式需求,其實用最簡單的編輯器(記事本)寫也可以。

烈燄 提到...

感謝您的回答,另請問如字體是採用xx-small, x-small, small, medium, large, x-large,這種方式的話,那您上面的HACK裡的fontSize = size+'px';這裡的單位可以改嗎?如可以那要成什麼單位呢?謝謝歐!

Abin 提到...

To 烈燄:
如果是用文字表示字型大小的話,後面是沒有單位的,直接用 fontSize = 'xx-small' 之類的即可。
舉例,如果不用指定字型大小的數字,要用文字,上面的 Javascript 程式裡倒數第三行改成:
components[i].style.fontSize = size;
而要呼叫的時候就不能用數字,要用文字,像是:
<a href="javascript:FontZoom('xx-small');">xx-small</a>
<a href="javascript:FontZoom('medium');">medium</a>
<a href="javascript:FontZoom('x-large');">x-large</a>

Christine 提到...

作者已經移除這則留言。

張貼留言

歡迎留言或發表意見,不過要理性不做人身攻擊。匿名的朋友得到回應的速度會比較慢喔~
發問相關的禮貌和規矩請先參考這篇文章,不當留言、和本文無關的回應可能會被直接刪除無視喔!