当前位置: 首页 > news >正文

Android usb 配件模式通信示例

当使用 Android 设备作为 USB 配件时,可以使用 Android 提供的 USB Accessory API 来进行 USB 通信。以下是一个简单的 Android USB 配件模式的通信例子。在本例中,我们将接收连接到 Android 设备的 USB 主机发送的数据并向 USB 主机发送响应。

首先,在 AndroidManifest.xml 文件中添加以下权限:

<uses-feature android:name="android.hardware.usb.accessory" />
<uses-permission android:name="android.permission.ACCESSORY" />
<uses-permission android:name="android.permission.WAKE_LOCK" />

接着,在 res/xml 文件夹中创建一个名为 accessory_filter.xml 的文件,用于指定 USB 配件的属性及其应用程序的信息。以下是示例文件的内容:

<?xml version="1.0" encoding="utf-8"?>
<resources><usb-accessory model="Android Accessory" manufacturer="Android" version="1.0" />
</resources>

在 Activity 中,添加以下代码:

private static final String TAG = "USBAccessoryDemo";private static final String ACTION_USB_PERMISSION = "com.example.android.usbaccessory.USB_PERMISSION";
private static final int TIMEOUT = 1000;
private static final int MAX_PACKET_SIZE = 16384;private UsbAccessory mAccessory;
private UsbManager mUsbManager;
private PendingIntent mPermissionIntent;
private boolean mPermissionRequestPending;
private UsbAccessoryConnection mAccessoryConnection;@Override
protected void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_main);mUsbManager = (UsbManager) getSystemService(Context.USB_SERVICE);mPermissionIntent = PendingIntent.getBroadcast(this, 0, new Intent(ACTION_USB_PERMISSION), 0);IntentFilter filter = new IntentFilter(ACTION_USB_PERMISSION);registerReceiver(mUsbReceiver, filter);HashMap<String, UsbAccessory> accessoryList = mUsbManager.getAccessoryList();if (accessoryList != null) {UsbAccessory accessory = accessoryList.get(0);if (accessory != null) {if (mUsbManager.hasPermission(accessory)) {openAccessory(accessory);} else {mUsbManager.requestPermission(accessory, mPermissionIntent);mPermissionRequestPending = true;}} else {Log.d(TAG, "accessory is null");}} else {Log.d(TAG, "accessoryList is null");}
}@Override
public void onResume() {super.onResume();if (mAccessoryConnection != null && mAccessoryConnection.isOpen()) {mAccessoryConnection.startReading();}
}@Override
public void onPause() {super.onPause();if (mAccessoryConnection != null && mAccessoryConnection.isOpen()) {mAccessoryConnection.stopReading();}
}@Override
protected void onDestroy() {super.onDestroy();unregisterReceiver(mUsbReceiver);if (mAccessoryConnection != null && mAccessoryConnection.isOpen()) {mAccessoryConnection.close();}
}private final BroadcastReceiver mUsbReceiver = new BroadcastReceiver() {public void onReceive(Context context, Intent intent) {String action = intent.getAction();if (ACTION_USB_PERMISSION.equals(action)) {synchronized (this) {UsbAccessory accessory = (UsbAccessory) intent.getParcelableExtra(UsbManager.EXTRA_ACCESSORY);if (intent.getBooleanExtra(UsbManager.EXTRA_PERMISSION_GRANTED, false)) {openAccessory(accessory);} else {Log.d(TAG, "permission denied for accessory " + accessory);}mPermissionRequestPending = false;}}}
};private void openAccessory(UsbAccessory accessory) {mAccessoryConnection = new UsbAccessoryConnection(this, accessory);mAccessoryConnection.open();
}private class UsbAccessoryConnection implements Runnable {private final UsbManager mUsbManager;private final UsbAccessory mAccessory;private UsbDeviceConnection mConnection;private UsbEndpoint mInEndpoint;private UsbEndpoint mOutEndpoint;private InputStream mInputStream;private OutputStream mOutputStream;private Thread mReadThread;private boolean mIsRunning;public UsbAccessoryConnection(Context context, UsbAccessory accessory) {mUsbManager = (UsbManager) context.getSystemService(Context.USB_SERVICE);mAccessory = accessory;}public void open() {mConnection = mUsbManager.openAccessory(mAccessory);if (mConnection != null) {mInEndpoint = mAccessory.getEndpoint(0);mOutEndpoint = mAccessory.getEndpoint(1);mInputStream = new BufferedInputStream(mConnection.openInputStream(mInEndpoint), MAX_PACKET_SIZE);mOutputStream =new BufferedOutputStream(mConnection.openOutputStream(mOutEndpoint), MAX_PACKET_SIZE);mIsRunning = true;mReadThread = new Thread(this);mReadThread.start();} else {Log.d(TAG, "openAccessory failed");}}public void close() {mIsRunning = false;if (mReadThread != null) {try {mReadThread.join();} catch (InterruptedException e) {e.printStackTrace();}}if (mInputStream != null) {try {mInputStream.close();} catch (IOException e) {e.printStackTrace();}}if (mOutputStream != null) {try {mOutputStream.close();} catch (IOException e) {e.printStackTrace();}}if (mConnection != null) {mConnection.close();}}public boolean isOpen() {return mConnection != null;}public void startReading() {if (mReadThread != null && !mReadThread.isAlive()) {mIsRunning = true;mReadThread = new Thread(this);mReadThread.start();}}public void stopReading() {mIsRunning = false;}public void write(byte[] data) {if (mOutputStream != null) {try {mOutputStream.write(data);mOutputStream.flush();} catch (IOException e) {e.printStackTrace();}}}@Overridepublic void run() {byte[] buffer = new byte[MAX_PACKET_SIZE];while (mIsRunning) {try {int len = mInputStream.read(buffer);if (len > 0) {final String receivedData = new String(buffer, 0, len);runOnUiThread(new Runnable() {@Overridepublic void run() {// 处理接收到的数据}});}} catch (IOException e) {e.printStackTrace();mIsRunning = false;}}}
}

在上面的代码中,我们首先检查是否已连接 USB 配件。如果已连接,则尝试打开连接。如果没有权限,则请求权限。如果没有可用的 USB 配件,则在日志中记录错误消息。

在打开连接后,我们创建一个 UsbAccessoryConnection 对象,并使用 open() 方法打开连接。在 open() 方法中,我们获取连接的 UsbDeviceConnection 对象,并使用它来获取读取和写入数据的输入/输出流。我们还启动了一个读线程,该线程不断地从输入流中读取数据,并将其传递给主线程以进行处理。

最后,我们可以使用 write() 方法向 USB 主机发送数据,并使用 close() 方法关闭连接。

以上就是Android usb 配件模式下的示例,在实际的开发过程中会比较复杂,但原理基本类似。如果文档对你有帮助,欢迎点赞、收藏和评论,谢谢!

相关文章:

Android usb 配件模式通信示例

当使用 Android 设备作为 USB 配件时&#xff0c;可以使用 Android 提供的 USB Accessory API 来进行 USB 通信。以下是一个简单的 Android USB 配件模式的通信例子。在本例中&#xff0c;我们将接收连接到 Android 设备的 USB 主机发送的数据并向 USB 主机发送响应。 首先&am…...

【Hive实战】Hive的压缩池与锁

文章目录 Hive的压缩池池的分配策略自动分配手动分配隐式分配 池的等待超时Labeled worker pools 标记的工作线程&#xff08;自定义线程池&#xff09;Default pool 默认池Worker allocation 工作线程的分配 锁Turn Off ConcurrencyDebuggingConfigurationhive.support.concur…...

【VUE】使用elementUI tree组件根据所选id自动回显

需求如下&#xff1a; 1.点击父级节点 将父级节点下children中所有id放入数组 2.点击父级下的子节点 将点击的子节点放入数组 3.取消选择父节点&#xff0c;将放入数组的所有子节点id删除 4.根据选择的子节点数组&#xff0c;匹配他所属的父节点 <el-tree:data"tre…...

RocketMQ, Dashboard, 控制台安装

文章说明 本文主要说明RocketMQ的控制台&#xff08;Dashboard&#xff09;的安装过程。工作中一直用的是别人装好的&#xff0c;这次终于自己亲手装了一遍。 由于每次都要启动三个应用&#xff0c;比较烦&#xff0c;于是我写了一键启动脚本&#xff0c;分享给大家。这个脚本…...

chrome解决http自动跳转https问题

1.地址栏输入&#xff1a; chrome://net-internals/#hsts 2.找到底部Delete domain security policies一栏&#xff0c;输入想处理的域名&#xff0c;点击delete。 3.再次访问http域名不再自动跳转https了。...

FastGithub 下载

Releases dotnetcore/FastGithub GitHub 无需安装&#xff0c;双击UI程序即可运行。...

TSINGSEE青犀视频安防监控管理平台EasyNVR如何配置鉴权?

视频监控汇聚平台EasyNVR是基于RTSP/Onvif协议的视频平台&#xff0c;可支持将接入的视频流进行全平台、全终端的分发&#xff0c;分发的视频流包括RTSP、RTMP、HTTP-FLV、WS-FLV、HLS、WebRTC等格式。为了满足用户的集成与二次开发需求&#xff0c;我们也提供了丰富的API接口供…...

unittest 数据驱动DDT应用

前言 一般进行接口测试时&#xff0c;每个接口的传参都不止一种情况&#xff0c;一般会考虑正向、逆向等多种组合。所以在测试一个接口时通常会编写多条case&#xff0c;而这些case除了传参不同外&#xff0c;其实并没什么区别。 这个时候就可以利用ddt来管理测试数据&#xf…...

素数个数——数论

题目描述 求 1,2,⋯,N 中素数的个数。 输入格式 一行一个整数 N。 输出格式 一行一个整数&#xff0c;表示素数的个数。 样例 #1 样例输入 #1 10样例输出 #1 4提示 对于 100% 的数据&#xff0c;1≤1081≤N≤108。 本题时间限制在2秒以内。 因为题目时间限制是2秒&#xff0c;所…...

express编写一个简单的get接口

/01编写get接口.jsconst express require(express) const app express()// 创建路由 const useRouter require(./router/user.js) // 注册路由 app.use(/api,useRouter)app.listen(8080, (req, res) > {console.log(8080监听) }) ./02编写post接口 // 注意&#xff1a;如…...

【力扣刷题C++】环形链表

来源&#xff1a;力扣&#xff08;LeetCode&#xff09; 链接&#xff1a;https://leetcode.cn/problems/linked-list-cycle 著作权归领扣网络所有。商业转载请联系官方授权&#xff0c;非商业转载请注明出处。 【题目】给你一个链表的头节点 head &#xff0c;判断链表中是否有…...

如何用Python统计CSDN质量分

文章目录 CSDN质量分查询selenium爬取博客地址单篇测试批量查询分析 CSDN质量分查询 CSDN对博客有一套分数评价标准&#xff0c;其查询入口在这里&#xff1a;质量分查询&#xff0c;效果大致如下 如果质量分太低&#xff0c;就会在博文的标题下面出现黄底黄字&#xff1a; 这…...

gin框架内容(三)--中间件

gin框架内容&#xff08;三&#xff09;--中间件 Gin框架允许开发者在处理请求的过程中&#xff0c;加入用户自己的函数。这个函数就叫中间件&#xff0c;中间件适合处理一些公共的业务逻辑&#xff0c;比如登录认证、权限校验、数据分页、记录日志、耗时统计等 即比如&#x…...

如何在工作中利用Prompt高效使用ChatGPT

导读 AI 不是来替代你的&#xff0c;是来帮助你更好工作。用better prompt使用chatgpt&#xff0c;替换搜索引擎&#xff0c;让你了解如何在工作中利用Prompt高效使用ChatGPT。 01背景 现在 GPT 已经开启了人工智能狂潮&#xff0c;不过是IT圈&#xff0c;还是金融圈。 一开…...

uniapp-小程序button分享传参,当好友通过分享点开该页面时,进行一些判断……

一、需求描述&#xff1a; 该小程序中&#xff0c;点击圈子列表页面—>进入圈子详情页面&#xff0c;在圈子详情页面点击button分享按钮后&#xff0c;发送给好友。当好友通过分享点开该页面时&#xff1a; 1.先判断是否登录&#xff0c;如果没有&#xff0c;先去登录&#…...

Ceph部署方法介绍

Ceph部署方法介绍 Installing Ceph — Ceph Documentation Ceph环境规划 admin是一个部署节点...

GoogleLeNet V2 V3 —— Batch Normalization

文章目录 Batch Normalizationinternal covariate shift激活层的作用BN执行的位置数据白化网络中的BN层训练过程 BN的实验效果MNIST与GoogleLeNet V1比较 GoogleLeNet出来之后&#xff0c;Google在这个基础上又演进了几个版本&#xff0c;一般来说是说有4个版本&#xff0c;之前…...

Mac 系统钥匙串证书不受信任

Mac 系统钥匙串证书不受信任 解决办法 通过尝试安装 Apple PKI 的 Worldwide Developer Relations - G4 (Expiring 12/10/2030 00:00:00 UTC) 解决该异常问题 以上便是此次分享的全部内容&#xff0c;希望能对大家有所帮助!...

一个企业级的文件上传组件应该是什么样的

目录 1.最简单的文件上传 2.拖拽粘贴样式优化 3.断点续传秒传进度条 文件切片 计算hash 断点续传秒传(前端) 断点续传秒传(后端) 进度条 4.抽样hash和webWorker 抽样hash(md5) webWorker 时间切片 5.文件类型判断 通过文件头判断文件类型 6.异步并发数控制(重要…...

安全渗透重点内容

this是js中的一个关键字&#xff0c;在不同的场合使用&#xff0c;this的值会发生变化&#xff0c;下面我将详细的介绍this在函数中的各种指向。 在方法中&#xff0c;this表示该方法所属的对象。 如果单独使用&#xff0c;this表示全局对象。 在函数中&#xff0c;this表示全…...

Wan2.2-I2V-A14B企业级部署案例:单卡24GB显存实现高并发视频API服务

Wan2.2-I2V-A14B企业级部署案例&#xff1a;单卡24GB显存实现高并发视频API服务 1. 企业级视频生成解决方案概述 在数字内容创作领域&#xff0c;视频生成技术正经历革命性变革。Wan2.2-I2V-A14B作为新一代文生视频模型&#xff0c;通过私有化部署方案&#xff0c;为企业提供…...

Python安全开发之简易Xss检测工具(详细注释)

核心代码&#xff1a;import requests # requests 库 - HTTP 请求处理库 # 【常用功能】: # requests.get(url) - 发送 HTTP GET 请求 # requests.post(url, data) - 发送 HTTP POST 请求 # response.text - 获取响应体内容&#xff08;字符串&#xff09; #…...

别再只盯着EMD了!滚动轴承故障诊断,试试VMD和MCKD这些新方法(附Python代码对比)

滚动轴承故障诊断&#xff1a;VMD与MCKD的实战对比与Python实现 滚动轴承作为旋转机械的核心部件&#xff0c;其健康状态直接影响设备运行安全。传统经验模态分解&#xff08;EMD&#xff09;虽广泛应用&#xff0c;但在处理强噪声和非平稳信号时存在明显局限。本文将深入解析变…...

Phi-4-mini-reasoning部署教程:Nginx反向代理+Basic Auth安全加固

Phi-4-mini-reasoning部署教程&#xff1a;Nginx反向代理Basic Auth安全加固 1. 项目介绍 Phi-4-mini-reasoning是一款由微软开源的轻量级AI模型&#xff0c;专注于数学推理、逻辑推导和多步解题等强逻辑任务。这个3.8B参数的模型虽然体积小巧&#xff0c;但在推理能力上表现…...

别再手动调时间了!手把手教你用LinuxPTP的ptp4l和phc2sys搞定TSN网络时钟同步

工业TSN网络高精度时钟同步实战&#xff1a;从原理到生产环境部署 在工业自动化、智能驾驶和实时音视频传输领域&#xff0c;微秒级的时间同步已成为刚需。传统NTP协议毫秒级的精度在这些场景下显得力不从心&#xff0c;而基于IEEE 1588和802.1AS协议的PTP&#xff08;精确时间…...

智能电网RAG优化:闭环协同与精准检索

RAG论文原理解析、公式含义与错误点对点修正方案 一、论文核心原理详细解析(含场景举例) 本文针对通用RAG框架在术语密集、强监管垂直领域(智能电网)的三大原生适配瓶颈,提出了** RAG领域原生闭环协同RAG范式**,核心是将智能电网领域知识嵌入检索-生成-评估全生命周期,…...

2026硬核对比:Claude 4.6官网双版本解析与Gemini 3.1 Pro镜像如何选

对于追求极致编码质量与深度推理的开发者与技术决策者&#xff0c;2026年Anthropic推出的Claude 4.6系列&#xff08;含旗舰Opus与高性价比Sonnet&#xff09;在智能体&#xff08;Agent&#xff09;能力与长上下文处理上树立了新标杆。 若想在国内网络环境下零成本深度对比其…...

【HALCON实战】set_window_param:解锁图形窗口高级定制与性能调优

1. 为什么你需要掌握set_window_param&#xff1f; 在机器视觉项目开发中&#xff0c;图形窗口就像工程师的眼睛。我见过太多同行把90%的精力花在算法优化上&#xff0c;却忽视了窗口显示这个"最后一公里"问题。直到某次在客户现场演示时&#xff0c;程序因为频繁刷新…...

C++程序发生崩溃闪退后为什么会自动重启?是因为程序中启用了重启管理器,系统感知到程序异常退出后自动重启程序

最近在使用sdkdemo程序测试我们的SDK功能时&#xff0c;发现当我们关闭程序后&#xff08;程序确实关闭了&#xff09;&#xff0c;程序居然又自动启动起来了&#xff01;后来运行Debug版本的sdkdemo&#xff0c;在关闭程序时会弹出报错提示框&#xff1a;估计是程序在退出时产…...

ArcGIS Pro脚本工具实战:一键自动化面要素数据质量检查与修复

1. 为什么需要自动化面要素质检工具 在GIS数据处理工作中&#xff0c;面要素的质量检查是个绕不开的痛点。我做过不少国土调查和城市规划项目&#xff0c;每次拿到甲方提供的原始数据&#xff0c;光是检查拓扑错误就得花上大半天。传统的手动检查流程有多繁琐呢&#xff1f;你得…...