攝影師:Tima Miroshnichenko: https://www.pexels.com/zh-tw/photo/html-5380664/

[網站架設] 利用 JavaScript 讓網頁每個連結開新的分頁

先說,我這篇的檔案完完全全是照這篇文章:Jekyll 新分頁開啟超連結
之前太習慣 WordPress簡單的介面設定,碰到 Jekyll 不熟悉的工具連這個小功能都得求助XD

為什麼要多新的分頁

不論是何種型態的網站,大部分的站長都會希望網友們能夠在自己的地盤待久一點。但有個惱人的狀況是:一旦有了連結,沒有特別去設定的話,整個網頁就跳轉到別的地方了。萬一網友也在這個跳轉出去的網頁久待,很快的他對你的網頁就只是個過客,很可能不小心看完手殘就把整個網頁關掉(我就是那個網友)。
當然還有其他更多的因素,較常見的是有放廣告的網站,為了增加廣告商們的曝光率,最簡單的方式就是讓網友們久留,如此也才能賺到錢。

讓網頁中的連結都開新分頁

在一般可以直接編輯 HTML 標籤的網頁,要開新分頁很簡單,在 <a> 標籤後面加上 target="_blank" 即可。而若是 WordPress 或是類似的平台,看使用的編輯器是哪一種,通常食指動一動就設設定好了。

例如 <a href="google.com" target="_blank"></a> 就是另開一個新分頁,連到 google.com,而 js 的按鈕寫法就是 <button type="button" onclick="window.open('google', '_blank')">BUTTON</button>

用 Jekyll 這工具生成的靜態網頁做法也很類似,因為我是用 Markdown 寫的文章,只要在連結後面加上 {:target="_blank"} 即可,完整寫法為:[link][url]{:target="_blank"}

但是,當初會想用這種筆記部落格形式,最大的初衷就是想省事,每次加個參考資料都要加一次 {:target="_blank"} 也是挺煩的,所以就用了網友的方法(我是完完全全照做喔,建議可以直接看原文章)。

新增一個 JavaScript 檔案

用 JavaScript 弄個可以開新分頁的檔案,我自己的 GitHub Pages 是把這個檔按放在 /asserts/js/ 裡面,取名叫做 new-tab.js

function handleExternalLinks () {
  var host = location.host
  var allLinks = document.querySelectorAll('a')
  forEach(allLinks, function (elem, index) {
    checkExternalLink(elem, host)
  })
}

function checkExternalLink (item, hostname) {
  var href = item.href
  var itemHost = href.replace(/https?:\/\/([^\/]+)(.*)/, '$1')
  if (itemHost !== '' && itemHost !== hostname) {
    item.target = '_blank'
  }
}

// NodeList forEach function
function forEach (array, callback, scope) {
  for (var i = 0; i < array.length; ++i) {
    callback.call(scope, array[i], i)
  }
}

handleExternalLinks ()

加入檔案

既然生了他,就要利用他。
以我自己的 GitHub Pages 來說,我要在 _layout/default.html 中引入這個 JavaScript 檔,有在寫網頁的人對這個步驟應該不陌生。至於為什麼是default.html,是因為沒意外的話他應該是 Jekyll 整個網站會用到的模板,這個部份每個人都不一樣,建議先確定自己的網站設置。以我目前的情況,在 default.html 引入,整個網站都會執行。

至於加在 <body> 還是 <head>… 這個部份印象中似乎有些微差距,但我之後應該會寫篇文章再深入討論。目前我是粗略地分:沒有要立刻執行的會加在 <head>,要立刻執行的會加在 <body> 的尾端。(這觀念可能不太正確)

<html>
  <head>    ......    </head>
  <body>
  ......
  <script type="text/javascript" src="/assets/js/new-tab.js"></script>
  </body>
<html>

微解析

有鑑於直接複製貼上程式碼太廢了,既然程式短短的,還是稍微用我乾癟的腦子生個解釋吧。

這裡的概念很簡單,要抓取所有的 <a> 標籤,加上 target="_blank",但若連結是自家網站就沒有需要留住客人的顧慮,因此希望能夠過濾自家的文章。這裡原作者設計了兩個 funciton:

handleExternalLinks():處理所有收集到的外部連結
linkcheckExternalLinkJ():用來判斷是不是自己家的連結,不是的話再開分頁

function checkExternalLink (item, hostname) {
  var href = item.href  //這是要取得url
  var itemHost = href.replace(/https?:\/\/([^\/]+)(.*)/, '$1')
//利用正規表示式和replace去抓取我要的host(要拿來判斷)

//接著判斷:hostname不是空的且和網站本身的hostname不一樣
//如果條件都符合,表示連結必須要開新的分頁

  if (itemHost !== '' && itemHost !== hostname) {
    item.target = '_blank'
  }
}

這部分寫完,包在 handleExternalLinks() 中執行

function handleExternalLinks () {
//先取得網站本身的hostname和所有<a>標籤內容
//(location.host 可以取得目前造訪網頁的主機名稱)
  var host = location.host
  var allLinks = document.querySelectorAll('a')
  forEach(allLinks, function (elem, index) {
    checkExternalLink(elem, host)  //這裡就是剛寫好要做判斷的function
  })
}

最後要立刻執行,記得加上:

handleExternalLinks ()

參考

♦ Jekyll 新分頁開啟超連結
♦ 如何用javascript取得網址(URL)

讓我知道你在想什麼!

Picture of ALEX

ALEX

藍白拖愛好者,一事無成話偏多

Recent Posts

C++

NLP