Addvertisement

Thursday, March 7, 2013

C++ / CPP on Android



1];- Create a new project on android.

2];- Create the jni folder under the android project

3]:- Create the Android.mk file on the jni directory.

The structure of Android.mk file as follows



LOCAL_PATH := $(call my-dir)



include $(CLEAR_VARS)


LOCAL_LDLIBS := -llog


LOCAL_MODULE := addcpp

LOCAL_SRC_FILES := ADDITION.CPP


include $(BUILD_SHARED_LIBRARY)





The name of the Android.mk file is a cases sensitive first letter is must be capital 'Android.mk'



Here the LOCAL_MODULE is any name you want to give , this name may call via the native method on android



LOCAL_SRC_FILES is the file name of your cpp class file


4]:- Add the CPP file on your jni directory .

The CPP class file having the following structure


ex:- 1

#include <jni.h>

#include "stdio.h"

#include <string.h>

#include "com_testcpp_HelloWord.h"



JNIEXPORT jstring JNICALL Java_com_testcpp_HelloWord_hello(JNIEnv * env, jobject obj)

{



jstring jstr = env->NewStringUTF("Welcome C++ on Android By Mahesh Nawale ");

return jstr;

}



ex:- 2

#include <jni.h>

#include "stdio.h"

#include <string.h>

#include "com_additionviacpp_NativeLib.h"



JNIEXPORT jint JNICALL Java_com_additionviacpp_NativeLib_addition(JNIEnv * env, jobject obj, jint value1, jint value2)

{

return (value1 + value2);

}




Here I give 2 different example of the CPP classes

This Classes are not the pure cpp classes



Android dose not parse the CPP classes which are written on pure cpp

Android use the JNI (Java Native Interface) classes which contain the cpp functionality .







5]:- Refresh the android project on the eclise or press F5



6];- Select the CPP file on left side of the project explore function Right Click on the then press the NEW-> OTHER so you got the following window








This will convert your project with the c++ compatible , so your project will contain the cpp libraries for your projects



Then you got the new window as follows








Then choose your project and below choose Makefile project and – Other Toolchain –. Click Finish



After doing this Eclipse will ask you if you want to switch to C/C++ perspective. Choose Yes because otherwise you wouldn’t be able to set C/C++ build preferences.













7]:-Click on your project with right button and select Properties or press Alt+Enter

Choose C/C++ Build and configure ndk-build as a build command



In Builder settings fill ndk-build into Build command entry. You have to uncheck Use default build command. You also need to have ndk-build script in your PATH. As follows







On the Use default build command

add the "bash" and then the respective path of ndk upto build folder







8]:- Choose C/C++ General->Paths and Symbols and configure include path



In Includes tab choose GNU C or GNU C++ and click Add… button.

Add paths for the respective programming language here I add the paths for the GNUC++



I added three different paths for the ndk . On which one off is your jni folder of your projects



see follows





1]- add the ndk\source\android\native_app_glue

2]- add the jni folder of your project

3]- ndk\toolchains\mipsel-linux-android-4.6\prebuilt\windows\lib\gcc\mipsel-linux-android\4.6\include



4]-ndk\toolchains\mipsel-linux-android-4.6\prebuilt\windows\lib\gcc\mipsel-linux-android\4.6\include-fixed



5]-ndk\platforms\android-9\arch-arm\usr\include





Add the above paths of your ndk respective but for the 2nd one you have to mention your jni folder of your projects





9]- After compilation of all this steps we have to create the .h file (header file) for our cpp class which we have to include as a header file on our cpp class see the below image





For the creation of a header file of your project you have to use the javah command of a jdk



You have to write a java code on your project as follows



for the example 1 of CPP class which call the native method of cpp on its static method


package com.testcpp;


public class HelloWord 
{



public native String hello();

     static

     {

       System.loadLibrary("testcpp");

      }


}



for the example 2 of CPP class



package com.additionviacpp;



public class NativeLib {

static {

System.loadLibrary("addcpp");

}

public native int addition( int v1, int v2 );

}



Using this classes we create the header file .h for the project which have the signature of this classes which call the native methods for calling cpp functionality . For that open the command prompt go to the bin\classes folder of your project then type the following command



ex:- project_name\bin\classes\ javah com.xyz.java_file_name see above image.





It will create the .h file with your package name on the bin\classes folder Don't edit this file Please



10]:- Cut paste this .h file on your jni folder



Then open your Cpp class file on any editor,  add the file as header file on your cpp code ex:-


#include "com_testcpp_HelloWord.h"

#include "com_additionviacpp_NativeLib.h"



see the examples one and tow as above CPP classes



11]- Now we have to compile this cpp class with the ndk-build command see the following image

















