Downloading
Managing PDF and other files is a common task in an application and depending on the task you may need various plugins to accomplish your needs. This tutorial is applicable for PDFs, Images or any file types.
This tutorial covers:
You can try out these features in this sample repository.
Downloading Options
There are various ways you could download a file in a Capacitor app:
- Use the
fetch
API - Use a library like Axios or Angular's HTTPClient
- Use the Capacitor HTTP plugin
- Use the Capacitor Filesystem plugin
DownloadFile
method
However, there are some caveats to some of these approaches:
- Using
fetch
,Axios
orHttpClient
require the right CORS setup to allow downloading the PDF. Capacitor HTTP
is limited by the amount of memory on the device to download and write a Base 64 encoded PDF. It also does not have a way to indicate progress of download.
Best Way to Download
The best approach is to use the Capacitor Filesystem plugin, and it's DownloadFile
method.
Below we download the file from a url
, setting path
to the filename we want the file to be stored as on the device.
_10import { Directory, Filesystem } from '@capacitor/filesystem';_10_10..._10_10const { path } = await Filesystem.downloadFile({_10 directory: Directory.Cache,_10 path: 'mypdf.pdf',_10 url_10 });
When it has downloaded the file it will return the path
. This can be used to share the PDF or open it.
Download Progress
To display a progress indicator in the UI we can use the ion-progress-bar
Ionic component:
_10@if (downloading) {_10<ion-progress-bar [value]="progress"></ion-progress-bar>_10}
In this Angular 17 example we display the progress bar only if we are downloading
. We need to set the value
property to a value between 0 and 1 which is done using the progress
event:
_10import { NgZone } from '@angular/core';_10..._10constructor(ngZone: NgZone) {_10 Filesystem.addListener('progress', (progressStatus) => {_10 ngZone.run(() => {_10 this.progress = progressStatus.bytes / progressStatus.contentLength;_10 });_10 });_10}
You will notice that in this Angular Component:
- We use
ngZone
to tell Angular that the we are making changes to something in the view (theprogress
variable). This is only needed for Angular as events that are emitted from Capacitor are not captured by Angular. - We calculate the progress by dividing
bytes
bycontentLength
from theProgressStatus
object that is given when theprogress
event occurs.
Next, we'll need to modify our downloadFile
method to make sure it is emitting its progress by setting progress
to true
:
_10this.downloading = true;_10_10const { path } = await Filesystem.downloadFile({_10 directory: Directory.Cache,_10 progress: true,_10 path: 'mypdf.pdf',_10 url,_10});_10_10this.downloading = false;
You can try out the downloadFile features in this sample repository.