016_PendingIntent 翻译学习

PendingIntent

官方:http://developer.android.com/reference/android/app/PendingIntent.html

相关博客:http://blog.youkuaiyun.com/harvic880925/article/details/42030955包含总结PendingIntent的其他文章,以及两个容易出错的地方提醒

类信息:public final class PendingIntent extends Object implementsParcelable

简介:PendingIntent是对一个Intent对象和目标动作的一个描述,它包含了一个Intent对象,但是这个Intent所代表的动作并不会马上得到执行,而是在之后某一时刻执行,比如通过PendingIntent发出一个通知,那么得在这个通知被点击时,这个Intent才会执行。同时,执行这个PendingIntent的应用并不一定是发出这个PendingIntent的应用A本身,如果是其他应用B来执行这个PendingIntent,那么这个其他应用B将会以应用A的名义来执行这个操作。

通过getActivity(Context context, int requestCode, Intent intent, intflags)系列方法可以从系统取得一个用于启动一个Activity的PendingIntent对象;
 通过getService(Context context, int requestCode, Intent intent, intflags)方法可以从系统取得一个用于启动一个Service的PendingIntent对象;

通过getBroadcast(Context context, int requestCode, Intent intent, intflags)方法可以从系统取得一个用于向BroadcastReceiver的Intent广播的PendingIntent对象。

一个PendingIntent本身就是一个系统令牌的引用,它可以实现获取对象的的元数据。这表示即使拥有这个PendingIntent的进程关闭了,这个PendingIntent对于那些收到它的进程依然有效。如果创建这个PendingIntent的程序又重新运行并重新获取同一个类型的PendingIntent(相同的操作,action,数据,类型和组件以及相同的标志),那么获取的这个PendingIntent还是指向同一个系统令牌(当这个令牌仍然有效的时候),当然,这个程序可以用cancel()来移除这个PendingIntent。

因此,当我们期望获得不同的PendingIntent时,我们必须确保它们所包含的Intent是不同的,需要的注意的是,我们不可以通过设置Intent的extra数据的不同来区分Intent。判断两个Intent是否相同,可以通过Intent提供的filterEquals(Intent other)方法。

à Intent由以下几个部分组成:动作(action),数据(data),分类(Category),类型(Type),组件(Component),和扩展信息(Extra)。两个Intent相同时,那么出Extra信息可以不同外,其他信息都是相同的。

翻译:

嵌套类

PendingIntent.CanceledException类:当这个PendingIntent对象已经被取消或者不可执行任务时发送任务,则会抛出这个异常;

PendingIntent.OnFinished接口:当发送的一个操作已经执行完成时将调用这个回调。

常量

FLAG_CANCEL_CURRENT    这个标志表示当已经存在一个与当前所需生成的PendingIntent对象相同的对象时(filterEquals(Intentother)方法返回true),那么将会先取消之前的那个PendingIntent对象,再生成新的这个对象。  它可以实现Intent携带的Extra Data更新,并且只有与这个新对象绑定的实体才可以使用它。

FLAG_UPDATE_CURRENT    这个标识表示当已经存在一个与当前所需生成的PendingIntent对象相同的对象时(filterEquals(Intent other)方法返回true),它只会去更新Extra Data中的内容,而所有与这个PendingIntent对象绑定的实体都可以使用新的Extra Data数据。

FLAG_NO_CREATE    这个标志表示当描述的这个对象不存在时,就简单地返回null,而不去生成它。

FLAG_ONE_SHOT   这个标志表示这个PendingIntent对象只能使用一次。在第一次使用send()方法调用以后,之后的所有调用都会失败。

公共方法

1、public void cancel()

取消当前的一个PendingIntent对象。只有生成PendingIntent对象的原应用可以取消它。

2、public booleanequals (Object otherObj)

比较两个PendingIntent对象是否相同,当这两个对象代表同一应用的相同操作时返回true。

3、public staticPendingIntent getActivity (Context context, int requestCode, Intent intent, intflags)

返回一个可用于启动一个Activity的PendingIntent对象。需要注意的是这个activity会在当前应用之外启动,因此这个PendingIntent对象的Intent必须使用启动标签:Intent.FLAG_ACTIVITY_NEW_TASK。

出于安全原因考虑,这里的Intent必须是通过Intent.setClass方法明确指定这个需要启动的Activity。

4、public staticPendingIntent getBroadcast (Context context, int requestCode, Intent intent,int flags)

返回一个可用于启动一个Braodcast的PendingIntent对象。

5、public staticPendingIntent getService (Context context, int requestCode, Intent intent, intflags)