We use the above command of ndk-build



open the command prompt and go to the your project name as above



ex:- \project_name> \ndk\ndk-build.cmd



This will create the .so file



On the java method where we call the static function to load the System.loadLibrary("testcpp");

the name of the loadLibrary function is same as the .so file but we don't have to mention the lib extension on the static method of a java class.







The 1st example source code as follows





MainActivity.java



package com.testcpp;



import android.os.Bundle;

import android.app.Activity;

import android.util.Log;

import android.view.Menu;

import android.widget.TextView;



public class MainActivity extends Activity 
{



TextView txtHello;

HelloWord obj;


@Override

protected void onCreate(Bundle savedInstanceState) 
{

    super.onCreate(savedInstanceState);

    setContentView(R.layout.activity_main);

    obj = new HelloWord();

    String helloText = obj.hello();


    txtHello=(TextView)findViewById(R.id.testText);

    txtHello.setText(helloText);


}



@Override

public boolean onCreateOptionsMenu(Menu menu)
 {

      // Inflate the menu; this adds items to the action bar if it is present.

      getMenuInflater().inflate(R.menu.activity_main, menu);

      return true;

    }






}



HelloWord class which call the native library of the Cpp code








/**

* @(#)HelloWord.java

*

*

* @author Mahesh Nawale

* @version 1.00 2013/3/5

*/



package com.testcpp;

public class HelloWord
 {



    public native String hello();

    static

    {

        System.loadLibrary("testcpp");

     }



}



activity_main.xml





<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"

xmlns:tools="http://schemas.android.com/tools"

android:layout_width="match_parent"

android:layout_height="match_parent"

tools:context=".MainActivity" >



<TextView

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_centerHorizontal="true"

android:layout_centerVertical="true"

android:text="@string/hello_world"

android:id="@+id/testText" />



</RelativeLayout>



Examples 2 source code which is the addition of tow numbers



package com.additionviacpp;

import android.os.Bundle;

import android.app.Activity;

import android.util.Log;

import android.view.Menu;

import android.view.View;

import android.widget.Button;

import android.widget.EditText;

import android.widget.TextView;

import android.view.View.OnClickListener;

public class MainActivity extends Activity {



NativeLib ObjnativeLib;

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

setContentView(R.layout.activity_main);


ObjnativeLib = new NativeLib();


// Setup the UI

Button buttonCalc = (Button) findViewById(R.id.btmCalc);



buttonCalc.setOnClickListener(new OnClickListener() {

TextView result = (TextView) findViewById(R.id.txt_result);

EditText value1 = (EditText) findViewById(R.id.txt_no1);

EditText value2 = (EditText) findViewById(R.id.txt_no2);



public void onClick(View v) 
{

      int v1, v2, res;

      v1 = Integer.parseInt(value1.getText().toString());

      v2 = Integer.parseInt(value2.getText().toString());







      res = ObjnativeLib.addition(v1, v2);


      result.setText(new Integer(res).toString());

   }

});



}


@Override

public boolean onCreateOptionsMenu(Menu menu) 
{

     // Inflate the menu; this adds items to the action bar if it is present.

     getMenuInflater().inflate(R.menu.activity_main, menu);

    return true;

  }



}



NativeLib class


package com.additionviacpp;



public class NativeLib 
{

   static 
   {

    System.loadLibrary("addcpp");

   }

  public native int addition( int v1, int v2 );

}


activity_main.xml code


<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"

xmlns:tools="http://schemas.android.com/tools"

android:layout_width="match_parent"

android:layout_height="match_parent"

tools:context=".MainActivity" >



<TextView

android:id="@+id/textView1"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:text="@string/hello_world" />



<EditText

android:id="@+id/txt_no1"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_alignParentLeft="true"

android:layout_below="@+id/textView1"

android:ems="10" />



<TextView

android:id="@+id/textView2"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_alignParentLeft="true"

android:layout_below="@+id/txt_no1"

android:layout_marginTop="14dp"

android:text="+"

android:textSize="50dp"/>



<EditText

android:id="@+id/txt_no2"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_alignParentLeft="true"

android:layout_below="@+id/textView2"

android:ems="10" >



<requestFocus />

</EditText>



<TextView

android:id="@+id/txt_result"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_alignParentLeft="true"

android:layout_below="@+id/txt_no2"

android:layout_marginTop="80dp"

android:text="TextView" />



<Button

android:id="@+id/btmCalc"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_alignParentLeft="true"

android:layout_below="@+id/txt_no2"

android:layout_marginTop="24dp"

android:text="=" />



</RelativeLayout>

The Oput of above two examples as follows :



Example 1:-


Example 2:-




Thank you

Mahesh Nawale

No comments:

Post a Comment