Phonegap - Получить фото с камеры Roll по пути
В моем мобильном приложении PhoneGap/jQuery я в настоящее время использую API камеры PhoneGaps, чтобы позволить пользователю делать снимок, который также хранится в Camera Roll. Я устанавливаю DestinationType в FILE_URI и сохраняю этот путь в локальном db. Однако FILE_URI - это путь к временному местоположению, которое уничтожается при закрытии приложения. Я думал сохранить имя изображения, а затем извлечь изображение из Camera Roll. Есть ли путь, который я могу использовать для последующего получения изображений в Camera Roll?
Я сохранял изображения как Base64 в db, но я немного устал от этого метода из-за этой заметки в PhoneGap API Doc:
Примечание. Качество изображения изображений, сделанных с помощью камеры на новее устройства неплохие. Кодирование таких изображений с использованием Base64 вызвало проблемы с памятью на некоторых из этих устройств (iPhone 4, BlackBerry Torch 9800). Поэтому, используя FILE_URI как "Camera.destinationType", настоятельно рекомендуется.
ИЗМЕНИТЬ:
Получил работу с ответом @Simon MacDonald. Вот мой урезанный код:
function capturePhoto() {
navigator.camera.getPicture(onPhotoURISuccess, onFail, { quality: 25, destinationType: Camera.DestinationType.FILE_URI });
}
function onPhotoURISuccess(imageURI) {
createFileEntry(imageURI);
}
function createFileEntry(imageURI) {
window.resolveLocalFileSystemURI(imageURI, copyPhoto, fail);
}
function copyPhoto(fileEntry) {
window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, function(fileSys) {
fileSys.root.getDirectory("photos", {create: true, exclusive: false}, function(dir) {
fileEntry.copyTo(dir, "file.jpg", onCopySuccess, fail);
}, fail);
}, fail);
}
function onCopySuccess(entry) {
console.log(entry.fullPath)
}
function fail(error) {
console.log(error.code);
}
Ответы
Ответ 1
После извлечения файла с использованием метода FILE_URI вы должны использовать File API для копирования изображения из папки temp в папку Documents и сохранения нового пути в вашей базе данных.
Итак, вы получите результат своего getPicture(), чтобы передать его в window.resolveLocalFileSystemURI(), чтобы получить FileEntry. Затем вы можете вызвать метод FileEntry.copyTo() для резервного копирования файла.
Ответ 2
Как и в случае с Cordova 1.8, это работает хорошо, см.
http://docs.phonegap.com/en/1.8.0/cordova_camera_camera.md.html#Camera
Ответ 3
Извините, что мне пришлось создать отдельный пост, потому что у меня недостаточно репутации для комментариев.
Спасибо Симону за совет и Кейси за решение.
Я работал над приложением Кордовы, которое требует, чтобы я сделал снимок на iOS, сохраните его в каталоге и ссылку на локальное хранилище, к которому вы сможете получить доступ позже. После того, как пользователь отправит изображение, приложение должно удалить его из каталога.
Здесь добавляются коды о том, как вы можете это сделать, а также о том, как вы можете просматривать папку "Документы проекта".
Вы можете получить полный каталог изображения, которое вы хотите удалить, с помощью $('# pictureid'). attr ('src').
function deletePic(file){
console.log("deleting: "+file+"...");
var file = "photos/"+file.toString().split('/').slice(-1)[0]; //gets photo name
window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, function(fileSys){
fileSys.root.getFile(file,
{create:false},
function(entry){
entry.remove();
}, resOnErrorDelete);
},
resOnErrorDelete);
}
function resOnErrorDelete(error) {
console.log("resOnErrorDelete: "+error.code);
}
В противном случае, если у вас есть форма с несколькими вложениями фотографий, вы можете захотеть предоставить созданную вами папку "Документы", чтобы сохранить фотографии с уникальным именем. Таким образом, вы можете удалить всю папку после отправки пакета фотографий, а не удалять их по одному.
function deleteFolder(folder){
window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, function(fileSys){
fileSys.root.getDirectory(folder,
{create:true, exclusive: false},
function(entry){
entry.removeRecursively();
}, resOnErrorDelete);
},
resOnErrorDelete);
}
function resOnErrorDelete(error) {
console.log("resOnErrorDelete: "+error.code);
}
Что касается доступа к папке "Документы проекта", вам необходимо отредактировать plist, чтобы включить "Общий доступ к файлам iTunes"
Перейдите в [project_folder]/platform/ios/[имя_проекта]/[имя_проекта] -Info.plist.
Щелкните правой кнопкой мыши и откройте с помощью XCode.
Вы увидите таблицу ключей. Щелкните правой кнопкой мыши в любом месте ниже таблицы и добавьте строку. Будет создана новая строка. Дважды щелкните по ключу и введите UIFileSharingEnabled. Он автоматически изменится на Приложение поддерживает обмен файлами iTunes, поместите это значение ключа в ДА.
Теперь, если вы перейдете в iTunes под приложениями устройств iOS, прокрутите весь путь вниз, чтобы увидеть раздел "Общий доступ к файлам", где вы можете увидеть свою папку. Тем не менее, это просто для вас, чтобы "Сохранить", но без редактирования.
Надеемся, что эта дополнительная информация поможет. Мне потребовалось 2 дня исследований, чтобы узнать.
Ответ 4
Совместное использование моей версии, которая использует promises и resolveLocalFileSystemURL, кроме resolveLocalFileSystemURI, потому что вторая устарела. Он также использует оригинальное имя файла в новом созданном.
function copyPhotoToAppDir(imageURI) {
if(!imageURI){
console.warn("You need to pass imageURI");
return;
}
var fileNameSplit = imageURI.split("/"),
fileName = fileNameSplit[fileNameSplit.length - 1],
deferred = $q.defer();
var copyPhoto = function(fileEntry) {
window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, function(fileSys) {
fileSys.root.getDirectory("photos", {create: true, exclusive: false}, function(dir) {
fileEntry.copyTo(dir, fileName, onCopySuccess, onFileFail);
}, onFileFail);
}, onFileFail);
};
var onCopySuccess = function onCopySuccess(entry) {
console.log("NEW PATH", entry.fullPath);
deferred.resolve(entry.fullPath);
};
var onFileFail = function (error) {
console.log("COPY FAIL", error);
deferred.reject();
};
window.resolveLocalFileSystemURL(imageURI, copyPhoto, onFileFail);
return deferred.promise;
}
Использование:
var uri = "path1";
copyPhotoToAppDir(uri).then(function(newURI){
console.log(newURI);
});
Использование нескольких URI:
var uriArr = ["path1", "path2"];
copyPhotoPromises = [];
uriArr.forEach(function(val){
copyPhotoPromises.push(copyPhotoToAppDir(val));
});
$q.all(copyPhotoPromises).then(function(values){
console.log("Array with new paths", values);
});
Новые URI файлы будут сохранены как "/photos/fileName.jpg".
Чтобы получить абсолютный путь, вы можете использовать:
cordova.file.documentsDirectory + newFileUri.substring(1);
Я использую $q от angular здесь для обработки promises, но его можно легко изменить на jQuery.
deferred = $q.defer();
необходимо изменить на:
deferred = jQuery.Deferred();
Приветствия