0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

【Android /Kotlin】WebViewでblobURLをダウンロードできるようにする

Last updated at Posted at 2025-05-07

はじめに

AndroidのWebViewでblobURLをダウンロードできるようにする方法について解説。

  1. JavaScriptInterface.ktを作成し、Android側のダウンロード時の処理を記述
  2. download_hander.jsを作成し、javascript側の処理を記述
  3. WebView使用時に、上記2つをセット

という流れで作成を行う。

1. JavaScriptInterfaceの作成

class JavaScriptInterface(private val context: Context) {
    @JavascriptInterface
    fun base64ToFile(base64: String, mimeType: String, fileName: String) {
        Log.d("base64ToFile", "base64:$base64")

        // Base64ヘッダーを除去
        val pureBase64 = base64.substringAfter(",")

        // バイナリにデコード
        val byteArray = Base64.decode(pureBase64, Base64.DEFAULT)

        val contentValues = ContentValues().apply {
            put(MediaStore.Downloads.DISPLAY_NAME, fileName)
            put(MediaStore.Downloads.MIME_TYPE, mimeType)
            put(MediaStore.Downloads.RELATIVE_PATH, Environment.DIRECTORY_DOWNLOADS)
            put(MediaStore.Downloads.IS_PENDING, 1)
        }

        val resolver = context.contentResolver
        val uri = resolver.insert(MediaStore.Downloads.EXTERNAL_CONTENT_URI, contentValues)

        if (uri != null) {
            resolver.openOutputStream(uri)?.use { outputStream ->
                outputStream.write(byteArray)
            }

            // IS_PENDING → 0 にして公開状態にする
            contentValues.clear()
            contentValues.put(MediaStore.Images.Media.IS_PENDING, 0)
            resolver.update(uri, contentValues, null, null)
        }
    }
}
  1. download_hander.jsの作成

下記に保存

app/
└─ src/
   └─ main/
      └─ assets/
         └─ js/
            └─ download_handler.js

コードは下記

(function(blobUrl) {
    try {
        var anchors = document.querySelectorAll('a[href="' + blobUrl + '"]');
        var fileName = "file_" + Date.now() + ".bin";

        if (anchors.length > 0) {
            var downloadAttr = anchors[0].getAttribute("download");
            if (downloadAttr) {
                fileName = downloadAttr;
            }
        }

        fetch(blobUrl)
            .then(response => {
                const contentType = response.headers.get("Content-Type") || "application/octet-stream";
                return response.blob().then(blob => ({ blob, contentType }));
            })
            .then(({ blob, contentType }) => {
                var reader = new FileReader();
                reader.onloadend = function() {
                    android.base64ToFile(reader.result, contentType, fileName);
                };
                reader.readAsDataURL(blob);
            })
            .catch(error => {
                console.error("fetchエラー:", error);
            });
    } catch (e) {
        console.error("JS実行時エラー:", e);
    }
})

最後に、download_hander.jsJavaScriptInterface.ktをWebViewにセットすれば良い。

WebView使用時に上記2つをセットするコードについては、こちらに記述。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?