2

I have an app that allows a user to select a photo from the gallery or take a photo via camera. I am trying to display an image that was taken via camera and it works fine, it returns a file path like

file:///Users/ray/Library/Developer/CoreSimulator/Devices/C8202B3B-300B-4819-8CD3-4C4AA690CE7C/ data/Applications/D82BF64E-6DD1-4645-B637-BCF65001FD29/tmp/cdv_photo_003.jpg

but when I try to select a photo from a gallery it shows a broken image thumbnail, and it turns a file path like.

content://com.android.providers.media.documents/document/image%3A21

Ionic CLI Version: PRO 4.2.1

Cordova Verion: 8.0.0

NPM Version: 6.4.1

Node.js version: 8.11.3

Platform: Android

I've also tried searching for a solution but it didn't work or I am still doing something wrong

Some of them suggests using this code

if (imageURI.substring(0,21)=="content://com.android") {
  photo_split=imageURI.split("%3A");
  imageURI="content://media/external/images/media/"+photo_split[1];
}

but this solution is not that robust cause not all of the image sources returns the same file path that contains 'content://com.android' like the photos that came from Google Photos which returns 'content://com.google.android'

_Some of them also suggests using DATA_URL on destination type but it is memory intensive and may cause the app to crash_

Here is my code:

TS file

selectImage(sourceType) {
    const options: CameraOptions = {
      quality: 100,
      destinationType: this.camera.DestinationType.FILE_URI,
      encodingType: this.camera.EncodingType.JPEG,
      mediaType: this.camera.MediaType.PICTURE,
      saveToPhotoAlbum: true,
      sourceType: sourceType
    }

    this.camera.getPicture(options).then((imageData) => {
     let base64Image = 'data:image/jpeg;base64,' + imageData;
     this.imagePreview = imageData;
    }, (err) => {
      this.toastCtrl.presentToast(err);
    });
  }

HTML File

<img src="{{imagePreview}}" />;

I hope someone could help me with this. Thank you in advance .

Oliver Primo
  • 317
  • 4
  • 18

4 Answers4

0

ts:

public base64Image:string; 
public getImage(){
const options: CameraOptions = {
  quality: 100,
  destinationType: this.camera.DestinationType.DATA_URL,
  encodingType: this.camera.EncodingType.JPEG,
  mediaType: this.camera.MediaType.PICTURE
}

this.camera.getPicture(options).then((imageData) => {
 this.base64Image = 'data:image/jpeg;base64,' + imageData;
}, (err) => {
 // Handle error
});
}

html:

<imge src={{base64Image}} />
Khurshid Ansari
  • 4,638
  • 2
  • 33
  • 52
  • I've already tried this solution and it didn't work to display both pictures from the gallery and the ones that are taken from the camera. – Oliver Primo Jan 31 '19 at 05:53
  • Except that I am using ```destinationType: this.camera.DestinationType.FILE_URI``` rather than ```destinationType: this.camera.DestinationType.DATA_URL``` because according to what I have searched, DATA_URL is a bit more memory intensive and may cause some apps to crash. – Oliver Primo Jan 31 '19 at 06:06
  • @OliverPrimo it is working in application. 'data_url is bit more memory intensive' - how or can you give some reference where you found this. – Khurshid Ansari Jan 31 '19 at 06:12
  • @OliverPrimo if you want to send to server the selected image then you need base64. – Khurshid Ansari Jan 31 '19 at 06:13
  • @OliverPrimo and if you want to use file uri then you have to check how to display that url in application. i have done file uri in that case i had converted that url to different which is not remember exactly. – Khurshid Ansari Jan 31 '19 at 06:25
  • I found it here https://cordova.apache.org/docs/en/latest/reference/cordova-plugin-camera/#camera ----- **NOTE: Photo resolution on newer devices is quite good. Photos selected from the device's gallery are not downscaled to a lower quality, even if a quality parameter is specified. To avoid common memory problems, set Camera.destinationType to FILE_URI rather than DATA_URL.** ----- and here https://stackoverflow.com/questions/20638932/unable-to-load-image-when-selected-from-the-gallery-on-android-4-4-kitkat-usin/20642318?noredirect=1#comment34336174_20642318 – Oliver Primo Jan 31 '19 at 06:28
  • @OliverPrimo yes. check how to display that url in application. i did some year ago. i had converted that url in different formate - exactly not remember. if i get i will tell you. – Khurshid Ansari Jan 31 '19 at 06:43
  • thanks a lot for your help . I'm really sorry for disturbing you because I am just a newbie in Ionic development. – Oliver Primo Jan 31 '19 at 06:49
