:::

Blogger範本之網頁類型(pageType)應用

6月 22, 2011 , 25 Comments Edit Copy Download

image

Blogger的範本是以Blogger特殊的範本語法跟HTML語法混合撰寫而成,在Blogger版面配置中有相關說明。常常會有人用「Blogger Hack」來形容修改範本的行為,而我自己把玩Blogger範本也有一段時間,偶爾也會跟大家分享一些Blogger的程式碼。

這篇要跟大家介紹的是Blogger範本程式中最常用到的「網頁類型」(page type),以及如何偵測不同的網頁類型來對版面進行微調。


網頁類型之index、archive、item

「網頁類型」是Blogger在不同情境下的狀態參數,名稱是blog.pageType,可以利用以下語法來顯示網頁類型:

<data:blog.pageType/>

在Blogger的資料標記說明中,網頁類型有「index」(包含首頁、搜尋、標籤label列表)、「archive」(每年、每月封存的文章列表)、「item」(文章全文,Google翻譯做項目)、「static_page」(靜態網頁)等四種。

實際上在使用網頁類型時,會搭配Blogger範本語法中的條件標記<b:if></b:if>跟<b:else/>來使用。舉例來說,我想要在item類型中的顯示一段話,在index類型中顯示另外一段話的話,可以插入以下語法:

<b:if cond='data:blog.pageType == &quot;item&quot;'>
這段文字會出現在item網頁類型。
</b:if>
<b:if cond='data:blog.pageType == &quot;index&quot;'>
這段文字會出現在index網頁類型。
</b:if>

其中「&quot;」是指「雙引號"」的脫逸化後的字串,同等於雙引號。只是在Blogger範本處理過程中,會自動將雙引號換成&quot;。大家在使用的時候請不要覺得奇怪喔。

區隔index中的首頁與其他網頁

預設的網頁類型雖然有四種,但是index類型包含了首頁、搜尋與列表,這樣的混雜令人難以使用。

舉例來說,我會希望我的Blogger首頁顯示文章內文摘要、而搜尋跟標籤(label)列表只要顯示標題就好。就像下表左右兩張圖的區別一樣。但是光用網頁類型卻無法區隔這兩者的差別。

image image

首頁

搜尋、標籤列表

其實,Blogger範本中還有另一種資料標記可以用來區隔是否是首頁,那就是「blog.homepageUrl」(Blog首頁的網址)跟「blog.url」(現在網頁網址)。blog.homepageUrl在各種類型的網頁中都是固定的參數,表示你的Blog首頁網址,例如「http://pulipuli.blogspot.com/」;blog.url則會隨著你現在瀏覽的網頁有所不同,例如「http://pulipuli.blogspot.com/search/label/Second%20Life」。

聰明的你應該發現到了,只有當頁面是首頁的時候,blog.url才會等於blog.homepageUrl。因此我們可以利用條件標記來判斷這是否是首頁,例如:

<b:if cond='data:blog.url == data:blog.homepageUrl'>
這是首頁。
<b:else/>
這不是首頁,可能是搜尋、標籤列表,或是文章全文、封存列表。
</b:if>

如果再加上網頁類型的判斷,就可以將範圍縮小到只區隔首頁跟搜尋、標籤列表這兩種類型。語法如下:

<b:if cond='data:blog.pageType == &quot;index&quot;'>
    <b:if cond='data:blog.url == data:blog.homepageUrl'>
        這是首頁。
        <b:else/>
        這是搜尋或標籤列表。
    </b:if>
</b:if>

於是這樣子,我們就能夠分辨清楚首頁與搜尋、標籤列表這兩種類型的網頁了。

重新歸類網頁類型

除了原本的四種網頁類型之外,上述的方法又可區分出首頁與搜尋、標籤列表這兩種類型。但對我來說,實際上我只把Blogger的網頁類型區分成四種:首頁、列表、文章、靜態網頁。以下一一敘述其情境、需求,以及Blogger範本語法的用法。

