android studio 实现类似百度地图 发布SDK机制实现(jni实现调用C++的so库,并封装jar包)

android studio  发布SDK机制实现

         本文主要是Android JNI编程相关,包括java接口打包jar包,c++编译so库,通过jni调用。并在一个全新的android项目中测试使用我们自己发布的sdk的整套流程。

写这篇文章的主要目的是,网上好像并没有这么一整套的机制实现参考。

        另外,完整的例子代码,见文章最后的链接。

一、制作SDK jar包so库

1.新建一个Android library

2.配置build。gradle

添加:

    dependencies {
        compile fileTree(dir: 'libs', include: ['*.jar'])
        testCompile 'junit:junit:4.12'
        compile 'com.android.support:appcompat-v7:23.3.0'
    }


task makeJar(type: Copy) {
    delete 'build/libs/mysdk.jar'
    from('build/intermediates/bundles/release/')
    into('build/libs/')
    include('classes.jar')
    rename('classes.jar', 'mysdk.jar')
}
makeJar.dependsOn(build)

sourceSets {
    main() {
        jniLibs.srcDirs = ['libs']
    }


完整如下:

apply plugin: 'com.android.library'
android {
    compileSdkVersion 23
    buildToolsVersion '23.0.3'

    defaultConfig {
        minSdkVersion 18
        targetSdkVersion 23
        versionCode 1
        versionName "1.0"

        ndk {
            moduleName "mylibrary"
        }
    }
    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        }
    }
    sourceSets {
        main() {
            jniLibs.srcDirs = ['libs']
        }
    }
}
    dependencies {
        compile fileTree(dir: 'libs', include: ['*.jar'])
        testCompile 'junit:junit:4.12'
        compile 'com.android.support:appcompat-v7:23.3.0'
    }


task makeJar(type: Copy) {
    delete 'build/libs/mysdk.jar'
    from('build/intermediates/bundles/release/')
    into('build/libs/')
    include('classes.jar')
    rename('classes.jar', 'mysdk.jar')
}
makeJar.dependsOn(build)
3.新建so的java接口文件

我这里单独写了一个java类写native方法,这样做到逻辑清晰,不是和大部分网上的例子写在main里面。再就是javah生成头文件的相关网上有大量文章,我这做简述。

package com.example.mylibrary;

/**
 * Created by Administrator on 2016/4/29.
 */
public class JNIInterface {
    public JNIInterface(){
    }
    public native String toTestJNI();
    public native String toTestJNI2();

    static {
        System.loadLibrary("mylibrary");
    }
}

然后build整个项目,然后控制台cd到com目录,通过javah -jni 包名。包名。包名支出JNIInterface 的class,生成。h头文件,然后 src main 右键jni folder 起名jni,拷贝进去,在新建c文件,实现代码,如下:

//
// Created by Administrator on 2016/5/3.
//

#include "com_example_mylibrary_JNIInterface.h"

JNIEXPORT jstring JNICALL Java_com_example_mylibrary_JNIInterface_toTestJNI
  (JNIEnv *env, jobject j)
  {
   return (*env)->NewStringUTF(env,"This just a t  io NDK JNI developer!");
  }

/*
 * Class:     com_example_mylibrary_JNIInterface
 * Method:    toTestJNI2
 * Signature: ()Ljava/lang/String;
 */
JNIEXPORT jstring JNICALL Java_com_example_mylibrary_JNIInterface_toTestJNI2
  (JNIEnv *env, jobject j)
  {
 return (*env)->NewStringUTF(env,"This just a t  io NDK JNI developer!");
  }

然后至此,我们可以得到classes.jar和libmylibrary.so,可以搜索找到,会有很多个,jar包无所谓,我这里so拷贝的是x86版本,因为电脑虚拟机操作系统是x86 cpu的。


二、新建Android界面项目测试

1.写一个textview测试下:

public class MainActivity extends AppCompatActivity {
    private JNIInterface interf = new JNIInterface();
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        TextView v = (TextView)findViewById(R.id.tet);
        String a =interf.toTestJNI();
        v.setText(interf.toTestJNI());
    }
}
2.配置gradle

sourceSets {
    main {
        //jniLibs.srcDirs = [ 'src/main/jniLibs/']
        jniLibs.srcDirs = ['libs']
        //jni.srcDirs = ['src/main/jni', 'src/main/jniLibs/']
    }
}
加上这句话。

引用第三方so这个网上很多方法,基本都的类似。然后这里的lbs是路径,是可以改的。我这里一开始的时候,总是提示找不到so库,原因是网上说的方法在src main下建立jnilibs文件夹,拷贝进去so,这样和这个libs是不匹配的,会找不到,所以写jbs,就拷贝到libs下。如图:

然后拷贝jar包到libs路径,然后右键add library即可。


完结:


至此运行整个项目即可通过jar包调用so库的接口,完美的实现打包jni方法,实现ui代码和so库等的分离。


资源下载:

一个是打包的完整代码,一个是调用的代码。

http://download.csdn.net/detail/villean/9510511


http://download.csdn.net/detail/villean/9510507


你可能感兴趣的:(原创)