Adding Cordova APIs to Android via CLI: Camera and File APIs – shoot picture and upload to server folder with PHP

In this article, we are continuing our exploration of the Cordova APIs. On this page, we’ll explore the Camera and File APIs to get a photo onto the server. Here, we’ll learn how to upload the image to a server directory after shooting it.

This article requires that you have a server with PHP installed, are able to upload a file to it, and the server accepts uploads. My simple server has a CPanel interface that allowed me to do all of the above. (Don’t worry; I’m going to give you the steps for all of this.)

[This was an exercise to learn about uploading to a server. This exercise uploads a photo from the device’s camera to a specific folder on a server. It’s highly unlikely that one would put this into production — who would want hundreds of app users’ photos inserted into a single folder? This is fine for personal use, however.] 

You can start a new HTML page and link to it via a button on the index.html page to access it (which is what I did). If you are starting a new page, copy/paste this HTML skeleton into a text editor and save it as camera.html to follow along:

<!-- ********************* HMTL5 Skeleton begin *********************** -->
<!DOCTYPE html>
 <meta charset="utf-8" />
 <meta name="format-detection" content="telephone=no" />
 <!-- WARNING from Cordova: for iOS 7, remove the width=device-width and height=device-height attributes. See -->
 <meta name="viewport" content="user-scalable=no, initial-scale=1, maximum-scale=1, minimum-scale=1, width=device-width, height=device-height, target-densitydpi=device-dpi" />
 <style type="text/css">
 .buttonClass, h2, p {
 font-family: "Helvetica"; color: #000; font-size:1em;
 .buttonClass {
 border-radius:8px; background-color:#fff;
 border:#878787 solid 1px; padding:0 1em;margin:.5em;
 height: 3em; width: 46%;
 .segment {
 display:block; border-radius:8px; background-color:#eee;
 border:#878787 solid 1px; padding:1em; margin:.5em;
 h2 {
 font-size:1.3em; font-weight: bold;
 @media screen and (max-width:800px) {
 .buttonClass { width: 100%;}
 <script type="text/javascript" src="cordova.js"></script> 
<!-- ********************* HMTL5 Skeleton end *********************** -->

Server’s php.ini Setup

We will use the File API to shoot our picture and upload it to a folder in a server. We need to set up the server first. I don’t have a “dedicated” server, so I did my work through the control panel (cpanel) of my admin account. I needed to make sure some PHP permissions were set correctly, and that meant changing the php.ini file. I did not have access to it (I could not find where it was located), so I contacted support and they copied it to a folder so I could edit it. Make the following changes by downloading your php.ini to your hard drive. I clicked on “cpanel” then on “File Manager,” then navigated to where they placed the file. I selected the file and chose “download” to download it.

You may need to do a search for the terms to find them. Change their values as noted. You might merely have to uncomment a line or two (to do that, remove the ; at the left of the text).

1. Download the php.ini file to your hard drive and open it in a text editor. Do not open it in a word processor!

My php.ini changes:

2. file_uploads must be set to on:

file_uploads = On

3. upload_tmp_dir value must be set to where uploads will be placed. I left the value as is; you probably should not change this:

upload_tmp_dir = var/tmp/

4. upload_max_filesize dictates how large a file can be sent

upload_max_filesize = 10M

5. Upload the file back to the server, overwriting the old version. I clicked on “upload,” navigated to the file on my hard drive, and “OK.”

6. Next, we need to add a folder into which all photos will be uploaded. In the cpanel, I clicked on the public_html/ folder to select it, then on “New Folder” and gave the folder the name of “uploads.” From the directory root, the uploads URL might look like: home2/yourDomain/public_html/uploads/ (“yourDomain” will be the name of your domain). Your server may have a different address; that’s fine.

7. Let’s make sure that php is working. Open a text file, save it as testphp.php, and add only the following line to it:

<?php phpinfo(); ?>

8. Upload that to the uploads/ folder in the same way you uploaded the php.ini file in step 5 and navigate to it in a browser. If your folder setup is the same as mine, it would look like: (with “yourDomain” will be the name of your own domain, of course). If all is well, you should get a whole page or so of information about your PHP settings. You may safely delete that file when done. If the page does not show PHP info, you’ll want to contact customer support and find out why not.

PHP Upload Script

We are using a PHP script to process the uploads. I found a script that will process the uploads but also adds security, and checks to make sure the file is what it purports to be (whether jpg, jpeg, png, gif). Copy the following into a blank text file and name it upload.php. Then upload it your server’s uploads/ folder. If you are using a different name for your uploads/ folder, then change it in the two places indicated before uploading it.

This file will check to make sure the file uploaded is indeed an image file, and that it’s under 10MB. It will prepend the date of the image shoot to help make the filename unique. Then it will give the final name of the file and the folder it’s stored in.

<!– ********************* upload.php begin *********************** –>

// File types allowed on upload:
$allowed_exts = array(“gif”, “jpeg”, “jpg”, “png”);
$temp = explode(“.”, $_FILES[“file”][“name”]);
$extension = end($temp);
if ((($_FILES[“file”][“type”] == “image/gif”)
|| ($_FILES[“file”][“type”] == “image/jpeg”)
|| ($_FILES[“file”][“type”] == “image/jpg”)
|| ($_FILES[“file”][“type”] == “image/pjpeg”)
|| ($_FILES[“file”][“type”] == “image/x-png”)
|| ($_FILES[“file”][“type”] == “image/png”))
&& ($_FILES[“file”][“size”] < 100000)
&& in_array($extension, $allowed_exts)) {
if ($_FILES[“file”][“error”] > 0) {
echo “Not allowed Code: ” . $_FILES[“file”][“error”] . “<br>”;
else {
echo “Upload: ” . $_FILES[“file”][“name”] . “<br>”;
echo “Type: ” . $_FILES[“file”][“type”] . “<br>”;
echo “Size: ” . ($_FILES[“file”][“size”] / 1024) . ” kB<br>”;
echo “Temp filename: ” . $_FILES[“file”][“tmp_name”] . “<br>”;

if (file_exists(“uploads/” . $_FILES[“file”][“name”])) {
echo $_FILES[“file”][“name”] . ” already exists. “;
else {
$timestamp = time();
$timestamp . “_” . $_FILES[“file”][“name”]); // Add time to filename to minimize overwriting.
echo “Stored in: uploads/” . $_FILES[“file”][“name”];
else {
echo “Sorry, invalid file upload (this is from upload.php).”;

<!DOCTYPE html>
<meta charset=”utf-8″ />
<title>Image Upload Page</title>
<style type=”text/css”>
li { font-size:1.5em; padding: .5em; }
<h2>Contents of the image file upload folder (this is from upload.php).</h2>

<!– ********************* upload.php end *********************** –>

Camera API

The following code comes from This code will access the camera and allow you to shoot the picture and retain it. Then it will segue into the next block of code after this one and upload the picture.

1. To follow along, please refer to the following article to set up your Cordova PhoneGap project files. You’ll want to follow the “Set Up the Android Project” section through step 9 inclusive.

2. Download the camera plugin in terminal:

cordova plugin add

2. Make sure it’s downloaded:

cordova plugin ls

3. Open CordovaAPI/platforms/android/res/xml/config.xml in a text file and add the following to just above </widget> and save:

<feature name="Camera">
    <param name="android-package" value="" />

4. Open platforms/android/AndroidManifest.xml with a text editor and enter the following among the other “<uses-permission” entries:

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

5. Add the following (from “Camera begin” to “Camera end”) to just above the </body> tag and change the URL to the upload.php page on your server in the two places indicated.

<!-- ********************* Camera begin *********************** -->
<script type="text/javascript" charset="utf-8">
var pictureSource; // picture source
 var destinationType; // sets the format
// Wait for device API libraries to load
 // device APIs are available
/** ***************** IMAGE CAPTURE ***************** */
// camera.getPicture
function onDeviceReady() {;;
// cameraSuccess
 // Called when a photo is successfully retrieved
 function onPhotoDataSuccess(imageData) {
 var smallImage = document.getElementById('smallImage'); // Get image handle = 'block'; // unhide image
 smallImage.src = "data:image/jpeg;base64," + imageData; // show image
function capturePhotoEdit() {
 // Take picture using device camera, allow edit, and retrieve image as base64-encoded string, onFail, { quality: 50, allowEdit: true, destinationType: destinationType.DATA_URL });
// Called if something bad happens.
 function onFail(message) {
 alert('Response: ' + error.code + '\n' + error.message);
function removeImages() {
 var smallImage = document.getElementById('smallImage'); = 'none';
 smallImage = null;
 function removeLargeImage() {
 var largeImage = document.getElementById('largeImage'); = 'none';
 largeImage = null;
/** ***************** GET IMAGE ***************** */
// Called when a photo is successfully retrieved
 function onPhotoURISuccess(imageURI) {
 var largeImage = document.getElementById('largeImage'); // Get image handle = 'block'; // unhide image
 largeImage.src = imageURI; // show image 
// cameraOptions
 function getPhoto(source) {
 // Retrieve image file location from specified source, onFail, { quality: 50,
 destinationType: destinationType.FILE_URI,
 sourceType: source });
<!-- ********************* Camera end *********************** -->

File API

Now we set up the page for the File API to use the fileTransfer script for uploading the picture.

1. In Terminal, download the plugin:

cordova plugin add org.apache.cordova.file

2. Add the file-transfer plug-in:

cordova plugin add org.apache.cordova.file-transfer

3. Make sure they are available:

cordova plugin ls

4. Add to config.xml in a text editor:

<feature name="File">
    <param name="android-package" value="org.apache.cordova.file.FileUtils" />
<feature name="FileTransfer">
    <param name="android-package" value="org.apache.cordova.filetransfer.FileTransfer" />

5. Make sure this is in AndroidManifest.xml; if not, add it in a text editor:

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

6. Add the following code (from “FileTransfer begin” to “FileTransfer end”) just above the </body> tag to complete the code needed to send the image to the server. Change “yourDomain” in the two sections where noted to your own domain name.

This fileTransfer script comes from

The code will give you confirmation of the photo name and where it is located.

It provides a button to visit the uploads/ folder to view the files.

<!-- ********************* FileTransfer begin *********************** -->
// upload (open camera to shoot) 
 function uploadPhotoStart() {
 var uploadStatus = document.getElementById('uploadStatus'); // get field ID = "blue";
 // Retrieve image file location from specified source
 function(message) { alert('uploadPhoto(imageURI) failed'); },
 quality : 50,
 destinationType :,
 sourceType :
 } // not
// FileUploadOptions
 function uploadPhoto(imageURI) {
 var options = new FileUploadOptions();
 var ft = new FileTransfer();
var params = {};
 params.value1 = "test";
 params.value2 = "param";
options.params = params;
 ft.upload(imageURI, "http://Domain/uploads/upload.php", win, fail, options);
function win(r) {
 var uploadStatus = document.getElementById('uploadStatus'); = "green";
 uploadStatus.innerHTML += "<br>Code = " + r.responseCode;
 uploadStatus.innerHTML += "<br>Response = " + r.response;
 uploadStatus.innerHTML += "<br>Sent = " + r.bytesSent;
/* Code of 200 = successful upload. */
function fail(error) {
 var uploadStatus = document.getElementById('uploadStatus'); = "red";
 uploadStatus.innerHTML += "<br>An error has occurred: Code = " + error.code;
 uploadStatus.innerHTML += "<br>Upload error source " + error.source;
 uploadStatus.innerHTML += "<br>Upload error target " +;
<!-- Onscreen Layout -->
<div class="segment">
<h2>File Transfer</h2>
<p><em>Shoot photo and upload it to server</em></p>
<input type="button" class="buttonClass" onclick="uploadPhotoStart();" value="Shoot Photo">
<p id="uploadStatus">&nbsp;</p>
<p><em>Open folder on server to see listing of images uploaded.</em></p>

<!– CUSTOMIZE THE FOLLOWING URL WITH THE URL TO YOUR OWN UPLOAD.PHP SCRIPT PAGE. DO NOT INCLUDE THIS LINK IN PRODUCTION. ONLY FOR TESTING. –> <input type=”button” class=”buttonClass” onclick=’window.location=”http://Domain/uploads/”&#8216; value=”Open Folder”>

<input type="button" class="buttonClass" onclick='window.location=""' value="View Code On">
<!-- ********************* FileTransfer end *********************** -->

Auto-convert the files to thumbnails

I found a file that converts the plain file listing into thumbnails. It’s the Indexr Directory Listing.

1. Visit:

2. Click on index.php

3. Copy the contents of that file into a text document and save it as index.php.

4. Upload the file to your uploads/ folder.

That’s it! It will format the images for you as thumbnails when you tap on the Open Folder button. As is, though, it doesn’t fit them to the small screen; you’ll be swiping to see them. The simple solution is to go to line 58 and change the number of columns from 3 to 1. That fixes it.

Also, the text is tiny because it’s designed for desktop monitors. At line 431, replace

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "">
<html xmlns="" xml:lang="en">


<!DOCTYPE html>


<meta http-equiv="Content-Type" content="text/html;charset=utf-8"/>


<meta http-equiv="Content-Type" content="text/html;charset=utf-8"/>
<meta name="viewport" content="user-scalable=no, initial-scale=1, maximum-scale=1, minimum-scale=1, width=device-width, height=device-height, target-densitydpi=device-dpi" />

Finally, replace line 439 with a larger font size:

body { background: black; color: #999; font: 1.5em Tahoma; margin: 18px 36px;}

Test the APK File

1. Build the files in the terminal, remembering to start from your project’s folder:

cordova build android

(or, cordova prepare android then cordova compile android)

2. Locate the apk file at platforms/android/bin/CordovaAPI-debug.apk and put it on your device. (I had recently updated to 3.4.0 and found the apk in platforms/android/ant-build/.)

3. Navigate to the page in your device and tap the button to shoot a picture. When done, you’ll be returned to the app, then the script will continue and upload your file to the server.

4. Tap the other button to view the uploads/ folder on the server. It will open in a browser and the print_r($_FILES); script on the uploads.php file will display the folder contents, showing you all the files. Tap on the image name to view it in the browser. You can also review an error_log file, if there is one, to help pinpoint problems.

For security reasons, you don’t want this button used by the public; remove that HTML from the app’s production version. For the same reason, please remove the print_r($_FILES); line from the upload.php page before using in a public release. I’m not sure that the security scripting is strong enough to thwart hackers’ attempts to inject malicious code.

Start screen:

Camera start screen


After image upload:

Camera upload verification


Viewing the uploads/ folder:

(Before changing to the thumbnail version)

Sample uploads/ folder contents


Viewing the uploads/ folder:

(After changing to the thumbnail version)



2 thoughts on “Adding Cordova APIs to Android via CLI: Camera and File APIs – shoot picture and upload to server folder with PHP

  1. Hi, wanted to say thanks for this. Haven’t tried the indexr, but the bones of it works an absolute charm. Great instructions for a newcomer to phone apps. Just need to tinker with it now to integrate with a form and upload on submit, but you’ve done the heavy lifting for me… thankyou!

Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s