AndroidでWebView画面をPDF保存する
はじめに
はじめまして、2022年4月よりスペースマーケットでアプリエンジニアを担当していますseoと申します。
弊社では「スペースシェアをあたりまえに」をMISSIONに、スペースシェアのプラットフォーム事業を運営しております。
その中で、法人のお客様のご利用も多く、利用前の見積書や利用後の領収書発行のニーズもたくさんございます。
今回は、見積書や領収書などWebView画面をPDFファイルとして、ローカルストレージへ保存する機能を実装しましたので、実装の中身(Android編)をご紹介できたらと思います!
最新版アプリにてご利用できますので、ぜひこちらのリンクよりダウンロードして、たくさんの素敵なスペースを利用してみてください✨
ゴール
予約一覧画面から「領収書を表示する」ボタンを押すと、
WebViewの領収書が表示され、
メニューから「PDFをダウンロード」を選択すると、
保存する画面が出てきます
実装してみよう
まずは、PDF化したWebViewを表示するActivityの作成です。
(Jetpack Composeでの記事はまたの機会に🙇♂️)
それぞれonCreate
内のメソッドの役割を見ていきましょう!
class PdfWebActivity : AppCompatActivity() {
companion object {
private const val KEY_URL: String = "KEY_URL"
fun openUrl(from: Context, url: String) {
Intent(from, PdfWebActivity::class.java).let {
it.putExtra(KEY_URL, url)
from.startActivity(it)
}
}
}
private lateinit var binding: ActivityWebBinding
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = DataBindingUtil.setContentView(this, R.layout.activity_web)
loadUrl()
setActionBar()
setViewPortrait()
}
}
WebViewに表示するurlのload処理ですね。
private fun loadUrl() {
val url = intent.getStringExtra(KEY_URL) ?: return
binding.webView.loadUrl(url)
}
「PDFを保存する」ボタンを表示するために、ActionBarとメニューボタンを設置します。
また、メニューボタンの項目をxmlファイルで作成しておきます。
private fun setActionBar() {
setSupportActionBar(toolbar)
supportActionBar?.run {
setDisplayHomeAsUpEnabled(true)
setHomeButtonEnabled(true)
}
}
override fun onCreateOptionsMenu(menu: Menu): Boolean {
menuInflater.inflate(R.menu.web_receipt, menu)
return true
}
表示するWeb画面がスマホサイズにレスポンシブ対応していないときは、こちらの設定を有効にすることをオススメします。いい感じにwidthをそろえてくれます。
private fun setViewPortrait() {
binding.webView.apply {
settings.javaScriptEnabled = true
settings.useWideViewPort = true
settings.loadWithOverviewMode = true
settings.builtInZoomControls = true
setInitialScale(1)
}
}
これでPDF化したいWebViewを表示することができました。
ここからがメインディッシュです!
override fun onOptionsItemSelected(item: MenuItem): Boolean {
when (item.itemId) {
R.id.menu_download_pdf -> {
val adapter = binding.webView.createPrintDocumentAdapter("保存したいファイル名"))
val printManager = getSystemService(PRINT_SERVICE) as PrintManager
printManager.print("Document", adapter, PrintAttributes.Builder().build())
}
}
return true
}
メニューボタンを押した時の動作を設定するoverride fun onOptionsItemSelected
にて、今回はmenu_download_pdf
を押下時に、PDF保存やプリントの設定ができるPrintManager
クラスをよびだします。
とういう形で、実質たった3行でPDF化をPrintManagerにまかせることができます。
この機能の実装前は、CS部門の方々が日々、問い合わせごとにメールなどで対応されていたとのことで、本当に必要な業務に集中できるようになってよかったです!
CS部門の方々、日々のご対応ありがとうございます🙇♂️
最後に
スペースマーケットでは一緒に働く仲間を募集中です!
弊社は、iOS/Android/Flutterと3つのアプリが存在するので、アプリエンジニアとしての総合力を向上させることができる環境です!
ぜひ、ご応募お待ちしております!!
スペースを簡単に貸し借りできるサービス「スペースマーケット」のエンジニアによる公式ブログです。 弊社採用技術スタックはこちら -> whatweuse.dev/company/spacemarket
Discussion