Taken image from camera not able to show in UI,


#1

I am using Cordova Plugin Camera to take picture and show the image in UI. However, I am not able to display the image in UI.

Here the Image path I have got when I invoke the camera. file:///storage/emulated/0/Android/data/io.ionic.starter/cache/1456188886652.jpg

  return Observable.create( (subscriber: Subscriber<string>) => {                                                           
            let co: CameraOptions = {};
            co.destinationType = Camera.DestinationType.FILE_URI;
            co.quality = 50;
            
            navigator.camera.getPicture(
                data => {
                    subscriber.next(data);
                },
                error => {
                    Observable.throw(error);
                }, co
            )       
   })

Please help me is there anything I need to do.

Here is my couple of question.

  1. What should be config.xml file for white-list
  2. Do I need to copy the image to application folder?

Thanks.


#2

I have similar issue with this. For me, when I take picture, it does not show up in the UI. However, when I take the 2nd picture, the 1st picture appear to the UI. Anyone knows how to fix this? Or is there any way to refresh the UI?


#3

I had huge problems with this too, adding ngZone and doing a zone.run() solved it for me, take a look here:
(Heads up, i am not sure that this should be necessary or is the best solution)

https://github.com/marcusasplund/ionic2-camera-demo/blob/master/app/pages/page1/page1.ts


#4

Thanks mate. IT WORKS!!! AWESOME


Ionic - Can't change DOM
#5

Appriciated your help here. However, I want to use File URI. Because I want to upload the images server too.

Also, noticed using zone with DATA_URI take a while to update the UI.

Looking forward to your answer.

Thansks,
Nitheen


#6

Try this:
Change destinationType to
destinationType: Camera.DestinationType.FILE_URI

Remove the base64 stuff in success callback

Install whitelist plugin
$ cordova plugin add cordova-plugin-whitelist

Add this metatag to your index.html to initialize plugin:
<meta http-equiv="Content-Security-Policy" content="default-src *; script-src 'self' 'unsafe-inline' 'unsafe-eval' *; style-src 'self' 'unsafe-inline' *">


#7

@pentryslampan thanks. It works awesome now.


#8

Hi @nithinshiriya,

Would you mind to share the code that you use to take the picture and then send to the server?

  • Also, how do you send the picture to the server? File? In database?
  • If database, it is a string or blob?
  • Do you keep it also in a Sqlite database on the phone?
  • Did you need to use the ngZone or not?

I want to do something similar to you where I want to be able to take a picture, show it on the phone, but also send it to the server database for future use.

Thanks in advance


#9

I tried this and nearly every solution on the forum and google search I could find any mention of it but can get to show the selected image. If I use the Data_URL to get base64 image data than this works but I need the URI so I can upload the image.
Code does not through and error. The the file URI come as file:///… and I can’t seem to find the way to resolve.


#10

Had the same problem. Solved by using this plugin:


You have to catch the upload event, parse the fileurl to get a proper one which will show up in the ui.

Code snippet on how i solved it:

https://gist.github.com/marcusasplund/b3cfd94c1ff218da20124ecc0105030c


#11

I have an example how to use the camera together with the filetransfer plugin (file uri) right here. It also shows the image (Made by camera or selected by image picker) in the UI. It might help out :slight_smile:


#12

My base64 image will appear in the UI after I take a picture, but only after I push it to another page. Even so, it takes forever to switch pages and appear. Is there anything I can do about this painful slowness? I attempted the ngZone solution today ( maybe I need to go back and try it again?).

My code is here. Any help or advice would be extremely appreciated.


#13

Hi i have solved the issue i will share my sample code…

1st you need to import some files…

import { Camera, CameraOptions } from '@ionic-native/camera';


//after that implement into the container
public camera:Camera,


const options: CameraOptions = {
  quality: 50,
  destinationType: this.camera.DestinationType.FILE_URI,
  encodingType: this.camera.EncodingType.JPEG,
  mediaType: this.camera.MediaType.PICTURE
}
this
  .camera
  .getPicture(options)
  .then((imageData) => {
    this.base64Image = imageData;
    alert(this.base64Image);
  }, (err) => {
    console.log(err);
  });

here's my html code

<img src="{{base64Image}}" alt="" class="image_container" />

#14

Hi everyone,

This one really pissed me off for ages. For me, it turned out to be a WKWebView thing. Try importing normalizeUrl from ionic-angular, and run the returned FILE_URI through it before displaying. Did the trick for me!


#15

Thank you. This allowed me to stop puttin my head through a wall trying to figure this out. Though I’m passing an <Entry>'s nativeUrl. It’s working great.

Should be marked as a solution


#16

HGello,

did you have a piece of code for better understanding?

Best regards, anna-liebt


#17

In my html. A quick example

<ion-item>
  <img [src]="normalizedUrl"  />
</ion-item>

In my component.

import { NavController, NavParams, Slides, normalizeURL <--- } from 'ionic-angular'; 
import { CameraAccessProvider } from '../../providers/camera-access/camera-access';

  export class PicturePage {
    normalizedUrl: string; <--- 

      constructor() {
      this.normalizedUrl = "";
   }

  /** function to takePicture */
  this.getImage(){
    this.cameraProvider.transferImage()
     .then((res: string) => this.cameraProvider.createFileEntry(res))
     .then((entry: Entry) => this.normalizedUrl = normalizeURL(entry.nativeURL))
}     

In my provider

import { File, DirectoryEntry, FileEntry, Entry } from '@ionic-native/file';
import { FileTransfer, FileUploadOptions, FileTransferObject, FileUploadResult } from '@ionic-native/file-transfer';
//Not all of these are necessary for what I posted.

export class CameraAccessProvider {

 constructor(
   public file: File,
   public camera: Camera) { 
     console.log('Feel free to ask if you want me to clarify anything');
  }

// Initial function to take photo and respond with imagePath (since it's FILE_URI)
  transferImage(): Promise<any> {
    let options: CameraOptions = {
      sourceType: this.camera.PictureSourceType.CAMERA,
      destinationType: this.camera.DestinationType.FILE_URI,
      encodingType: this.camera.EncodingType.JPEG
    }
     return this.camera.getPicture(options)
     .then((imagePath) => imagePath)
     .catch(err => err.message)
  }

Then I create a file entry with the imagePath

  createFileEntry(imagePath: string): Promise<any> {
   let cleansedPath = imagePath.replace(/^.*[\\\/]/, '');
   let d = new Date();
   let t = d.getTime();
   let newFileName: string = t + ".jpg";

    return this.file.moveFile(this.file.tempDirectory, cleansedPath, this.file.dataDirectory, newFileName)
    .then((entry: Entry) => entry)
    .catch((err) => err.message)
   }

the ((entry: Entry) is what I added normalizeUrl to up top. Without adding normalizeUrl, no image displays. With it, image shows up crystal clear.

FYI, only tested on iOS device


#18

Hello,

Thank you very much.

Best regards, anna-liebt


#19

Very welcome.

regards as well,
Jason Dziadosz


#20

@jaydz thank you for solution …am not implement it…but in my case camera is opening in above android 6.0 -v but not opening for android 4 and 5 …any solution please