展开说说:Android服务之实现AIDL跨应用通信

前面几篇总结了Service的使用和源码执行流程,这里再简单分析一下如果需要Service跨进程通信该怎样做。AIDL(Android Interface Definition Language)Android接口定义语言,用于实现 Android 两个进程之间进行进程间通信(IPC)。

AIDL技术跨进程通信可以理解为是服务端和客户端之间的通信(IPC),定义Service的进程称为服务端,调用服务的进程就是客户端。

分析一下服务端生成aidl、定义Service已经再客户端调用服务。本文使用的两个APP实现,服务端是app,客户端是otherapp。

1、首先准备两个Android工程

我这里就是建一个project然后建两个module,您也可以建两个project反正最后都是安装到同一个手机的两个APP。

2、服务端工程新建aidl文件

建议直接通过鼠标右键-> New -> AIDL -> AIDL File新建一个 adil 文件,build 后生成对应的 java 类。

AIDL文件,setName是我定义的方法:

// IMyAidlInterface.aidl
package com.example.testdemo;// Declare any non-default types here with import statementsinterface IMyAidlInterface {/*** Demonstrates some basic types that you can use as parameters* and return values in AIDL.*/void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat,double aDouble, String aString);/*** 自定义方法*/void setName(String name);
}

自动生成的java文件:

这里内容不少,里面有个内部类名字叫Stub

public static abstract class Stub extends android.os.Binder implements com.example.testdemo.IMyAidlInterface{

}

Stub 类可以看到我们定义的setName方法。

注意不管你aidl文件名字叫什么编译后的java文件都是在Stub 类定义你的方法。

3、服务端定义Service并创建对应的 Stub 对象;

/*** AIDL的服务端*/
public class MyService extends Service {public static final String TAG = "MyService";private boolean setServiceRunning = true;@Overridepublic void onCreate() {super.onCreate();}@Overridepublic IBinder onBind(Intent intent) {Log.e(TAG, "onBind: " );return mStub;}IMyAidlInterface.Stub mStub = new IMyAidlInterface.Stub() {@Overridepublic void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat, double aDouble, String aString) throws RemoteException {}@Overridepublic void setName(String name) throws RemoteException {Log.e(TAG, "setName:  收到other说的name= "+name );}};
}

清单文件注册:

<serviceandroid:name="com.example.testdemo.service.MyService"android:enabled="true"android:exported="true"><intent-filter><category android:name="android.intent.category.DEFAULT"></category></intent-filter>
</service>

4、客户端要将服务端这个aidl文件拷贝过来,准备和服务端一模一样的生活环境, 两端的aidl 文件和所在包名必须一致

