Autorun
Autorun

Reputation: 319

How to display base64 image in AngularJS

Need help again ;)

I would like to show a photo in my Angular page. These are my steps,

  1. REST API gets a document/record from backend MongoDB. The base64 images are stored as this.

enter image description here

  1. The images/data are loaded into an array {{file_src[i]}} in the component code, then the component HTML will show the image as below

enter image description here

Situations:

  1. If I used "img srcs={{file_src[i]}}", I got insecure operation. My REST API server has CORS enabled. Since the image is base64 data and doesn't have any URL, I don't know it is related to CORS.

enter image description here

  1. I googled around and found the ng-src and data-ng-src directives. Both of them don't work too. Please see my binding error below.

enter image description here

Question: how to show the base64 image in my Angular page?

------Code as requested by Vic--------

<section class="fhirForm">
        <fieldset>
            <legend class="hd">
                <span class="text">Photo</span>
            </legend>
            <div class="bd" formArrayName="photos">
                <div *ngFor="let photo of patFormGroup.controls.photos.controls; let i=index" class="panel panel-default">
                    <div class="panel-body" [formGroupName]="i">

                        <label>Description</label>
                        <input type="text" class="form-control" formControlName="desc">

                        <label>Photo</label>
                        <input type="file" size="30" multiple formControlName="photo" name="crud8" (change)="photoChange(input, i)" #input>
                        <!-- img src={{file_srcs[i]}} crossorigin="anonymous" alt="" /-->
                        <img data-ng-src={{file_srcs[i]}} alt="" />

                        <span class="glyphicon glyphicon-remove pull-right" *ngIf="patFormGroup.controls.photos.controls.length > 1" (click)="removePhoto(i)"></span>
                    </div>
                </div>
            </div>
        </fieldset>

        <div class="margin-20">
            <a (click)="addPhoto()" style="cursor: default">
                <small>Add another photo +</small>
            </a>
        </div>
    </section>

  initPhoto(desc?: String, photo?: string) {
    //Add new entry on the 1 dimensional array. Allow 1 photo per section
    this.file_srcs.push(photo);
    console.log("Photo for file_srcs: [" + this.file_srcs[this.file_srcs.length - 1] + "]");

    return this.formBuilder.group({
      desc: [desc],
      photo: [photo]
    });
  }

Please see the console.log. It showed that this.file_srcs are valid.

enter image description here

------------- Error Message in Chrome -------

enter image description here

------------- UPDATE 1 -----------

If I commented out the "input type=file ..." line above the "img src" as below, I can see the photo. What's wrong with my input? Sorry, I don't remember what is that #input for.

Hence, my issue may not be in the photo, but on the input line ;) Shame on me!!!

                <label>Photo</label>
                <!-- input type="file" size="30" formControlName="photo" name="crud8" (change)="photoChange(input, i)" #input -->
                <img src={{file_srcs[i]}} crossorigin="anonymous" alt="" />

enter image description here

--------- RESOLVED -----------

Thanks a lot for all the help!!!

i. the base64 image isn't the root cause;

ii. the file input "input type=file" was initialized by incorrect supplying the base64 image as the default value. It caused the error - failed to set the value of HtmlInputElement is correct in IE. The error message 'Insecure Operation' may be misleading in Firefox.

Hence, the root cause is not related to the base64 image. I would like to delete this thread a week later.

initPhoto(desc?: String, photo?: string) {

this.file_srcs.push(photo);
console.log("Photo for file_srcs[" + (this.file_srcs.length - 1) + "]: [" + this.file_srcs[this.file_srcs.length - 1] + "]");

return this.formBuilder.group({
  desc: [desc],
  photo: [""]     //This was photo: [photo]. After supplying the default value as "", it works well.
});

Best regards,

Autorun

Upvotes: 1

Views: 8487

Answers (2)

Icycool
Icycool

Reputation: 7179

I use base64 image a lot and haven't see that error before. Is it caused by the crossorigin attribute?

angular.module('test', []).controller('Test', Test);

function Test($scope) {
  $scope.base64 = "data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAA8AAAAOCAYAAADwikbvAAAA+0lEQVQ4T6WS3W3CMBSFz40QvDJCu0GYALJB2QBeUFzjCm9AJ0gLMQl9STegG5QNYARG6CsI+SKjpmppSY3w8/10fnwIVzy6lE2SollrbBcAPV8ET2fzOzAXDNYPUrx6wxOT9QjkwL4DnWMvODV5wUAP4EclxbiM+i88meUJMUYA3pSMu987qoRLqwDW+10j0rr/4QV/lrNwxwGClpSD9enPHJXTdD5i4vY+YK2F2BjzElrYdwDN05x/KpelMOGJGB0AIQGboYxvz23hR+apyVcO+jq2HCklll7wcT31rbMbgrBU93FUtcBfbSdZdlOztILlbpWq90jOqR8Au8VfIQFLZecAAAAASUVORK5CYII=";
}
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.8/angular.min.js"></script>
<div ng-app='test' ng-controller='Test'>
  <img src={{base64}} />
</div>

Upvotes: 0

Vikasdeep Singh
Vikasdeep Singh

Reputation: 21766

Fetch the base64 content in your controller like this:

$http.get($scope.user.photo).then(function(response) {
    $scope.user.data = response.data;
});

then display it on view

<img data-ng-src="data:image/png;base64,{{user.data}}"/>

Upvotes: 2

Related Questions