返回一个可用于启动一个Service的PendingIntent对象。

6、public StringgetCreatorPackage ()                                  add inandroid4 .2

返回创建这个PendingIntent对象的包名,它是这个对象的一个标识。这个String对象由系统返回,因此应用无法作假。

7、public intgetCreatorUid ()                                        add inandroid4 .2

返回创建这个PendingIntent对象的应用uid,它是这个对象的一个标识。这个String对象由系统返回,因此应用无法作假。

8、public UserHandlegetCreatorUserHandle ()                         add in android4 .2

返回创建这个PendingIntent对象的应用UserHandle,它是这个对象的一个标识。这个String对象由系统返回,因此应用无法作假。

9、public IntentSendergetIntentSender ()

返回包装这个PendingIntent对象的IntentSender对象。

10、public StringgetTargetPackage ()

返回创建这个PendingIntent对象的包名。这个方法已经在android 4.2中被getCreatorPackage方法取代。

11、public int hashCode()

返回这个PendingIntent对象的hash code。两个相同的对象的hash code应该是一样的。

需要自己去覆盖Object的这个hashCode方法。

12、public static PendingIntentreadPendingIntentOrNullFromParcel (Parcel in)

读取Parcel对象中的Messengener对象或者null。它是在方法writePendingIntentOrNullToParcel(PendingIntent, Parcel) 中指定的。

13、public void send(int code)

执行关联到这个PendingIntent的操作。

14、public void send(Context context, int code, Intent intent, PendingIntent.OnFinished onFinished,Handler handler, String requiredPermission)                             add in android 4.0

执行关联到这个PendingIntent的操作。

15、public void send ()

执行关联到这个PendingIntent的操作。

16、public void send(Context context, int code, Intent intent)

执行关联到这个PendingIntent的操作。

17、public void send(Context context, int code, Intent intent, PendingIntent.OnFinished onFinished,Handler handler)

执行关联到这个PendingIntent的操作。

18、public static voidwritePendingIntentOrNullToParcel (PendingIntent sender, Parcel out)

制定一个PendingIntent或者null对象到Parcel对象。

19、public voidwriteToParcel (Parcel out, int flags)

将这个对象写入到Parcel。

 

