Uploading a file with AngularJS and bluimp on success callback of another form
ajax-upload, angularjs, angularjs-directive, angularjs-service
Solution
Blueimp has an AngularJS version of jQuery File Upload available.
It includes a `fileUpload` directive and a `FileUploadController` with a `submit()` method that you can call manually.
You can see a working version at http://blueimp.github.io/jQuery-File-Upload/angularjs.html.
One thing you should pay attention to: make sure you load all .js files from the example in the correct order to avoid problems (cf. source of the example page).
Hope that helps!
UPDATE AFTER YOUR COMMENT:
When using the AngularJS version of jQuery File Upload, you create a form tag with the `file-upload` attribute like this:
<!-- Create a file upload form with options passed in from your scope -->
<form data-file-upload="options" data-ng-controller="YourController">
<!-- This button will trigger a file selection dialog -->
<span class="btn btn-success fileinput-button" ng-class="{disabled: disabled}">
<span>Add files...</span>
<input type="file" name="files[]" multiple="" ng-disabled="disabled">
</span>
<!-- This button will start the upload -->
<button type="button" class="btn btn-primary start" data-ng-click="submit()">
<span>Start upload</span>
</button>
<form>
Then in your controller you can assign the options for the jQuery File Upload like this:
angular.module('yourModule')
.controller('YourController', [$scope, function($scope){
// Options you want to pass to jQuery File Upload e.g.:
$scope.options = {
maxFileSize: 5000000,
acceptFileTypes: /(\.|\/)(gif|jpe?g|png)$/i
};
}]);
You can assign the `submit()` handler to any `ng-click` attribute as long as it is inside the form (and thus can access the method).
Let me know if you need further help...
EXTRA SAMPLE CODE FOR SUCCESS CALLBACK:
If you need to run a callback function after all uploads have been completed, you can listen to the `fileuploadstop` event that is broadcasted by Blueimp:
// Listen to fileuploadstop event
$scope.$on('fileuploadstop', function(){
// Your code here
console.log('All uploads have finished');
});
Hope that helps!
Problem
I have followed the following tutorial in order to integrate the notorious bluimp jQuery file uploader in my AngularJS project. After some research I found that in the options array, witihn the jquery.fileuploader.js file, there is an option called autoUpload, which when set to true upload the file automatically. I tried to disable it(false, undefined), but quickly I learned out that this causes the upload not to function at all, not even on the form submit. I need to trigger the upload manually, say within another callback, or by a click event. can that be done?. code: ``` app.directive("fileupload", function() { return { restrict: "A", scope: { done: "&", progress: "&", fail: "&", uploadurl: "=", customdata: "&" }, link: function(scope, elem, attrs) { var uploadOptions; uploadOptions = { url: scope.uploadurl, dataType: "json" }; if (scope.done) { uploadOptions.done = function(e, data) { return scope.$apply(function() { return scope.done({ e: e, data: data }); }); }; } if (scope.fail) { uploadOptions.fail = function(e, data) { return scope.$apply(function() { return scope.fail({ e: e, data: data }); }); }; } if (scope.progress) { uploadOptions.progress = function(e, data) { return scope.$apply(function() { return scope.progress({ e: e, data: data }); }); }; } return elem.fileupload(uploadOptions).bind("fileuploadsubmit", function(e, data) { return data.formData = { JSON.stringify(scope.customdata()) }; }); } }; }); app.service('uploadService', function(authService) { var initializeFn, processFn; initializeFn = function(e, data, process) { var upload; return upload = { message: '', uploadurl: authService.getBaseUrl() + '/applications/', status: false }; }; processFn = function(e, data, process) { var file, upload; upload = {}; upload.successData = []; upload.status = true; upload.error = false; if (process === 'done') { upload.message = data.result.result; console.log(data); file = data.result.resume; upload.successData = { // name: file.name, // fullUrl: file.url, // thumbUrl: file.thumbnail_url }; } else if (process === 'progress') { upload.message = 'Uploading....!!!'; } else { upload.error = true; upload.message = 'Please try again'; console.log(e, data); } return upload; }; return { process: processFn, initialize: initializeFn }; }); app.controller('applyCtrl', function($scope, $routeParams, uploadService){ $scope.model.formData = {}; $scope.model.formData.job = $routeParams.jobId; $scope.uploadLayer = function(e, data, process) { return $scope.uploadReturn = uploadService.process(e, data, process); }; $scope.customData = function() { return $scope.model.formData; }; return $scope.uploadReturn = uploadService.initialize(); }); ``` view: ``` <form class="applyForm" ng-submit="uploadLayer(e, data, 'progress')"> <fieldset> <div class="formLine"> <div class="wideFieldContainer"> <input id="testUpload" type="file" fileupload customdata="customData()" name="resume" uploadurl="uploadReturn.uploadurl" done="uploadLayer(e, data, 'done')" fail="uploadLayer(e, data, 'fail')" progress="uploadLayer(e, data, 'progress')" /> </div> </div> </fieldset> </form> ``` scripts loading order: ``` ... <script src="//ajax.googleapis.com/ajax/libs/jquery/1.10.2/jquery.min.js"></script> <script src="lib/angular/angular.js"></script> <script src="lib/angular/angular-resource.js"></script> <script src="js/app.js"></script> <script src="js/services.js"></script> <script src="js/controllers.js"></script> <script src="js/filters.js"></script> <script src="js/directives.js"></script> <script src="lib/bluimp/js/vendor/jquery.ui.widget.js"></script> <script src="lib/bluimp/js/jquery.piframe-transport.js"></script> <script src="lib/bluimp/js/jquery.fileupload.js"></script> </body> </html> ```