首頁

image

首頁,Blog一進來就會看到的網頁,是整個Blog的門面。

  • 舉例網址:http://pulipuli.blogspot.com/
  • 文章數量:我會在首頁擺放五篇左右的最新文章
  • 文章內文(post content):僅顯示文章的摘要內文(用Blogger的繼續閱讀功能,或是以JavaScript來實作)。
  • 導覽列(sidebar)預設狀態:顯示
  • 小工具(widget):列出所有的小工具,供使用者取用完整的功能。
  • 網頁類型(page type):index

首頁被歸類在網頁類型的「index」中,但透過blog.url跟blog.homepageUrl來判斷,就能實作判斷首頁的語法。Blogger範本判斷首頁的語法如下:(如果只要知道首頁的話,就不需要blog.pageType的判斷)

<b:if cond='data:blog.url == data:blog.homepageUrl'>
    這是首頁。
</b:if>
列表

image

列表是使用搜尋功能、瀏覽標籤以及網頁存檔的時候顯示的文章列表。雖然Blogger把首頁跟搜尋、標籤列表混在一起當做index網頁類型,但實際上,我們使用搜尋、標籤跟網頁存檔的時候,通常會因為單一頁面顯示太多篇文章,導致網頁讀取速度太慢。而此時使用者專注於搜尋,導覽列裡一些小工具也不需要顯示或執行,以免拖慢網頁速度。

我以前常常覺得Blogger內建的搜尋速度實在是太慢,這是因為搜尋頁面中會顯示的文章太多,加上圖片讀取、JavaScript執行的時間,就算是Google Chrome開起來也常常覺得會有即將當機的感覺。以前我能力不足,只會用JavaScript勉強修正,但現在知道怎麼利用Blogger範本之後,這個問題就迎刃而解了!

在Blogger範本中,要使用列表的條件標籤語法如下:

<b:if cond='data:blog.pageType == &quot;index&quot;'>
    <b:if cond='data:blog.url != data:blog.homepageUrl'>
        這是列表(搜尋、標籤)。
    </b:if>
</b:if>
<b:if cond='data:blog.pageType == &quot;archive&quot;'>
    這是列表(封存)。
</b:if>
文章

image

文章就是Blog單篇文章的全文。

  • 舉例網址:
    文章全文 http://pulipuli.blogspot.com/2011/06/oped.html
  • 文章數量:一篇
  • 文章內文:全部顯示
  • 導覽列預設狀態:隱藏
  • 小工具:列出全部的小工具,但延遲載入。
  • 網頁類型:item

我個人不喜歡閱讀文章時,旁邊還有一串導覽列,造成文章閱讀起來容易分心、還佔了版面的位置。所以我希望能在文章類型的頁面中隱藏導覽列,讓使用者能專心閱讀。

Blogger範本中可以直接用blog.pageType來偵測文章的網頁類型,語法如下:

<b:if cond='data:blog.pageType == &quot;item&quot;'>
    這是文章。
</b:if>
靜態網頁

靜態網頁通常是放一些長期顯示的訊息,例如詳細的「關於我」介紹、「與我聯絡」的細節。我目前並沒有使用靜態網頁,因為我覺得隨著時間一次又一次建立的網頁典藏比較有趣。因此,下面只是我推測靜態網頁可能的情境與需求而已:

  • 文章數量:一篇
  • 文章內文:全部顯示
  • 導覽列預設狀態:顯示
  • 小工具:列出全部的小工具。
  • 網頁類型:static_page

Blogger範本中也可以直接用blog.pageType來偵測靜態網頁的網頁類型,語法如下:

<b:if cond='data:blog.pageType == &quot;static_page&quot;'>
    這是靜態網頁。
</b:if>

網頁類型改變顯示內容的應用

