【JavaScript】在網頁上設置下載按鈕

本篇大綱

  1. 簡介
  2. 使用 HTML <a> download Attribute
  3. 通過 blob 下載圖片
  4. 通過 blob 下載 txt 檔案

簡介

稍微記錄如何在網頁上設置下載按鈕。第一個方式為使用 HTML <a> tag 原先提供的 download 屬性,但它有其限制性。另一個方法則為通過 blob 物件讓使用者能夠直接儲存檔案。

Codepen Live Demo: Download file buttons


使用 HTML <a> download attribute

1
<a href="https://i.imgflip.com/5qptjs.jpg" download="meme-filename" target="_blank">Download</a>

這裡以圖片下載為例。使用 <a> 的 download attribute 直接下載是最方便的方式。某些情況下,需要提供使用者下載的不是已經存在的檔案,而是一個鏈接,使用 <a> tag 會出現這個狀況:<a> tag 在被點擊後,瀏覽器會打開檔案,使用者需要手動 儲存檔案


通過 blob 的方式直接儲存圖片

可以通過操作 blob 物件來達到按鈕在被點擊後,儲存檔案的框框跳出,讓使用者直接儲存檔案的效果。

1
<button class="image-blob-button">Download</button>

首先 fetch 需要下載的 URL 獲得 blob, 接著使用 URL.createObjectURL 來創建 objectURL. 這時候回傳的結果會是:

1
"blob:https://cdpn.io/211925a7-4b2e-42a7-b2f0-6fc043dc7bbe"

接著創造 <a> tag, 其下載鏈接為剛剛創造出來的 objectURL. 檔名可以使用 .download 來設定。接下來將創造好的鏈接塞到 body 內,再觸發它就可以達到想要的效果了。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
//JavaScript

const imageBlobButton = document.querySelector('.image-blob-button')
imageBlobButton.addEventListener('click', downloadImage)

async function downloadImage() {
// fetch the image blob
const url = 'https://i.imgflip.com/5qptjs.jpg'
const response = await fetch(url)
const blob = await response.blob()

// create an objectURL
const blobURL = URL.createObjectURL(blob)

// set <a> tag's href to blob url
const link = document.createElement('a')
link.href = blobURL
link.download = "meme"

// Append link and trigger the download
document.body.appendChild(link)
link.click()
document.body.removeChild(link)
}

下載 text file

如果要下載 txt 檔案,或是將特定的字串轉換成 txt 檔案下載,使用的方法與剛才提到的方式類似。這裡下載不是 url 而是一個字串 / 檔案,因此要先創造一個新的 blob 物件,其餘包括取得 objectURL 的方式和觸發點擊的寫法則與 url 的相同。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
const context = "helllo, let's download some text!"
const txtBlobButton = document.querySelector('.txt-blob-button')
txtBlobButton.addEventListener('click', downloadTxt)

function downloadTxt() {
// first argument should be array
blob = new Blob([context], {type: 'text/plain'})
let blobUrl = URL.createObjectURL(blob)
let link = document.createElement("a")

link.href = blobUrl
link.download = "text"

document.body.appendChild(link)
link.click()
document.body.removeChild(link)
}

實際使用案例

之前在實習專案開發中遇到需要設置下載按鈕的功能,找到了這個解法,又想起之前做過的迷因小作品能夠用上,所以就把他加進去啦。迷因在製作好後,會回傳該迷因的鏈接,因此就可以通過 blob 的方式來讓用戶下載圖片。

順道一提,這是剛剛開始學 react 時候寫的小東西,半年後再看回覺得真的是有很大很大很大的進步空間啊。

Github repo: Winnie0609/meme-generator
Live Demo: Mene Generator

如果文章有誤,或是可以做得更好的地方,再麻煩留言告訴我啦 :)


參考資料

  1. Downloading images in the browser with Node.js
  2. Blob
  3. W3 school HTML <a> download Attribute
  4. Blob-对象介绍

Comments