Intent intentService = new Intent();
intentService.setComponent(new ComponentName("com.example.testdemo","com.example.testdemo.service.MyService"));
boolean b = bindAidl(intentService);
private boolean bindAidl(Intent intent) {ServiceConnection serviceConnection = new ServiceConnection() {@Overridepublic void onServiceConnected(ComponentName componentName, IBinder iBinder) {Log.e(TAG, "onServiceConnected: " );IMyAidlInterface iMyAidlInterface = IMyAidlInterface.Stub.asInterface(iBinder);//连接成功,调用绑定的service中的方法try {iMyAidlInterface.setName("Hello 服务端,我是Server端");} catch (RemoteException e) {e.printStackTrace();}}@Overridepublic void onServiceDisconnected(ComponentName componentName) {Log.e(TAG, "onServiceDisconnected: " );}@Overridepublic void onBindingDied(ComponentName name) {Log.e(TAG, "onBindingDied: " );}@Overridepublic void onNullBinding(ComponentName name) {Log.e(TAG, "onNullBinding: " );}};boolean b = bindService(intent, serviceConnection, Context.BIND_AUTO_CREATE);Log.e(TAG, "onClick: start-bind   结果="+b);return b;
}

注意:

第一:上面代码intentService.setComponent(new ComponentName("com.example.testdemo","com.example.testdemo.service.MyService"));中创建ComponentName实例的第一个参数是应用的包名,不携带类的上层路径;第二个参数是你定义的服务这个Java文件的全类名

第二:bindService方法如果返回报错,需要在androidManifest,xml中加入
<uses-permission android:name="android.permission.QUERY_ALL_PACKAGES"
    tools:ignore="QueryAllPackagesPermission" />
 <queries>
     <package android:name="com.example.testdemo"/>
 </queries>
第三:如果加了上面第二点这些导致项目编译失败,报错"manifest merger failed xxxx " ,需要把根工程里的build.gradle中的classPath升级到3.5.4或以上,比如classpath "com.android.tools.build:gradle:3.5.4"

才疏学浅,如有错误,欢迎指正,多谢。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/43941.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Clickhouse的联合索引

Clickhouse 有了单独的键索引&#xff0c;为什么还需要有联合索引呢&#xff1f;了解过mysql的兄弟们应该都知道这个事。 对sql比较熟悉的兄弟们估计看见这个联合索引心里大概有点数了&#xff0c;不过clickhouse的联合索引相比mysql的又有些不一样了&#xff0c;mysql 很遵循最…

Spring源码二十:Bean实例化流程三

上一篇Spring源码十九&#xff1a;Bean实例化流程二中&#xff0c;我们主要讨论了单例Bean创建对象的主要方法getSingleton了解到了他的核心流程无非是&#xff1a;通过一个简单工厂的getObject方法来实例化bean&#xff0c;当然spring在实例化前后提供了扩展如&#xff1a;bef…

第5章-组合序列类型

#全部是重点知识&#xff0c;必须会。 了解序列和索引|的相关概念 掌握序列的相关操作 掌握列表的相关操作 掌握元组的相关操作 掌握字典的相关操作 掌握集合的相关操作1&#xff0c;序列和索引 1&#xff0c;序列是一个用于存储多个值的连续空间&#xff0c;每一个值都对应一…

灵活多变的对象创建——工厂方法模式(Python实现)

1. 引言 大家好&#xff0c;又见面了&#xff01;在上一篇文章中&#xff0c;我们聊了聊简单工厂模式&#xff0c;今天&#xff0c;我们要进一步探讨一种更加灵活的工厂设计模式——工厂方法模式。如果说简单工厂模式是“万能钥匙”&#xff0c;那工厂方法模式就是“变形金刚”…

Python采集京东标题,店铺,销量,价格,SKU,评论,图片

京东的许多数据是通过 JavaScript 动态加载的&#xff0c;包括销量、价格、评论和评论时间等信息。我们无法仅通过传统的静态网页爬取方法获取到这些数据。需要使用到如 Selenium 或 Pyppeteer 等能够模拟浏览器行为的工具。 另外&#xff0c;京东的评论系统是独立的一个系统&a…

offer题目33:判断是否是二叉搜索树的后序遍历序列

题目描述&#xff1a;输入一个整数数组&#xff0c;判断该数组是不是某二叉搜索树的后序遍历结果。如果是则返回true,否则返回false。假设输入的数组的任意两个数字都互不相同。例如&#xff0c;输入数组{5,7,6,9,11,10,8},则返回true,&#xff0c;因为这个整数是下图二叉搜索树…

c++内存管理(上)

目录 引入 分析 说明 C语言中动态内存管理方式 C内存管理方式 new/delete操作内置类型 new和delete操作自定义类型 引入 我们先来看下面的一段代码和相关问题 int globalVar 1; static int staticGlobalVar 1; void Test() { static int staticVar 1; int localVar 1…

数图助推朝阳佳惠辽宁华联开启数字化导航、精细化管理新纪元!

近期&#xff0c;辽宁省著名零售企业朝阳佳惠与辽宁华联&#xff0c;秉持创新精神&#xff0c;大胆尝试&#xff0c;在品类空间管理方面推出了创新举措。引入了先进的数图可视化陈列管理系统&#xff0c;通过智能化、直观化的方式优化商品布局。此举不仅大幅提高了商品管理的效…

element-ui封装分页组件:实现首页、上一页、下一页、末页、跳转按钮

首页、上一页、下一页、末页、跳转按钮 因为el-pagination只有一个插槽&#xff0c;所以通过两个el-pagination插槽分别加入首页、末页按钮&#xff0c;再拼接这两个el-pagination的方式来实现首页、末页按钮跳转按钮不用加事件&#xff0c;如果el-pagination修改了前往的页数…

【work】AI八股-神经网络相关

Deep-Learning-Interview-Book/docs/深度学习.md at master amusi/Deep-Learning-Interview-Book GitHub 网上相关总结&#xff1a; 小菜鸡写一写基础深度学习的问题&#xff08;复制大佬的&#xff0c;自己复习用&#xff09; - 知乎 (zhihu.com) CV面试问题准备持续更新贴 …

聚类分析方法(二)

目录 三、层次聚类方法&#xff08;一&#xff09;层次聚类策略&#xff08;二&#xff09;AGNES算法&#xff08;三&#xff09;DIANA算法 四、密度聚类方法&#xff08;一&#xff09;基本概念&#xff08;二&#xff09;算法描述&#xff08;三&#xff09;计算实例&#xf…

Google账号输入用户名和密码后提醒要到手机通知点是,还要点击数字,但是我手机收不到

有一些朋友换了一个新的电脑后手机登录谷歌账号时&#xff0c;用户名和密码都正确输入以后&#xff0c;第三步弹出一个提示&#xff0c;要在手机上的通知栏点击是&#xff0c;并且点击手机上相应的数字才能继续登录。 但是自己的手机上下拉通知栏却没有来自谷歌的通知&#xf…

符号同步、定时同步和载波同步

符号同步、定时同步和载波同步是通信系统中重要的同步技术&#xff0c;它们各自承担着不同的功能和作用。以下是对这三种同步技术的详细解释&#xff1a; 符号同步 定义&#xff1a; 符号同步&#xff0c;也称为定时恢复或时钟恢复&#xff0c;是指在数字通信系统中&#xff…

继承关系中的访问控制

继承关系中的访问控制 类中成员的访问权限类继承中的访问权限派生类向基类转换的权限问题&#xff08;向上转型&#xff09;友元在继承中的访问权限 类中成员的访问权限 public&#xff1a;类的对象&#xff08;外部&#xff09;可以访问&#xff0c;派生类也可以访问protecte…

LeNet原理及代码实现

目录 1.原理及介绍 2.代码实现 2.1model.py 2.2model_train.py 2.3model.test.py 1.原理及介绍 2.代码实现 2.1model.py import torch from torch import nn from torchsummary import summaryclass LeNet(nn.Module):def __init__(self):super(LeNet, self).__init__…

nuxt、vue树形图d3.js

直接上代码 //安装 npm i d3 --save<template><div class"d3"><div :id"id" class"d3-content"></div></div> </template> <script> import * as d3 from "d3";export default {props: {d…

Github Actions 构建Vue3 + Vite项目

本篇文章以自己创建的项目为例&#xff0c;用Github Actions构建。 Github地址&#xff1a;https://github.com/ling08140814/myCarousel 访问地址&#xff1a;https://ling08140814.github.io/myCarousel/ 具体步骤&#xff1a; 1、创建一个Vue3的项目&#xff0c;并完成代…

接口基础知识1:认识接口

课程大纲 一、定义 接口&#xff1a;外部与系统之间、内部各子系统之间的交互点。 比如日常使用的电脑&#xff0c;有电源接口、usb接口、耳机接口、显示器接口等&#xff0c;分别可以实现&#xff1a;与外部的充电、文件数据传输、声音输入输出、图像输入输出等功能。 接口的本…

262个地级市-市场潜力指数(do文件+原始文件)

全国262个地级市-市场潜力指数&#xff08;市场潜力计算方法代码数据&#xff09;_市场潜力数据分析资源-CSDN文库 市场潜力指数&#xff1a;洞察未来发展的指南针 市场潜力指数是一个综合性的评估工具&#xff0c;它通过深入分析市场需求、竞争环境、政策支持和技术创新等多个…

(2)滑动窗口算法练习:无重复字符的最长子串

无重复字符的最长子串 题目链接&#xff1a;3. 无重复字符的最长子串 - 力扣&#xff08;LeetCode&#xff09; 给定一个字符串 s &#xff0c;请你找出其中不含有重复字符的最长子串的长度。 输入: s "abcabcbb" 输出: 3 解释: 因为无重复字符的最长子串是"a…