上述的四種情境,在文章內文、導覽列預設狀態跟小工具的顯示上皆有不同的需求。那麼要如何針對不同的網頁類型,改變成該類型的顯示內容呢?答案是依照網頁類型載入不同的CSS樣式檔與JavaScript腳本檔。

全網站與類型專用的檔案

實務上,我會建立一個應用於全網站的blogger.css樣式檔以及blogger.js腳本檔,然後再依照不同網頁型態建立各自型態使用的檔案。不同網頁型態的檔案名稱字尾有所不同,我的作法是:

  • 首頁:-index
  • 列表:-list
  • 文章:-item
  • 靜態網頁:-static-page

例如文章就會有專屬的blogger-item.css樣式檔跟blogger-item.js腳本檔。

全網站的檔案跟專屬的檔案有什麼差別呢?我以「布丁布丁吃什麼?」blog右邊的導覽列為例。在blogger.css中定義主要內文與導覽列寬度的CSS語法如下:

div#main-wrapper div#main {
    width: 66%;
}
div#sidebar-wrapper {
    width: 30%;
}

因此全網站預設導覽列會在主要內容右邊,佔據大概30%的寬度。其中,兩者相加沒有100%的原因是避免擠壓到邊線排版。

而在文章網頁類型中,我希望導覽列能隱藏,而主要內文的寬度能最大化。因此在blogger-item.css中定義主要內文與導覽列寬度的CSS語法如下:

div#sidebar-wrapper {
    display:none !important;
    width: 0% !important;
}

div#content-wrapper div#main {
    width: 97% !important;
}

如此一來,當載入blogger-item.css的時候,CSS語法的「!important」就會強制覆寫blogger.css的定義,讓主要內文的寬度擴展到97%,並將導覽列隱藏起來。

至於JavaScript腳本檔的方面,雖然我沒有特別說明,不過對於常常在玩JavaScript的人來說,看到這邊應該就能夠舉一反三了吧。

載入檔案語法

建立好各自的檔案之後,在Blogger範本中,可以在<head></head>之間載入全網站的樣式檔與腳本檔,並加入判斷式載入各種不同網頁類型專屬的樣式檔與腳本檔。假設你的所有檔案都上傳到了http://yourhost/,並且可以直接取用,那麼範本的語法如下:

<!-- 載入全網站的樣式檔與腳本檔 -->
<script src='http://yourhost/blogger.js' type='text/javascript'/>
<link href='http://yourhost/blogger.css' rel='stylesheet' type='text/css'/>

<b:if cond='data:blog.pageType == &quot;index&quot;'>
    <b:if cond='data:blog.url == data:blog.homepageUrl'>
        <!-- 載入首頁的樣式檔與腳本檔 -->
        <script src='http://yourhost/blogger-index.js' type='text/javascript'/>
        <link href='http://yourhost/blogger-index.css' rel='stylesheet' type='text/css'/>
    <b:else/>
        <!-- 載入列表的樣式檔與腳本檔 -->
        <script src='http://yourhost/blogger-list.js' type='text/javascript'/>
        <link href='http://yourhost/blogger-list.css' rel='stylesheet' type='text/css'/>
    </b:if>
</b:if>
<b:if cond='data:blog.pageType == &quot;archive&quot;'>
    <!-- 載入列表的樣式檔與腳本檔 -->
    <script src='http://yourhost/blogger-list.js' type='text/javascript'/>
    <link href='http://yourhost/blogger-list.css' rel='stylesheet' type='text/css'/>
</b:if>
<b:if cond='data:blog.pageType == &quot;item&quot;'>
    <!-- 載入文章的樣式檔與腳本檔 -->
    <script src='http://yourhost/blogger-item.js' type='text/javascript'/>
    <link href='http://yourhost/blogger-item.css' rel='stylesheet' type='text/css'/>
