Ionic- Angular.js Capture and Submit: Blank Images
So, I was able to use a custom directive to upload images to my server via Angular.js. I also managed to implement the camera functionality from Cordova. Now I am trying to connect them, but when I post images to the server, they are stored as null. I believe the problem is that I was using an input field to get the image and it was getting the full Object, and now I only get the path to the image after I take a shot and send it. My problem is that I don't really understand how I could convert the object path IF this is the problem?
index.html
<form class="form-horizontal" role="form">
<button class="picButton" ng-click="getPhoto()" class="button button-block button-primary">Take Photo</button>
<img ng-src="{{lastPhoto}}" style="max-width: 100%">
...
</form>
controllers.js
$scope.getPhoto = function() {
Camera.getPicture().then(function(imageURI) {
console.log(imageURI);
$scope.lastPhoto = imageURI;
$scope.upload(); <-- call to upload the pic
},
function(err) {
console.err(err);
}, {
quality: 75,
targetWidth: 320,
targetHeight: 320,
saveToPhotoAlbum: false
});
};
$scope.upload = function() {
var url = '';
var fd = new FormData();
//previously I had this
//angular.forEach($scope.files, function(file){
//fd.append('image',file)
//});
fd.append('image', $scope.lastPhoto);
$http.post(url, fd, {
transformRequest:angular.identity,
headers:{'Content-Type':undefined
}
})
.success(function(data, status, headers){
$scope.imageURL = data.resource_uri; //set it to the response we get
})
.error(function(data, status, headers){
})
}
When I print $ scope.lastPhoto I get the path to the image: file: ///var/mobile/Applications/../tmp/filename.jpg
EDIT
Request header:
------WebKitFormBoundaryEzXidt71U741Mc45
Content-Disposition: form-data; name="image"
file:///var/mobile/Applications/C65C8030-33BF-4BBB-B2BB-7ECEC86E87A7/tmp/cdv_photo_015.jpg
------WebKitFormBoundaryEzXidt71U741Mc45--
Should this be causing the problem? Since I can see that I am sending the path, but not the image itself.
Before the change, I used a custom directive and used $ scope.files to add my request to the upload function:
<input type="file" file-input="files" multiple onchange="angular.element(this).scope().filesChanged(this);upload();">
<button ng-click="upload()">Upload</button>
source to share
I resolve with this code:
$scope.getPhoto = function() {
navigator.camera.getPicture(onSuccess, onFail, { quality: 75, targetWidth: 320,
targetHeight: 320, destinationType: 0 });
//destination type was a base64 encoding
function onSuccess(imageData) {
//preview image on img tag
$('#image-preview').attr('src', "data:image/jpeg;base64,"+imageData);
//setting scope.lastPhoto
$scope.lastPhoto = dataURItoBlob("data:image/jpeg;base64,"+imageData);
}
function onFail(message) {
alert('Failed because: ' + message);
}
}
function dataURItoBlob(dataURI) {
// convert base64/URLEncoded data component to raw binary data held in a string
var byteString = atob(dataURI.split(',')[1]);
var mimeString = dataURI.split(',')[0].split(':')[1].split(';')[0]
var ab = new ArrayBuffer(byteString.length);
var ia = new Uint8Array(ab);
for (var i = 0; i < byteString.length; i++)
{
ia[i] = byteString.charCodeAt(i);
}
var bb = new Blob([ab], { "type": mimeString });
return bb;
}
after this use add data to your forms like this:
formData.append('photo', $scope.lastPhoto, $scope.publish.name+'.jpg')
This code works on IOS without issue.
source to share
What I ended up doing was to add destinationType: Camera.DestinationType.DATA_URL to the parameters of the getPhoto function and return a base64 image representation, which I then send to the server and save to TextField () (Django):
$scope.getPhoto = function() {
Camera.getPicture().then(function(imageURI) {
console.log(imageURI);
$scope.lastPhoto = imageURI;
$scope.upload(); <-- call to upload the pic
},
function(err) {
console.err(err);
}, {
quality: 75,
targetWidth: 320,
targetHeight: 320,
saveToPhotoAlbum: false,
destinationType: Camera.DestinationType.DATA_URL
});
};
Also, when working with Base64 images, remember to call:
<img ng-src="data:image/jpeg;base64,{{image}}" />
source to share