Reputation: 10067
I'm trying to get the base64 from an image that picked from the album on my phone, but I cannot make it work:
I tried this:
window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, function(fileSystem) {
console.log("0");
fileSystem.root.getFile(imageURI, null, function(fileEntry) {
console.log("1");
fileEntry.file(function(file) {
console.log("2");
var reader = new FileReader();
reader.onloadend = function(evt) {
console.log("Read complete!");
image64.value = Base64.encode(evt.target.result);
};
reader.readAsText(file);
}, failFile);
}, failFile);
}, failSystem);
Although the image is displayed correctly.. I receive an error from this function:
fileSystem.root.getFile(imageURI, null, function(fileEntry)
And the error is: FileError.ENCODING_ERR
I know that code doesn't look pretty. But I don't know how to get the Base64 encoding from an imageURI.
Upvotes: 4
Views: 11670
Reputation: 22595
The cordova-plugin-file implements the HTML5 File API, and that uses callback API's. I prefer promises so I rewrote the method using the $q library:
function getContentAsBase64(fileUrl) {
//Using $q to change the API so that getContentAsBase64 returns a promise
var deferred = $q.defer();
//function to call when either resolve or retrieval fails
var fail = function (error) {
errorHandler(error);
deferred.reject(error);
}
//function to call when resolve file succeeded
//we have a FileEntry - get the file,
var fileResolved = function (fileEntry) {
fileEntry.file(fileSuccess, fail);
}
//function to call when file successfully retrieved
//convert to base64 string
var fileSuccess = function (file) {
var reader = new FileReader();
reader.onloadend = function (evt) {
//promise is resolved with the base64 string
deferred.resolve(evt.target.result);
};
reader.readAsDataURL(file);
};
window.resolveLocalFileSystemURL(fileUrl, fileResolved, fail);
return deferred.promise;
}
The readAsDataURL method is used to read the contents of the specified Blob or File. When the read operation is finished, the readyState becomes DONE, and the loadend is triggered.At that time, the result attribute contains the data as a URL representing the file's data as a base64 encoded string.
Usage:
var imageData;
getContentAsBase64(aq.FileUri).then(function (content) {
imageData= content;
});
Upvotes: 1
Reputation: 10067
I found the solution in Google groups. I modified it a little bit and this is the result:
var gotFileEntry = function(fileEntry) {
console.log("got image file entry: " + fileEntry.fullPath);
fileEntry.file( function(file) {
var reader = new FileReader();
reader.onloadend = function(evt) {
console.log("Read complete!");
image64.value = Base64.encode(evt.target.result);
};
reader.readAsText(file);
}, failFile);
};
window.resolveLocalFileSystemURI(imageURI, gotFileEntry, failSystem);
NOTE: It takes about 20 seconds to read a normal 5MPixel image and another 10-15 to Base64 encode it.
Upvotes: 7
Reputation: 160
The above method from SERPRO works...but i have to change
reader.readAsText(file);
to
reader.readAsDataURL(file);
Thus, line
image64.value = Base64.encode(evt.target.result);
can be removed and the base64 result can be directly extracted as
image64.value = evt.target.result;
Upvotes: 7