</b:if>
<b:if cond='data:blog.pageType == &quot;static_page&quot;'>
    <!-- 載入靜態網頁的樣式檔與腳本檔 -->
    <script src='http://yourhost/blogger-static-page.js' type='text/javascript'/>
    <link href='http://yourhost/blogger-static-page.css' rel='stylesheet' type='text/css'/>
</b:if>

實際上可能不會應用到這麼多種類型的檔案,像我自己沒有使用靜態網頁,所以並沒有判斷static_page。

不要直接修改Blogger範本的理由

有了條件標記之後,其實也能夠直接針對Blogger範本內文進行變更。例如,在某些類型中不輸出導覽列的標記內容。

在大部分情況中,我並不建議這樣做。一來是管理上比較不方便。網頁的樣式與腳本都經過全網站與各別類型的檔案分開管理,這樣子可以明確地知道在什麼情境下會有什麼樣的效果。

二來,由於Blogger範本的條件標記不支援多重條件,因此當條件變多的時候,就得重複撰寫條件的內容。例如我將搜尋、標籤列表與存檔網頁都視為列表類型,但實際上他們的條件判斷都不一樣,因此內容都必須重複撰寫。上面的檔案引用語法中blogger-list.css跟blogger-list.js寫了兩次,就是這個意思。

不過,如果是判斷文章內文是否顯示的時候,我會建議你直接寫在Blogger範本中。

各種類型中的文章內文顯示

預設的Blogger範本中,顯示文章內文的語法通常會這樣表示:

<div class='post-body entry-content'>
    <data:post.body/>
</div>

其中,post.body會包含文章全部的內文。像我Blog每篇往往動輒二、三千字,一個列表網頁展示個十篇文章左右的數量,文章內文就會大到難以下載。

因此我建議只有在首頁、文章跟靜態網頁這三種網頁類型的時候才顯示文章內文。語法如下:

<div class='post-body entry-content'>
    <b:if cond='data:blog.url == data:blog.homepageUrl'>
        <data:post.body/>
    </b:if>
    <b:if cond='data:blog.pageType == &quot;item&quot;'>
        <data:post.body/>
    </b:if>
    <b:if cond='data:blog.pageType == &quot;static_page&quot;'>
        <data:post.body/>
    </b:if>
</div>

在上面各種網頁類型需求中,我對首頁的需求是想要文章內文只顯示摘要。如果你有用Blogger預設的語法來插入繼續閱讀的摘要點,那麼這樣子就足以讓他在首頁時只顯示摘要。如果你跟我一樣,不習慣每次寫文章都還要手動設定摘要點,那麼你可以用我之前寫的JavaScript自動摘要程式看看。


結語

經過這一串的研究與改造之後,希望「布丁布丁吃什麼?」blog能帶給大家更好的瀏覽體驗。不過與其說是對大家好,不如說是對我自己的需求來改善。因為我常常需要回頭找blog寫過的東西,但是以前沒有針對網頁類型判斷的時候,過大的網頁內文量總是會讓網頁讀到快當掉,令我非常難過。現在讀取速度應該是比較好了吧?不知道大家的看法如何呢?

歡迎一起討論Blogger Hack的技巧吧!

