スマホアプリの開発に今回初めて触れました。
端末にファイルをダウンロードするのにも一苦労しました。iOSやAndroid、画像とPDFでも、使用するプラグイン含め実装方法や、動きがだいぶ異なりました。
普段スマホアプリを開発している人には当たり前の事も多いかもしれませんが、せっかくなので調べたことを備忘録に残します。
目次
以下の2つのプラグインを使用します。
ファイルダウンロードの為に使用します。その他アップロードなどの機能もあります。
ファイルの保存場所の指定に使用します。
Android
Androidでファイルの保存が完了した状態(今回はDownloadフォルダに保存させました。)
確認端末:Android Studio エミュレーター(Pixel 4)
※エミュレーターや実機でPDFを表示するのに適したアプリがインストールされていなければ表示はできません。
Android Studio エミュレーターでは「GooglPlay」マークがついているものであれば、元々PDFを閲覧可能だったので、上記確認端末を使用して確認しました。
var fileTransfer = new FileTransfer();
// 今回はdataURIを渡します
var data = 'data:image/png;base64/iVBORw0KGgoAAAANSUhEU0.....';
// Androidファイル任意の保存先(cordova.file.externalRootDirectory部分で「ファイル操作プラグイン」を使用)
var storeDirectory = cordova.file.externalRootDirectory + 'Download/';
// ファイル名 ○○.png や ○○.pdf 等
var fileName = 'XXXXXXX.png';
// 保存先パス(ディレクトリ+ファイル名)
var filePath = storeDirectory + fileName;
// ダウンロード
fileTransfer.download(
data,
filePath,
function(entry) {
console.log("ダウンロード完了: " + entry.toURL());
// entry.toURL()で得られるパスの例
file:///storage/emulated/0/Download/XXXXXXX.png
},
function(error) {
console.log("ダウンロード失敗" + error.source);
},
false,
{
headers: {
"Authorization": "Basic dGVzdHVzZXJuYW1lOnRlc3RwYXNzd29yZA=="
}
}
);
iOS
iOSもAndroidと同様のコードでダウンロードが可能ですが、ダウンロード先についてiOS独特の知識が必要で、不慣れな私はここで時間を食いました。
Androidの方は、端末で一般的に使用されている「ファイル」アプリのDownloadフォルダで、実際にダウンロードされていることが確認できました。
iOSはいろんなパス(cordova-plugin-file を使用した cordova.file.XXXXXXの部分)を試してみましたが、一向に端末で確認できる場所にダウンロードされません。。
iOSでは「サンドボックス」(端末では確認できないアプリの占有ボックス)と呼ばれる構造になっており、他アプリから閲覧できないようになっているのです。
他社製Appはすべて「サンドボックス化」されるので、ほかのAppによって保存されたファイルにアクセスしたり、デバイスに変更を加えたりすることはできません。サンドボックス化は、ほかのAppによって保存された情報が収集または変更されるのを防ぐために行われます。
Appleサポート サンドボックス化
xcodeで確認してみると、アプリのサンドボックス内に、PDFも画像もダウンロードされていることを確認しました。
後述のソースでも、entry.toURL()
で得られるパスfile:///var/mobile/Containers/Data/Application/8544A743-4870-4073-B0F...(アプリに割り振られるID)/Library/Cloud/XXXXXXX.png
を確認しても分かるように、アプリのスペースの中に保存されています。
不慣れな私は、「他アプリから閲覧できない」というところに、違和感を感じました。
いつも使用している以下の「ファイル」「写真」をアプリの一つだとして意識した事があまり無かったからです。
「ファイル」「写真」もアプリの一つで、そのアプリに開発中のアプリでダウンロードしたファイルを「共有」するという考え方になります。
先述の考え方を踏まえ、ダウンロードは、サンドボックス内だけでいいんだという方はAndroidとほぼ同じですが、以下のコードでダウンロードが可能です。
サンドボックス内でなく、端末に保存したいのだ!いう方はこの後紹介するプラグインを導入することで解決可能です。
var fileTransfer = new FileTransfer();
// 今回はdataURIを渡します
var data = 'data:image/png;base64/iVBORw0KGgoAAAANSUhEU0.....';
// iOSファイル任意の保存先(cordova.file.syncedDataDirectory部分で「ファイル操作プラグイン」を使用)
var storeDirectory = cordova.file.syncedDataDirectory;
// ファイル名 ○○.png や ○○.pdf 等
var fileName = 'XXXXXXX.png';
// 保存先パス(ディレクトリ+ファイル名)
var filePath = storeDirectory + fileName;
// ダウンロード
fileTransfer.download(
data,
filePath,
function(entry) {
console.log("ダウンロード完了: " + entry.toURL());
// entry.toURL()で得られるパスの例
file:///var/mobile/Containers/Data/Application/アプリに割り振られるID/Library/Cloud/XXXXXXX.png
},
function(error) {
console.log("ダウンロード失敗" + error.source);
},
false,
{
headers: {
"Authorization": "Basic dGVzdHVzZXJuYW1lOnRlc3RwYXNzd29yZA=="
}
}
);
別のプラグインを導入することで端末へのダウンロードが可能です。
実際に動きを試したものとそうでないものがありますが紹介させていただきます。
iPhoneユーザーの方は何かファイルや画像をダウンロード使用したときに以下をよく見かけませんか?
端末へダウンロードさせるために、以下のプラグインを使用して、このアクション子画面を表示させることが可能です。
このプラグインの詳細については以下の記事にまとめています。
cordovaプラグイン「previewAnyFile」の動きをスクリーンショットで紹介上記のpreviewAnyFileプラグインと同じようなアクション子画面が表示されます。
SNSへの共有だけではなく、「写真」アプリ等への共有が可能です。