<think>我们正在讨论Android中的PendingIntent标志:FLAG_IMMUTABLE、FLAG_MUTABLE和FLAG_ONE_SHOT。这些标志用于控制PendingIntent的行为,特别是在安全性和灵活性方面。 首先,让我们回顾一下PendingIntent是什么。PendingIntent是一种特殊的Intent,它允许其他应用程序以你的应用程序的权限执行一段代码。它通常用于通知、AlarmManager和任务调度等场景。 现在,我们分别解释这三个标志: 1. **FLAG_IMMUTABLE**: - 这个标志表示创建的PendingIntent是不可变的。也就是说,一旦创建,其内部的Intent不能被修改。其他应用程序通过PendingIntent.getActivity()、getService()或getBroadcast()获得的Intent是固定的,不能更改其内容。 - 从Android 6.0(API 23)开始,推荐使用这个标志以提高安全性。在Android 12(API 31)及以上版本,如果创建PendingIntent时没有指定可变性(即没有使用FLAG_MUTABLE),则系统会默认使用FLAG_IMMUTABLE。 - 使用场景:当你不需要让接收PendingIntent的应用程序修改其内部Intent时,使用这个标志。这可以防止恶意应用篡改Intent的内容。 2. **FLAG_MUTABLE**: - 这个标志允许创建的PendingIntent是可变动的。这意味着,获得该PendingIntent的应用程序可以修改其内部的Intent(通过使用Intent.fillIn()方法),但前提是这些修改在创建PendingIntent时被允许(即创建时指定的Intent中留有可填充的字段,比如使用Intent.setComponent()明确指定了组件,则其他组件无法修改)。 - 注意:在Android 12(API 31)及以上版本,如果需要创建可变的PendingIntent,必须显式指定FLAG_MUTABLE。同时,为了安全起见,应该尽可能使用FLAG_IMMUTABLE,除非有明确的需求需要可变。 - 使用场景:当你需要让接收PendingIntent的应用程序能够修改Intent中的某些部分时,例如在通知中允许通过RemoteInput添加附加数据。 3. **FLAG_ONE_SHOT**: - 这个标志表示PendingIntent只能使用一次。一旦它被使用(例如发送),后续再尝试使用相同的PendingIntent将会失败(表现为send()方法返回错误或启动的Activity不会打开)。 - 这个标志与上面两个标志可以组合使用(即可以同时是ONE_SHOT和IMMUTABLE,或ONE_SHOT和MUTABLE)。 - 使用场景:当你希望PendingIntent只被使用一次时,比如用于一次性的身份验证操作,防止被重复使用。 **总结区别**: - **FLAG_IMMUTABLE**和**FLAG_MUTABLE**主要控制PendingIntent内部Intent的可变性。前者更安全,后者更灵活。 - **FLAG_ONE_SHOT**控制PendingIntent的使用次数,只能使用一次。 **安全性考虑**: 在Android 12及以上,为了安全,系统强制要求指定可变性。如果没有指定,默认使用FLAG_IMMUTABLE。因此,如果应用需要可变性,必须显式使用FLAG_MUTABLE,但要注意,使用FLAG_MUTABLE时,应该确保填充Intent的应用程序是可信的,因为恶意应用可能会修改Intent的内容。 **示例**: 创建一个不可变的PendingIntent: ```java PendingIntent pendingIntent = PendingIntent.getActivity(context, requestCode, intent, PendingIntent.FLAG_IMMUTABLE); ``` 创建一个可变的PendingIntent(在API 31+必须显式指定): ```java PendingIntent pendingIntent = PendingIntent.getActivity(context, requestCode, intent, PendingIntent.FLAG_MUTABLE); ``` 创建一个一次性的不可变PendingIntent: ```java PendingIntent pendingIntent = PendingIntent.getActivity(context, requestCode, intent, PendingIntent.FLAG_ONE_SHOT | PendingIntent.FLAG_IMMUTABLE); ``` **注意**:在创建PendingIntent时,还需要注意其他标志,例如FLAG_UPDATE_CURRENT、FLAG_CANCEL_CURRENT等,这些标志控制当PendingIntent已经存在时的行为。 现在,根据要求生成相关问题:</think>### PendingIntent 标志详解 在 Android 开发中,`PendingIntent` 的标志用于控制其行为和安全特性,主要区别如下: #### 1. **FLAG_IMMUTABLE** (不可变标志) - **作用**:创建不可修改的 `PendingIntent`,接收方无法更改其包含的 `Intent` 内容 - **安全特性**: - 防止恶意应用篡改 `Intent` 数据(如注入额外参数)[^1] - Android 12(API 31+)强制要求:未指定可变性标志时默认使用此标志 - **使用场景**: ```java // 适用于不需要修改内容的场景(如静态通知) PendingIntent.getBroadcast(context, requestCode, intent, PendingIntent.FLAG_IMMUTABLE); ``` #### 2. **FLAG_MUTABLE** (可变标志) - **作用**:允许接收方通过 `Intent.fillIn()` 修改 `Intent` 内容 - **安全风险**: - 需谨慎使用,可能被恶意应用注入额外数据 - Android 12+ 要求显式声明此标志才能创建可变 PendingIntent - **使用场景**: ```java // 仅当需要动态修改时使用(如带输入框的通知) PendingIntent.getActivity(context, requestCode, intent, PendingIntent.FLAG_MUTABLE | PendingIntent.FLAG_UPDATE_CURRENT); ``` #### 3. **FLAG_ONE_SHOT** (单次标志) - **作用**:限制 `PendingIntent` 仅能使用一次 - **特性**: - 首次使用后自动失效,后续调用会抛出 `CanceledException` - 可与上述标志组合使用(如 `FLAG_ONE_SHOT | FLAG_IMMUTABLE`) - **使用场景**: ```java // 适用于一次性操作(如支付确认) PendingIntent.getService(context, requestCode, intent, PendingIntent.FLAG_ONE_SHOT | PendingIntent.FLAG_IMMUTABLE); ``` ### 关键区别总结 | 特性 | FLAG_IMMUTABLE | FLAG_MUTABLE | FLAG_ONE_SHOT | |---------------------|----------------------|----------------------|---------------------| | **Intent 可修改性** | ❌ 不可修改 | ✅ 可修改 | 依赖可变性标志 | | **使用次数** | 可多次使用 | 可多次使用 | ❌ 仅限一次 | | **Android 12+ 要求**| 默认标志 | 必须显式声明 | 无特殊要求 | | **典型场景** | 普通通知、广播 | 动态内容更新 | 敏感操作(如支付) | > **安全建议**:优先使用 `FLAG_IMMUTABLE`,仅在必要时选择 `FLAG_MUTABLE` 并严格验证填充数据[^2]。从 Android 12 开始,未指定可变性标志将导致崩溃(需显式设置 `FLAG_IMMUTABLE` 或 `FLAG_MUTABLE`)[^3]。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值