總共25 則留言 ( 我要發問 , 隱藏留言 顯示留言 )

  1. 請問大大
    有沒有辦法修改標頭(header)的超連結,目前預設都是回到blogspot的網誌頁面,我想要修改超連結的網址或是讓超連結失效不知是否有辦法達到?

    回覆刪除
  2. To gibsonsg61re:

    把範本中以下程式碼:

    <a expr:href='data:blog.homepageUrl'><data:title/></a>

    去掉a標籤之後:

    <data:title/>

    就可以取消標頭的超連結了

    回覆刪除
  3. 不好意思我想請教一下^^
    想請問有沒有辦法將首頁變更為某篇指定標籤文章or網頁呢?

    回覆刪除
  4. To 7樓匿名,

    預設首頁的輸入資料會是最新日期排序下來

    要改的話,我想應該只能從程式碼,使用JavaScript去load某個page或label來做剖析吧。
    例如像是插入最新文章列表:http://pulipuli.blogspot.tw/2009/04/bloggerjquery.html

    我最近也剛好想要大改blog首頁,我不想要首頁進來看到的是一篇一篇文章,想要做得比較像是個人的網頁這樣

    回覆刪除
  5. 沒錯就是想像個人網頁那樣o_O
    目前是使用隱藏最底下的首頁較新較舊文章&顯示一篇文章來達成XD
    期待您研究成功XD

    回覆刪除
  6. To 9樓匿名,

    好的,等我研究出一些結果……
    這個Blog的首頁就會大改了XD

    回覆刪除
  7. 請問若要指定某一頁當首頁要如何做呢
    Blogger預設首頁是以文章列表
    但我想製作一個網頁指定預設是首頁
    謝謝

    回覆刪除
    回覆
    1. To Polin:

      有兩個做法,一個比較難,另一個比較簡單。

      a. 困難做法:條件判斷

      <div class='post-body entry-content'>
          <b:if cond='data:blog.url == data:blog.homepageUrl'>
              <!-- 這邊寫上首頁才能夠顯示的網頁 -->
          </b:if>
          <b:else/>
              <!-- 這邊寫上正常運作的網頁內容 -->
          </b:if>
      </div>

      這是最徹底的方法。但如果你看不懂Blogger範本組成方式的話,那我不建議這樣做。

      b. 簡單做法:跳轉

      <b:if cond='data:blog.url == data:blog.homepageUrl'>
          <meta http-equiv="refresh" content="0;url=<你指定要跳轉的網址>" />
      </b:if>

      這段程式碼請插入在</head>之前即可。
      這樣子的話,只要來到首頁的時候,都會被強制跳轉到你所指定的網址。
      這樣方法對SEO不太好,搜尋引擎會覺得奇怪。但是設定簡單,所以推薦你使用。

      刪除
  8. 布丁大大,這篇真的很讚,解決我落落長的內文!

    可是解決內文的同時,不知道要怎樣做,才能顯示圖片? (我想隱藏所有內文,只顯示圖片)

    回覆刪除
    回覆
    1. 你好,

      使用CSS來隱藏文字就可以了?

      如果你是為了商業營運,想要一些客製化的特殊規則
      那可能使用能夠提供更多客製化功能的Blog系統,像是WordPress
      或是去找Blogger客製化的專家,像是WFU Blog https://www.wfublog.com/2013/06/service-suggest-cooperation.html

      刪除
  9. 作者已經移除這則留言。

    回覆刪除
  10. 抱歉~ 大概我沒說清楚!! 我的意思是,不是要在範本上判斷,是要直接使用在 CSS 或前端 script 上

    不過、想一想 好像也沒有這個必要 ~ 哈!!

    #index-view div#main {
    width: 60%;
    }
    #index-view div#sidebar-wrapper {
    width: 35%;
    }

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

    #item-view div#main {
    width: 90%;
    }
    #item-view div#sidebar-wrapper {
    display:none;
    }

    回覆刪除
    回覆
    1. To 灰鴿,

      能的話還是會建議在範本上先做處理比較好

      範本上的語法設定是後端程式碼,在範本上設定可以帶來兩個好處:
      1. 精簡輸出到前端的程式碼大小,提升網頁讀取的效率:不是屬於這一頁的資料就不會輸出到前端。用CSS隱藏雖然表面上看不到,但使用者瀏覽器還是要載入這些資料。
      2. 降低前端網頁的運算量:你使用CSS隱藏的做法會增加前端瀏覽器的運算負荷。即使這對現代電腦來說微不足道,但能降低使用者的讀取門檻,還是功德一件

      如果想要鑽研製作有效率的網頁,那可以試著使用PageSpeed Insights
      https://developers.google.com/speed/pagespeed/insights/?utm_source=analytics

      加油

      刪除

  11. 你真是個善心人士!!
    我知道、先在範本上做處理,等於是在寫 PHP 或 ASPX,你要什麼我就只給你什麼。

    現在、我都已改用 Blogger 5種新的 pageType 做判斷

    data:view.isPreview

    data:view.isSingleItem

    data:view.isArchive

    data:view.isLabelSearch

    data:view.isSearch


    前車之鑑。像 CSS 2 的屬性 & HTML 2 標籤,現在的瀏覽器已不在支援,jquery 也是一樣,有些早期版本的 Function 也都不能用了 ...

    回覆刪除
    回覆
    1. To 灰鴿,

      原來現在Blogger範本擴充了這麼多種變數了,更好用了呢

      我看到別人整理的表格,裡面還有更多判斷頁面類型的方法
      https://www.share-collections.com/2020/09/blogger-cheatsheet-dataview.html

      謝謝您的補充

      刪除
  12. 你好:
    請問一下,如果當我輸入部落格的網址,例如:https://yourhost.blogger.com
    然後,我想要直接開啟自己在部落格中的某一網頁檔案(a.html)當成這個部落格的首頁,
    也就是輸入https://yourhost.blogger.com後,以a.html當成這個部落格的第一個出現的頁面,作為首頁。
    請問,這要怎麼設定阿??
    謝謝您!!煩請指點一下

    回覆刪除
    回覆
    1. 這問題? 讓我來幫房東回覆 ~
      第一個、先把 Blog1 設成 cond='not data:view.isHomepage' 在首頁不要出現

      接著、放上這個小工具 https://e-717.blogspot.com/2021/07/blogger.html 放在主題區段 Blog1 上方

      刪除
    2. To 灰鴿,

      我可能直接會使用JavaScript。

      在任意地方插入以下程式碼:
      https://pulipulichen.github.io/blog-pulipuli-info-data-2021/08/direct-index-to-a-html/js-to-a-html.txt

      或著是在Blogger範本內加入以下程式碼:
      https://pulipulichen.github.io/blog-pulipuli-info-data-2021/08/direct-index-to-a-html/blogger-tag-to-a-html.txt

      -----------

      如果是在自己的伺服器上,就可以調整伺服器的設定中,作爲預設網頁的程式碼。
      如果是Apache的話,可以修改DirectoryIndex的設定。
      詳細設定可以看:https://httpd.apache.org/docs/2.4/mod/mod_dir.html

      不過這個方法不能在Blogger使用。

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

      這樣應該就可以了。

      刪除
    3. 他的提問 ~ https://yourhost.blogger.com ,所以我認為是在問 : blogger

      這樣做和 自訂網域、重新導向一樣,再也無法回到 網誌首頁,讀取摘要索引頁

      <b:if cond='data:view.isHomepage'>
      <script>
      location.href = "/a.html"
      </script>
      </b:if>

      其實、閹了Blog1 之後 假如是我會在 <body> 之後、 直接寫上

      <b:if cond='data:view.isHomepage' >
      <div> 首頁內容</div>
      </b:if>

      刪除
    4. 咦 ?! 效果好像都一樣,都回不去了,除非在URL上再動手腳 https://pic.pimg.tw/e717/1408664231-2612678349.gif

      刪除
    5. To 灰鴿,

      其實我認爲原PO就是不想要看到摘要頁耶。

      雖然Blogger是寫blog用的,習慣看blog的人都會覺得第一頁就應該是近期文章的摘要。
      但也有很多人拿Blogger架站,那第一頁就應該是靜態頁面的介紹,其中有個連結才連到各個blog文章。

      如果要改成文章摘要頁面,也許可以搭配search來顯示

      例如以下連結會顯示2090年前我Blog最新的10篇文章:
      https://blog.pulipuli.info/search?updated-max=2090-04-29T00:15:00%2B08:00&max-results=10

      刪除