Android NDK开发详解之JNI中的库文件
Android NDK开发详解之JNI中的库文件
- 简介
- 工作原理
- 流程
- 原生 activity 和应用
简介
本部分简要介绍了 NDK 的工作原理。Android NDK 是一组使您能将 C 或 C++(“原生代码”)嵌入到 Android 应用中的工具。能够在 Android 应用中使用原生代码对于想执行以下一项或多项操作的开发者特别有用:
在平台之间移植其应用。重复使用现有库,或者提供其自己的库供重复使用。在特定情况下提高性能,特别是像游戏这种计算密集型应用。
工作原理
本部分介绍了在为 Android 构建原生应用时使用的主要组件,并且介绍了构建和封装过程。
主要组件
在构建应用时,您应该已经了解以下组件:
原生共享库:NDK 从 C/C++ 源代码构建这些库或 .so 文件。原生静态库:NDK 也可构建静态库或 .a 文件,而您可将静态库关联到其他库。Java 原生接口 (JNI):JNI 是 Java 和 C++ 组件用于相互通信的接口。本指南假设您具备 JNI 知识;如需了解相关信息,请查阅 Java 原生接口规范。应用二进制接口 (ABI):ABI 可以非常精确地定义应用的机器代码在运行时应该如何与系统交互。NDK 根据这些定义构建 .so 文件。不同的 ABI 对应不同的架构:NDK 为 32 位 ARM、AArch64、x86 及 x86-64 提供 ABI 支持。如需了解详情,请参阅 Android ABI。清单:如果您编写的应用不包含 Java 组件,必须在清单中声明 NativeActivity 类。要详细了解如何执行此操作,请参阅使用 native_activity.h 接口。
流程
为 Android 开发原生应用的一般流程如下:
设计应用,确定要使用 Java 实现的部分,以及要以原生代码形式实现的部分。注意:虽然可以完全避免使用 Java,但您可能会发现 Android Java 框架对于控制显示和界面等任务很有用。像创建任何其他 Android 项目一样创建一个 Android 应用项目。如果要编写纯原生应用,请在 AndroidManifest.xml 中声明 NativeActivity 类。如需了解详情,请参阅原生 activity 和应用。在“JNI”目录中创建一个描述原生库(包括名称、标记、关联库和要编译的源文件)的 Android.mk 文件。或者,您也可以创建一个配置目标 ABI、工具链、发布/调试模式和 STL 的 Application.mk 文件。对于其中任何您未指明的项,将分别使用以下默认值:ABI:所有非弃用的 ABI模式:发布STL:系统将原生源代码放在项目的 jni 目录下。使用 ndk-build 编译原生(.so、.a)库。构建 Java 组件,生成可执行 .dex 文件。将所有内容封装到一个 APK 文件中,包括 .so、.dex 以及应用运行所需的其他文件。
原生 activity 和应用
Android SDK 提供了辅助类 NativeActivity,可用于编写完全原生的 activity。NativeActivity 可处理 Android 框架与原生代码之间的通信,因此您不必子类化该类或调用其方法,而只需在 AndroidManifest.xml 文件中将您的应用声明为原生应用,然后开始创建该原生应用。
使用 NativeActivity 的 Android 应用仍会在其自己的虚拟机中运行,与其他应用以沙盒的形式分隔。因此,您仍可通过 JNI 访问 Android 框架 API。在某些情况下(例如对于传感器、输入事件和资源),NDK 提供可使用的原生接口,而无需通过 JNI 调用。如需详细了解此类支持,请参阅原生 API。
无论是否要开发原生 activity,我们都建议使用传统 Android 构建工具创建项目。这样有助于确保使用正确的结构构建和封装 Android 应用。
Android NDK 为实现原生 activity 提供两个选项:
native_activity.h 头文件会定义 NativeActivity 类的原生版本。其中包含创建原生 activity 所需的回调接口和数据结构。由于应用的主线程会处理回调,因此回调实现不能阻止主线程,否则可能会收到 ANR(应用无响应)错误,因为主线程在回调返回之前无响应。android_native_app_glue.h 文件会定义基于 native_activity.h 接口构建的静态辅助库。它会派生出另一个线程,用于处理事件循环中的回调或输入事件等。将这些事件移至单独的线程可防止任何回调阻止主线程。
此外,<ndk_root>/sources/android/native_app_glue/android_native_app_glue.c 源代码也可供使用,使您能够修改实现。
如需详细了解如何使用此静态库,请查看原生 activity 示例应用及其文档。<ndk_root>/sources/android/native_app_glue/android_native_app_glue.h 文件中的注释提供了更多其他信息。
使用 native_activity.h 接口
要使用 native_activity.h 接口实现原生 activity,请执行以下操作:
在项目的根目录中创建一个 jni/ 目录。此目录用于存储所有原生代码。在 AndroidManifest.xml 文件中声明原生 activity。由于您的应用没有 Java 代码,因此请将 android:hasCode 设为 false。
<application android:label="@string/app_name" android:hasCode="false">
您必须将 activity 标记的 android:name 属性设置为 NativeActivity。
<activity android:name="android.app.NativeActivity"android:label="@string/app_name">
注意:您可以子类化 NativeActivity。如果子类化该类,请使用子类的名称,而不是 NativeActivity。
meta-data 标记的 android:value 属性会指定共享库的名称,其中包含应用的入口点(例如 C/C++ main),省略库名的 lib 前缀和 .so 后缀。
<manifest><application><activity><meta-data android:name="android.app.lib_name"android:value="native-activity" /><intent-filter><action android:name="android.intent.action.MAIN" /><category android:name="android.intent.category.LAUNCHER" /></intent-filter></activity></application>
</manifest>
创建用于原生 activity 的文件,并实现 ANativeActivity_onCreate 变量中指定的函数。应用在原生 activity 启动时会调用此函数。此函数类似于 C/C++ 中的 main,它会接收 ANativeActivity 结构的指针,其中包含您需要编写的各个回调实现的函数指针。在 ANativeActivity->callbacks 中设置回调实现的适用回调函数指针。
将 ANativeActivity->instance 字段设置为您要使用的特定数据的任何实例的地址。
实现您希望 activity 在启动时执行的任何其他操作。
实现您在 ANativeActivity->callbacks 中设置的其余回调。如需详细了解何时调用回调,请参阅管理 activity 生命周期。
开发应用的其余部分。
在项目的 jni/ 目录中创建 Android.mk file,向构建系统描述您的原生模块。如需了解详情,请参阅 Android.mk。
创建 Android.mk 文件后,使用 ndk-build 命令编译原生代码。
cd <path>/<to>/<project>
$NDK/ndk-build
像平常一样构建和安装 Android 项目。如果原生代码存放在 jni/ 目录中,构建脚本会自动将从原生代码构建的 .so 文件封装到 APK 中。
相关文章:
Android NDK开发详解之JNI中的库文件
Android NDK开发详解之JNI中的库文件 简介工作原理流程原生 activity 和应用 简介 本部分简要介绍了 NDK 的工作原理。Android NDK 是一组使您能将 C 或 C(“原生代码”)嵌入到 Android 应用中的工具。能够在 Android 应用中使用原生代码对于想执行以下…...
KNN模型
使用K-Nearest Neighbors (KNN)算法进行分类。首先加载一个数据集,然后进行预处理,选择最佳的K值,并训练一个KNN模型。 # encodingutf-8 import numpy as np datas np.loadtxt(datingTestSet2.txt) # 加载数据集,返回一个numpy数…...
Python 学习1 基础
文章目录 基础字符串字面量常用的值类型注释变量print语句数据类型数据类型转换标识符运算符 字符串拓展小结 2023.10.28 周六 最近打算学一下Python,毕竟确实简单方便,而且那个编程语言排名还是在第一。不过不打算靠它吃饭,深不深入暂且不说…...
网络协议--TCP的超时与重传
21.1 引言 TCP提供可靠的运输层。它使用的方法之一就是确认从另一端收到的数据。但数据和确认都有可能会丢失。TCP通过在发送时设置一个定时器来解决这种问题。如果当定时器溢出时还没有收到确认,它就重传该数据。对任何实现而言,关键之处就在于超时和重…...
Thread
Thread 线程启动线程第一种创建线程线程的第二种创建方式使用匿名内部类完成线程的两种创建 Thread API线程的优先级线程提供的静态方法守护线程用户线程和守护线程的区别体现在进程结束时 多线并发安全问题同步块 线程 启动线程 启动线程:调用线程的start方法,而不是直接调用…...
FOC系列(二)----继续学习DRV8301芯片
一、 程序框图 跟随上篇博客咱们继续往下看,下面是芯片内部的程序框图: 1.1 BUCK电路 1.2 内部各电源 1.3 SPI通信、栅极驱动器和时序控制器 1.4 MOSFET驱动电路 1.5 电流采样放大电路 数据手册只是给出了这一部分框图,但是没有更加详细的介…...
A. Directional Increase -前缀和与差分理解 + 思维
题面 分析 观察指针移动的性质,可以发现每一段都是从起点走到终点,在原路返回,这样每一段也就表示,在起点处加一,在终点处减一,形成了很明显的差分结构,思考能否构造出a数组的关键就是他的前缀…...
openpnp - java调试环境 - 最好只保留一套jdk环境
文章目录 openpnp - java调试环境 - 最好只保留一套jdk环境概述END openpnp - java调试环境 - 最好只保留一套jdk环境 概述 没注意做了啥操作, 前天好好的, 昨天下午开始, 编译好的openpnp程序就无法正常打开了. 故障表现: 程序运行后, 最多只能看到欢迎对话框(显示版本和发…...
AI技术的钓鱼邮件有多强
如今,人工智能技术的迅猛发展给各个领域都带来了前所未有的变革和进步。2023年上半年ChatGPT的火爆出圈,让人们看到了AI惊艳表现的光彩一面,但同时黑暗的一面也正在暗自发力,野蛮生长。 AI技术不仅可用于维护网络安全,…...
vue/react项目刷新页面出现404报错的原因及解决办法
Vue项目打包部署到线上后,刷新页面会提示404,下面这篇文章主要给大家介绍了关于vue/react项目刷新页面出现404报错的原因及解决办法,文中将解决的办法介绍的很详细,需要的朋友可以参考下 背景解决办法 法1:将vue/react路由模式由history路由改为has…...
黑客技术(网络安全)——如何高效学习
前言 前几天发布了一篇 网络安全(黑客)自学 没想到收到了许多人的私信想要学习网安黑客技术!却不知道从哪里开始学起!怎么学 今天给大家分享一下,很多人上来就说想学习黑客,但是连方向都没搞清楚就开始学习…...
53.MongoDB分片集群高级集群架构详解
MongoDB分片集群架构详解 为什么要使用分片 分片(shard)是指在将数据进行水平切分之后,将其存储到多个不同的服务器节点上的一种扩展方式。 一个复制集能承载的容量和负载是有限的,遇到以下场景就需要考虑使用分片 存储容量需…...
Servlet 上下文参数
7)Servlet上下文对象:ServletContext生活中的例子:张三和李四在不远处窃窃私语,并且频繁的对着你坏笑。你肯定会跑过去问:你们俩在聊什么?注意:此处的聊什么,其实就是你在咨询他们聊天的上下文&…...
ChatGPT正在测试原生文件分析功能,DALL·E 3能P图啦!
10月29日,有部分用户在社交平台上分享,ChatGPT Plus正在测试原生文件上传、分析功能,可以通过文本问答的方式,对上传的PDF等数据文件进行提问、搜索。 例如,上传一份50页的员工手册PDF文件,然后向ChatGPT提…...
三相马达的电机故障维护
目录 电机故障维护编辑 更换电机操作 三相电路 热继电器 今天继续小编的工作经验的分享,今天就说说遇到的问题吧,今天组立熔接机出现故障,后面部分出现了“咕噜噜”的杂声,走到后面一听是电机发出的声音。没有办法了就开始拆…...
【易售小程序项目】后端部署、Uniapp项目Web部署
文章目录 Uniapp项目Web打包部署为什么不部署小程序Web打包前对项目进行调整网站、小程序切换增加constant.js来控制常量将js绑定到main.js的全局变量中 WebSocket差异监听键盘呼出导航条打包部署 后端项目打包部署打包前准备打包部署 Uniapp项目Web打包部署 为什么不部署小程…...
prometheus监控kafka
一、前言 关于对kafka的监控,要求高的话可以使用kafka-exorter和jmx-exporter一起收集监控数据,要求不高的情况下可以使用kafka-exporter收集监控数据即可 二、部署 kafka-exporter 部署kafka-exporter,我是在k8s集群中部署的 编辑yaml文件…...
【STL】:list用法详解
朋友们、伙计们,我们又见面了,本期来给大家解读一下有关list的使用,如果看完之后对你有一定的启发,那么请留下你的三连,祝大家心想事成! C 语 言 专 栏:C语言:从入门到精通 数据结构…...
SQL Wildcards 通配符
SQL Wildcards 通配符 通配符用于替换字符串中的任何其他字符。 通配符与 SQL LIKE 运算符一起使用。在 WHERE 子句中使用LIKE运算符来搜索列中的指定模式。 有两个通配符与 LIKE 运算符一起使用: % - 百分号表示零个,一个或多个字符_ - 下…...
入门必学 | R语言for循环的常规应用
文章目录 何为判断语句在for循环中添加判断语句嵌套循环 在上一节中,我们介绍了迭代与for循环,并对for循环的结构与原理进行了深入的介绍。在这一节中,我们将分享for循环的常规应用,包括在其中加入判断语句与嵌套循环。 何为判断语…...
Linux应用开发之网络套接字编程(实例篇)
服务端与客户端单连接 服务端代码 #include <sys/socket.h> #include <sys/types.h> #include <netinet/in.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include <arpa/inet.h> #include <pthread.h> …...
RocketMQ延迟消息机制
两种延迟消息 RocketMQ中提供了两种延迟消息机制 指定固定的延迟级别 通过在Message中设定一个MessageDelayLevel参数,对应18个预设的延迟级别指定时间点的延迟级别 通过在Message中设定一个DeliverTimeMS指定一个Long类型表示的具体时间点。到了时间点后…...
Leetcode 3576. Transform Array to All Equal Elements
Leetcode 3576. Transform Array to All Equal Elements 1. 解题思路2. 代码实现 题目链接:3576. Transform Array to All Equal Elements 1. 解题思路 这一题思路上就是分别考察一下是否能将其转化为全1或者全-1数组即可。 至于每一种情况是否可以达到…...
K8S认证|CKS题库+答案| 11. AppArmor
目录 11. AppArmor 免费获取并激活 CKA_v1.31_模拟系统 题目 开始操作: 1)、切换集群 2)、切换节点 3)、切换到 apparmor 的目录 4)、执行 apparmor 策略模块 5)、修改 pod 文件 6)、…...
云启出海,智联未来|阿里云网络「企业出海」系列客户沙龙上海站圆满落地
借阿里云中企出海大会的东风,以**「云启出海,智联未来|打造安全可靠的出海云网络引擎」为主题的阿里云企业出海客户沙龙云网络&安全专场于5.28日下午在上海顺利举办,现场吸引了来自携程、小红书、米哈游、哔哩哔哩、波克城市、…...
MMaDA: Multimodal Large Diffusion Language Models
CODE : https://github.com/Gen-Verse/MMaDA Abstract 我们介绍了一种新型的多模态扩散基础模型MMaDA,它被设计用于在文本推理、多模态理解和文本到图像生成等不同领域实现卓越的性能。该方法的特点是三个关键创新:(i) MMaDA采用统一的扩散架构…...
学习STC51单片机31(芯片为STC89C52RCRC)OLED显示屏1
每日一言 生活的美好,总是藏在那些你咬牙坚持的日子里。 硬件:OLED 以后要用到OLED的时候找到这个文件 OLED的设备地址 SSD1306"SSD" 是品牌缩写,"1306" 是产品编号。 驱动 OLED 屏幕的 IIC 总线数据传输格式 示意图 …...
前端开发面试题总结-JavaScript篇(一)
文章目录 JavaScript高频问答一、作用域与闭包1.什么是闭包(Closure)?闭包有什么应用场景和潜在问题?2.解释 JavaScript 的作用域链(Scope Chain) 二、原型与继承3.原型链是什么?如何实现继承&a…...
SiFli 52把Imagie图片,Font字体资源放在指定位置,编译成指定img.bin和font.bin的问题
分区配置 (ptab.json) img 属性介绍: img 属性指定分区存放的 image 名称,指定的 image 名称必须是当前工程生成的 binary 。 如果 binary 有多个文件,则以 proj_name:binary_name 格式指定文件名, proj_name 为工程 名&…...
论文笔记——相干体技术在裂缝预测中的应用研究
目录 相关地震知识补充地震数据的认识地震几何属性 相干体算法定义基本原理第一代相干体技术:基于互相关的相干体技术(Correlation)第二代相干体技术:基于相似的相干体技术(Semblance)基于多道相似的相干体…...
