I spent 2 days on configuring this. I read lot of blogs and instrutction steps from various sites. I would like share my experience on installing Android NDK and Working with Eclipse.
Objective:
Using JNI Technology in Eclipse with Android NDK r6/r7 on Windows xp/7 Professional
Pre-requirements:
- Java SE SDK -- Java Development Kit
- Eclipse Helios/Indigo -- IDE to work with Java, Android, C/C++ etc.
- Android SDK -- Android Applications Development Kit
- Android ADT Plugin for Eclipse -- Download the latest Android SDK Platform Tools
- C/C++ Plugin for Eclipse (Optional) -- Make sure that .c, .cpp, .h files opening from Eclipse
- Android NDK (r6/r7) -- Native development i.e. Running c libraries in Android
- Cygwin 1.7.x or above -- Makefile creation, Library file creation tools, Compiling C files
Installation:
- Install the Java Development Kit
- Install the Android SDK and ADT Plugin with Eclipse
- [Optional] Install CDT plugin for Eclipse
- Download and extract the Android NDK
- Install Cygwin 1.7.x or above
Example:
"Program Files" -- Don't Use
"ProgramFiles" -- Use
Configuration:
Please make sure that you have set the environment variables like
- JAVA_HOME -- Java Home Directory
- NDK_HOME -- Android NDK Home Directory
- Update Path Variable with JDK Bin folder
- In Eclipse, Select File->New->Android Project
- Enter the Project Name and Click on "Next" button
- Select the "Build Target", I opted for Android 2.2, SDK 8 Version and Click on "Next" button
- In Application Info dialog, enter the "Package Name" and Select "Finish" button
- Now, you can see the newly created SampleNDK project in the eclipse project explorer window
Example:
- Eclipse Workspace Folder: D:\Workspace
- Android Application Name: SampleNDK
- Android Application Working Folder: D:\Workspace\SampleNDK
- Package Name: com.samplendk
- Android Application Source Folder: D:\Workspace\SampleNDK\src
Source of AndroidNDKActivity.java
package com.samplendk;
import android.app.Activity;
import android.app.AlertDialog;
import android.os.Bundle;
public class SampleNDKActivity extends Activity {
//Declare the native method
private native String invokeNativeFunction();
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
//Call the native methods
String hello = invokeNativeFunction();
new AlertDialog.Builder(this).setMessage(hello).show();
}
}
import android.app.Activity;
import android.app.AlertDialog;
import android.os.Bundle;
public class SampleNDKActivity extends Activity {
//Declare the native method
private native String invokeNativeFunction();
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
//Call the native methods
String hello = invokeNativeFunction();
new AlertDialog.Builder(this).setMessage(hello).show();
}
}
- Create a folder named "jni" in the project
- Right click on the "SampleNDK" project-> Select "New"-> Select "Folder"->Type "jni"
- Create files "Android.mk" and "native.c" in Jni folder
- Right click on the "jni" folder-> Select "New"-> Select "File"->Type "Android.mk"
- Right click on the "jni" folder-> Select "New"-> Select "File"->Type "native.c"
- After Creating those folder and files, the project explorer window look like this
- Do some continuous steps.
- Build, Refresh, and Clean project
- Right Click on the "SampleNDK" project and Select the "Build Project"
- Select "Sample NDK" project and Click "F5" button on keyboard
- Select "Project" menu and Select "Clean" option
- Create header file of the java file
- In windows command prompt, change to project source directory
- Syntax:
- cmd>
- cmd> cd ProjectDir/src
- Example:
- cmd> D:
- D:\> cd SampleNDK/src
- Run the Javah command to create header file
- Syntax:
- cmd> javah -jni
.javafile_without_.java_extension // JDK 1.7
- cmd> javah -classpath ..\bin\classes
.javafile_without_.java_extension //JDK1.6
- Example:
- D:\SampleNDK\src> javah -jni com.samplendk.SampleNDKActivity //JDK1.7
- D:\SampleNDK\src> javah -classpath ..\bin\classes com.samplendk.SampleNDKActivity //JDK1.6
- Note:
- Don't include the .java at the end of javah command
- Copy the created java header file to jni folder
- D:\SampleNDK\src> copy com_samplendk_SampleNDKActivity.h ..\jni
- Go to Eclipse and Refresh the project by pressing "F5" on keyboard.
- Open the header file from jni folder
- Copy the function created by javah as shown below
- Paste the code in native.c and change the code similar to this
#include <string.h>
#include "com_samplendk_SampleNDKActivity.h"
jstring JNICALL Java_com_samplendk_SampleNDKActivity_invokeNativeFunction
(JNIEnv *env, jobject obj)
{
return (*env)->NewStringUTF(env, "Hello from native function !!");
}
#include "com_samplendk_SampleNDKActivity.h"
jstring JNICALL Java_com_samplendk_SampleNDKActivity_invokeNativeFunction
(JNIEnv *env, jobject obj)
{
return (*env)->NewStringUTF(env, "Hello from native function !!");
}
Source of Android.mk
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
# Here we give our module name and source file(s)
LOCAL_MODULE := SampleNDK
LOCAL_SRC_FILES := native.c
include $(BUILD_SHARED_LIBRARY)
include $(CLEAR_VARS)
# Here we give our module name and source file(s)
LOCAL_MODULE := SampleNDK
LOCAL_SRC_FILES := native.c
include $(BUILD_SHARED_LIBRARY)
- Run Cygwin.bat file in the Cygwin installed directory
- It will open the cygwin command prompt
- Change the directory to SampleNDK project directory
- Note: All the drives in your systems are mounted to some directory in the cygwin.
- To see your drive mount points type mount
- # mount
- # cd /cygdrive/d/SampleNDK/
- Run the ndk-build command from the android ndk directory
- # /cygdrive/d/android-ndk-r7/ndk-build
- Error(Only in Android-ndk-r7):
- You may get some error like the following
/awk.exe: can't open file check-awk.awk
- Andoid NDK: Host 'awk' tool is outdated. Please define
- HOST-Awk to Point to Gawk or Nawk !
- Resolution:
- Goto the android-ndk/prebuilt/windows/bin/
- Change the awk.exe to awk_.exe
- Now you may see the following output after successful execution
- After successful creating libSampleNDK.so file, refresh your Eclipse project
- You can see the updated "Project Explorer" with "libs" folder in the tree hierarchy
- Update the java source code now by adding this library to it
package com.samplendk;
import android.app.Activity;
import android.app.AlertDialog;
import android.os.Bundle;
public class SampleNDKActivity extends Activity {
static
{
System.loadLibrary("SampleNDK");
}
//Declare the native method
private native String invokeNativeFunction();
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
//Call the native methods
String hello = invokeNativeFunction();
new AlertDialog.Builder(this).setMessage(hello).show();
}
}
import android.app.Activity;
import android.app.AlertDialog;
import android.os.Bundle;
public class SampleNDKActivity extends Activity {
static
{
System.loadLibrary("SampleNDK");
}
//Declare the native method
private native String invokeNativeFunction();
/** Called when the activity is first created. */
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
//Call the native methods
String hello = invokeNativeFunction();
new AlertDialog.Builder(this).setMessage(hello).show();
}
}
- Clean the project by Selecting "Project"->"Clean"
- Run the application as "Android Application"
- Note:
- Error:
- java.lang.unsatisfiedLinkError Library -- not found
- Resolution:
- Please see if you have added the "lib" in java source before adding the library in System.loadLibrary() method
- Please find the screenshot of above running program in emulator
If you have queries, please mail to psrdotcom@gmail.com