Open a Text File with Angular

I had some trouble this weekend figuring out how to open a text file in Angular. My luck turned around when I found this StackOverflow question. The question addressed loading an image, but I was able to fiddle with this Plunker example until I was able to load text files. (Basically, I replaced every instance of “readAsDataURL” in the upload.js file with “readAsText”.)

app.js

var UploadController = function ($scope, fileReader) {
  console.log(fileReader)
  $scope.getFile = function () {
    $scope.progress = 0;
    fileReader.readAsText($scope.file, $scope)
      .then( function(result) {
        $scope.imageSrc = result;
      });
    };
 
    $scope.$on("fileProgress", function(e, progress) {
      $scope.progress = progress.loaded / progress.total;
    });
};
app.directive("ngFileSelect",function(){
  return {
    link: function($scope,el){
      el.bind("change", function(e){
        $scope.file = (e.srcElement || e.target).files[0];
        $scope.getFile();
      })
    }
  }
})

index.html

<!DOCTYPE html>
<html ng-app="plunker">

  <head>
    <meta charset="utf-8" />
    <title>AngularJS Plunker</title>
    <script>document.write('<base href="' + document.location + '" />');</script>
    <link rel="stylesheet" href="style.css" />
    <script data-require="angular.js@1.0.x" src="https://ajax.googleapis.com/ajax/libs/angularjs/1.0.8/angular.min.js" data-semver="1.0.8"></script>
    <script> var app = angular.module('plunker', []); </script>
    <script src="upload.js"></script>
    <script src="app.js"></script>
  </head>

  <div ng-controller="UploadController ">
    <form>
      <input type="file" ng-file-select="onFileSelect($files)" >
      <!--<input type="file" ng-file-select="onFileSelect($files)" multiple> -->
    </form>
    <b>Preview:</b><br />
    <i ng-hide="imageSrc">No image chosen</i>
    <pre>{{imageSrc}}</pre><br/>
    <b>Progress:</b>
    <progress value="{{progress}}"></progress>
  </div>

</html>

upload.js

(function (module) {
     
    var fileReader = function ($q, $log) {
 
        var onLoad = function(reader, deferred, scope) {
            return function () {
                scope.$apply(function () {
                    deferred.resolve(reader.result);
                });
            };
        };
 
        var onError = function (reader, deferred, scope) {
            return function () {
                scope.$apply(function () {
                    deferred.reject(reader.result);
                });
            };
        };
 
        var onProgress = function(reader, scope) {
            return function (event) {
                scope.$broadcast("fileProgress",
                    {
                        total: event.total,
                        loaded: event.loaded
                    });
            };
        };
 
        var getReader = function(deferred, scope) {
            var reader = new FileReader();
            reader.onload = onLoad(reader, deferred, scope);
            reader.onerror = onError(reader, deferred, scope);
            reader.onprogress = onProgress(reader, scope);
            return reader;
        };
 
        var readAsText = function (file, scope) {
            var deferred = $q.defer();
             
            var reader = getReader(deferred, scope);         
            reader.readAsText(file);
             
            return deferred.promise;
        };
 
        return {
            readAsText: readAsText  
        };
    };
 
    module.factory("fileReader",
                   ["$q", "$log", fileReader]);
 
}(angular.module("plunker")));