0

Give this a try:-

   //From Gallery
     ChooseGallery() {
        var _self=this;
        const options: CameraOptions = {
          allowEdit: true,
          correctOrientation: true,
          quality: 100, // picture quality
          destinationType: this.camera.DestinationType.FILE_URI,
          encodingType: this.camera.EncodingType.JPEG,
          sourceType: this.camera.PictureSourceType.SAVEDPHOTOALBUM
        }
        this.camera.getPicture(options).then((ImageData) => {
          _self.base64value = ImageData;
        })
      }

From Camera

  ChooseCamera() {
    var _self=this;
    const options: CameraOptions = {
      allowEdit: true,
      correctOrientation: true,
      quality: 100, // picture quality
      destinationType: this.camera.DestinationType.FILE_URI,
      encodingType: this.camera.EncodingType.JPEG,
      mediaType: this.camera.MediaType.PICTURE
    }
    this.camera.getPicture(options).then((ImageData) => {
      _self.base64value =  ImageData;
    })
  }

I hope this helps! Thanks!

rchau
  • 535
  • 9
  • 32
  • Hello @rchau. I'll give it a try and let you know the result afterward. Thank you for your suggestion – Oliver Primo Jan 31 '19 at 06:13
  • @OliverPrimo Sure thing. :) – rchau Jan 31 '19 at 06:14
  • @rchau he want with data uri. – Khurshid Ansari Jan 31 '19 at 06:27
  • @rchau I am trying to work with FILE_URI instead of DATA_URL for Camera.DestinationType. I'm sorry because it causes some malfunctions in my app and I don't know how to prevent that so I am sticking with FILE_URI. – Oliver Primo Jan 31 '19 at 06:38
  • @OliverPrimo There is no much of change even if you use `FILE_URI`. I want to know what are you getting in `imageData`. Do an alert there. – rchau Jan 31 '19 at 07:06
  • @rchau It does not alert anything and it slows down my application, it didn't even display the value even though I placed it inside a paragraph in my view ```

    {{base64value}}

    ```. There is one time that my app crashed after selecting an image from the gallery and maybe that is the problem with the use of DATA_URL or Maybe I am still doing something wrong.
    – Oliver Primo Jan 31 '19 at 07:47
  • @rchau I tried your suggestion with FILE_URI but it still doesn't work. the value of ```ImageData``` is ```content://com.android.providers.media.documents/document/image%3A21``` I don't know where did I go wrong – Oliver Primo Jan 31 '19 at 08:26
0

Solved my problem using DomSanitizer https://devfanaticblog.com/working-with-camera-in-ionic-2-and-ionic-native/

Oliver Primo
  • 317
  • 4
  • 18
0
let options: CameraOptions = {
  quality: 100,
  sourceType: this.camera.PictureSourceType.SAVEDPHOTOALBUM,
  saveToPhotoAlbum: true,
  correctOrientation: true,
  encodingType: this.camera.EncodingType.JPEG,
  destinationType: this.camera.DestinationType.FILE_URI
};

this.camera.getPicture(options).then((imageData) => {
  let photo_split=imageData.split("%3A");
  let photo_split2=photo_split[0].split("?");
  let filename = photo_split2[0].substring(photo_split2[0].lastIndexOf('/')+1);
  let path =  photo_split2[0].substring(0,photo_split2[0].lastIndexOf('/')+1);

  alert(photo_split2[0])
  alert(filename)
  alert(path)
  this.file.readAsDataURL(path, filename).then(res=> {
    alert("FUNCIONA!")
    this.imageURI = res;
  }).catch((reason) => {
    alert(JSON.stringify(reason));
  });
}).catch((reason) => {
  alert(JSON.stringify(reason));
});

//HTML

    <img alt="uploaded Image" [src]="imageURI">