Camera Plus Cordova Plugin

I have prepared a Custom Camera Plugin for iOS and Android because the default one does not provide the functionality I need.

What I want to achieve is retrieving images from the camera in the background without displaying a preview frame so that they can be requested from the Javascript and used directly in the HTML or posted in Base64 by HTTP POST. (+ a few other things that are not ready yet :))

I’ve actually managed and I have uploaded my plugin here:

Things are working as expected on Android but I have a problem on iOS (probably a memory leak).

It works for 3-4 minutes, the memory is increasing and suddently it stops refreshing (the app is still alive, the Camera object also).

Since ARC is enabled, I cannot manually release/dispose some of the objects myself. I have tried to wrap some places that were looking strategic with @autoreleasepool { }, memory usage is slightly better but the issue is still here.

I was wondering if there is an Objective C specialist out there who could have a look at my plugin and maybe provide some advises on how to fix this or at least locate where it comes from.

I have the feeling that it’s the fact of calling the plugin every 50-100ms to retreive an image that consumes the memory and doesn’t release it (the returned stream is between 8kb and 2Mb depending on the resolution):

        CDVPluginResult* pluginResult = [CDVPluginResult resultWithStatus:CDVCommandStatus_OK messageAsString:base64String];

    [self.commandDelegate sendPluginResult:pluginResult callbackId:command.callbackId];

But even by stopping the refresh and the camera the memory never gets released even when CPU usages get lower.

In order to hopefully motivate somebody to have a look at the code, I have prepared a simple and ready-to-use Ionic project here:

After grabbing this normally, all you have to do it:

cordova platform add ios (or android)
ionic build ios (or android)

Maybe there is a better approach. Suggestions are welcome anyway :smile:

I have realized (of course after creating my own) that I wasn’t the first one with this idea but looking at the existing variants didn’t help me to solve this problem.

The ones I’ve tried apparently have similar memory issues.

I have found those:

https://github.com/daraosn/Cordova-CanvasCamera (iOS only)
https://github.com/mbppower/CordovaCameraPreview (iOS + Android)
https://github.com/Clark-Nikdel-Powell/realtime_camera (iOS only, interesting variant that doesn’t need to call the plugin for every frame but trigs a callback in javascript multiple time directly from the Objective C side but I think that his approach didn’t work since it’s disabled in the code :confused: )

Thanks in advance.

2 Likes

The memory issue seems to be really killing the official Cordova camera plugin as well. I dabbled with yours a bit and still got the “Memory Pressure” crash.

If you find someone to help solve this, let them know there is a $250 bounty for that issue : https://github.com/calendee/cordovaCameraIssues

After deeper investigations, I know exactly where it comes from.

It’s UIWebView that leaks which is common and the case for all Cordova Plugins, there are several interesting articles about this subject and some with hints such as:
http://www.codercowboy.com/code-uiwebview-memory-leak-prevention/

Since the idea of my plugin is to pull high resolution images at approx 10-15fps and the base64 is quite big (200-2000kb) then the leaks goes fast in my case so it was easily noticeable.

I’ve found an alternative to this and it’s what I did in this application:

I’m not saying that it will apply in your situation but it solved the problem in my case. I have made a more complex version of the above plugin CameraPlus so I wrote CameraServer. Same approach as as the original but instead of communicating with the Javascript part the standard way with Cordova methods and callbacks, it’s creating an instance of a local webserver on the device that provides live images on demand. My Ionic app directly pulls Jpeg images now from a local webserver rather that making requests directly to my plugin the “standard” way.

I don’t have memory leaks anymore, it’s much faster and can run for hours… also for all the information that I need to provide from the native part to the UI part, I have just created Json methods through the local web server so apart Start and Stop so i’m not relying on standard Cordova methods to avoid such leaks as much as possible.

Cordova plugins methods are ok if they are not used intensively and not used for transfering big amount of data. Otherwise it will anyway generate memory leaks.

Hopefully it’s something that will be fixed with WKWebView, it’s apparently not something new and not something that we can do much about :confused:

1 Like

Hi ferretizer,

Any chance you plan on releasing CameraServer as a cordova plugin? I tried using your CameraPlus plugin for a time lapse project but ran into the same issues you described.

1 Like

I doubt I will make this one public at this time however I am ready to share it with a few users having plans to improve / extend the functionality.

I don’t have time to work much on this plugin myself so I could share if somebody wants to add support for audio / remote settings control (by ex. resolution selection for android is still missing) for any of the platform.

I saw that you contacted me by email so we will continue this discussion privately.

1 Like

Hi,

I have an iOS Camera Roll plugin that provides access to all photos in the Camera Roll without going through an AssetPicker. I had a dev shop build it for me - but I need an Android version. Would anyone be interested in helping me do an Android version? A public version is definitely a possibility.

@Calendee did you find any resolution/work around to your issues with the camera… I have completely hit a wall with the Heavy Memory Issue on an iphone 6 plus - https://github.com/calendee/cordovaCameraIssues#heavy-app-higher-memory-load-1

I will event settle for a hack at this point!

Hey @aaronksaunders,

Unfortunately, I never did and simply gave up. What’s crazy about this is that it’s completely device dependent. I’ve personally seen many devices have absolutely zero issues with this. I’ve heard from dozens of people that have no trouble with it. It simply seems that some devices have some flaw that this presents on. I have no idea why.

You might want to check out ezAR. http://www.ezartech.com/documentation This has a custom camera plugin that will allow for live access to the camera.

what is funny is I am just trying to take a picture… not even a live video.

Since I’m getting at least1 request per month for opening sources of my newer/fixed plugin, I have decided to open its sources as well.

The updated version which provides the images over HTTP instead of using the Cordova plugin callback approach (formelly Camera Server Plugin) is available here:

I wanted to update the main post accordingly, however i’m not allowed to.

If it seems of interest for some of you, I will create a new topic about it.

1 Like

I am so glad you shared your work with community. Well done!

1 Like

Hi @ferretizer, thanks for sharing the cordova-cameraserver!

However, I haven’t been able to put it to work. I’ve followed the steps described on you git hub, which are very explicit and easy to follow, but I can’t get any image on my android. I call the startServer function and it returns successfully, so does startCamera, but when I try to show it on the html, nothing shows up.
I tried to call getJpegImage and it also returns successfully but without the image itself.

Do you have any idea what it might be? Also, is there any example application for cameraserver has the “cordova-cameraplus-testapp”?

Thanks in advance. MP

2 Likes

Sorry for the delay. Since Cordova 4.0 it seems also required to add the cordova-plugin-whitelist and explicitly allow the app to do requests (even to 127.0.0.1 or localhost as the plugin is using)

Github has been updated with little fixes and i have added this to the documentation as well.

I’m running ionic 2 beta.
After I’ve ran:
ionic plugin add https://github.com/moonware/cordova-cameraplus.git
How can I use the plugin?
I’ve tried:

import {CameraPlus} from ‘ionic-native’;
and
import {CameraPlus} from ‘plugins/com.moonware.cameraplus/WWW/CameraPlus.js’;
I just don’t have a clue about how to get the plugin exports . . .

Hi what can I add in the “options” parameter?

startCamera( options, success_callback, error_callback );

I get the app running but dont’ show any image.

Thanks.