为 Android 中的 createChooser 方法获取 IntentSender 对象
Get IntentSender object for createChooser method in Android
我想使用新版本的 Intent.createChooser 方法,它使用 IntentSender
。
文档仅说明我可以从 PendingIntent
实例中获取它。就我而言,PendingIntent
似乎没有任何其他用途。
是否有其他方法获得 IntentSender
或者我是否需要创建 PendingIntent
?
选择器目标意图不是 PendingIntent
。例如,在下面的代码片段中,我声明了 ACTION_SEND
的意图,类型为 text/plain
,这是 Intent.createChooser
的目标意图。然后我正在创建另一个 Intent
、接收器和一个处理程序 PendingIntent
,它将在用户从选择器中选择内容后调用我的 BroadcastReceiver 的 onReceive
。
// Set up the broadcast receiver (preferably as a class member)
BroadcastReceiver broadcastReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
// Unregister self right away
context.unregisterReceiver(this);
// Component will hold the package info of the app the user chose
ComponentName component = intent.getParcelableExtra<ComponentName>(Intent.EXTRA_CHOSEN_COMPONENT);
// Do something with component
}
}
Intent intent = new Intent(Intent.ACTION_SEND);
intent.putExtra(Intent.EXTRA_TEXT, "This is my text to send.");
intent.setType("text/plain");
// Use custom action only for your app to receive the broadcast
final String shareAction = "com.yourdomain.share.SHARE_ACTION";
Intent receiver = new Intent(shareAction);
receiver.putExtra("test", "test");
PendingIntent pendingIntent = PendingIntent.getBroadcast(this, 0, receiver, PendingIntent.FLAG_UPDATE_CURRENT);
Intent chooser = Intent.createChooser(intent, "test", pendingIntent.getIntentSender());
// Before firing chooser activity, register the receiver with our custom action from above so that we receive the chosen app
context.registerReceiver(broadcastReceiver, new IntentFilter(SHARE_ACTION));
startActivity(chooser);
编辑:
在 BroadcastReceiver
的情况下,信息嵌入在您作为参数获得的意图中。选择其中一个选项后,检索 Bundle 的 extras 并使用键 Intent.EXTRA_CHOSEN_COMPONENT
,您应该能够找到用户选择的内容。
尝试添加简单的 Log.d 到 onReceive
for (String key : intent.getExtras().keySet()) {
Log.d(getClass().getSimpleName(), " " + intent.getExtras().get(key));
}
在我的例子中我得到了
ComponentInfo{org.telegram.messenger/org.telegram.ui.LaunchActivity}
对于Telegram
和
ComponentInfo{com.google.android.apps.inbox/com.google.android.apps.bigtop.activities.ComposeMessageActivity}
对于InBox
另一种方法。
/**
* Receiver to record the chosen component when sharing an Intent.
*/
static class TargetChosenReceiver extends BroadcastReceiver {
private static final String EXTRA_RECEIVER_TOKEN = "receiver_token";
private static final Object LOCK = new Object();
private static String sTargetChosenReceiveAction;
private static TargetChosenReceiver sLastRegisteredReceiver;
static boolean isSupported() {
return Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP_MR1;
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP_MR1)
static void sendChooserIntent(Activity activity, Intent sharingIntent) {
synchronized (LOCK) {
if (sTargetChosenReceiveAction == null) {
sTargetChosenReceiveAction = activity.getPackageName() + "/"
+ TargetChosenReceiver.class.getName() + "_ACTION";
}
Context context = activity.getApplicationContext();
if (sLastRegisteredReceiver != null) {
context.unregisterReceiver(sLastRegisteredReceiver);
}
sLastRegisteredReceiver = new TargetChosenReceiver();
context.registerReceiver(
sLastRegisteredReceiver, new IntentFilter(sTargetChosenReceiveAction));
}
Intent intent = new Intent(sTargetChosenReceiveAction);
intent.setPackage(activity.getPackageName());
intent.putExtra(EXTRA_RECEIVER_TOKEN, sLastRegisteredReceiver.hashCode());
final PendingIntent callback = PendingIntent.getBroadcast(activity, 0, intent,
PendingIntent.FLAG_CANCEL_CURRENT | PendingIntent.FLAG_ONE_SHOT);
Intent chooserIntent = Intent.createChooser(sharingIntent,
activity.getString(R.string.share_link_chooser_title),
callback.getIntentSender());
activity.startActivity(chooserIntent);
}
@Override
public void onReceive(Context context, Intent intent) {
synchronized (LOCK) {
if (sLastRegisteredReceiver != this) return;
context.getApplicationContext().unregisterReceiver(sLastRegisteredReceiver);
sLastRegisteredReceiver = null;
}
if (!intent.hasExtra(EXTRA_RECEIVER_TOKEN)
|| intent.getIntExtra(EXTRA_RECEIVER_TOKEN, 0) != this.hashCode()) {
return;
}
ComponentName target = intent.getParcelableExtra(Intent.EXTRA_CHOSEN_COMPONENT);
if (target != null) {
setLastShareComponentName(context, target);
}
}
}
我想使用新版本的 Intent.createChooser 方法,它使用 IntentSender
。
文档仅说明我可以从 PendingIntent
实例中获取它。就我而言,PendingIntent
似乎没有任何其他用途。
是否有其他方法获得 IntentSender
或者我是否需要创建 PendingIntent
?
选择器目标意图不是 PendingIntent
。例如,在下面的代码片段中,我声明了 ACTION_SEND
的意图,类型为 text/plain
,这是 Intent.createChooser
的目标意图。然后我正在创建另一个 Intent
、接收器和一个处理程序 PendingIntent
,它将在用户从选择器中选择内容后调用我的 BroadcastReceiver 的 onReceive
。
// Set up the broadcast receiver (preferably as a class member)
BroadcastReceiver broadcastReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
// Unregister self right away
context.unregisterReceiver(this);
// Component will hold the package info of the app the user chose
ComponentName component = intent.getParcelableExtra<ComponentName>(Intent.EXTRA_CHOSEN_COMPONENT);
// Do something with component
}
}
Intent intent = new Intent(Intent.ACTION_SEND);
intent.putExtra(Intent.EXTRA_TEXT, "This is my text to send.");
intent.setType("text/plain");
// Use custom action only for your app to receive the broadcast
final String shareAction = "com.yourdomain.share.SHARE_ACTION";
Intent receiver = new Intent(shareAction);
receiver.putExtra("test", "test");
PendingIntent pendingIntent = PendingIntent.getBroadcast(this, 0, receiver, PendingIntent.FLAG_UPDATE_CURRENT);
Intent chooser = Intent.createChooser(intent, "test", pendingIntent.getIntentSender());
// Before firing chooser activity, register the receiver with our custom action from above so that we receive the chosen app
context.registerReceiver(broadcastReceiver, new IntentFilter(SHARE_ACTION));
startActivity(chooser);
编辑:
在 BroadcastReceiver
的情况下,信息嵌入在您作为参数获得的意图中。选择其中一个选项后,检索 Bundle 的 extras 并使用键 Intent.EXTRA_CHOSEN_COMPONENT
,您应该能够找到用户选择的内容。
尝试添加简单的 Log.d 到 onReceive
for (String key : intent.getExtras().keySet()) {
Log.d(getClass().getSimpleName(), " " + intent.getExtras().get(key));
}
在我的例子中我得到了
ComponentInfo{org.telegram.messenger/org.telegram.ui.LaunchActivity}
对于Telegram
和
ComponentInfo{com.google.android.apps.inbox/com.google.android.apps.bigtop.activities.ComposeMessageActivity}
对于InBox
另一种方法。
/**
* Receiver to record the chosen component when sharing an Intent.
*/
static class TargetChosenReceiver extends BroadcastReceiver {
private static final String EXTRA_RECEIVER_TOKEN = "receiver_token";
private static final Object LOCK = new Object();
private static String sTargetChosenReceiveAction;
private static TargetChosenReceiver sLastRegisteredReceiver;
static boolean isSupported() {
return Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP_MR1;
}
@TargetApi(Build.VERSION_CODES.LOLLIPOP_MR1)
static void sendChooserIntent(Activity activity, Intent sharingIntent) {
synchronized (LOCK) {
if (sTargetChosenReceiveAction == null) {
sTargetChosenReceiveAction = activity.getPackageName() + "/"
+ TargetChosenReceiver.class.getName() + "_ACTION";
}
Context context = activity.getApplicationContext();
if (sLastRegisteredReceiver != null) {
context.unregisterReceiver(sLastRegisteredReceiver);
}
sLastRegisteredReceiver = new TargetChosenReceiver();
context.registerReceiver(
sLastRegisteredReceiver, new IntentFilter(sTargetChosenReceiveAction));
}
Intent intent = new Intent(sTargetChosenReceiveAction);
intent.setPackage(activity.getPackageName());
intent.putExtra(EXTRA_RECEIVER_TOKEN, sLastRegisteredReceiver.hashCode());
final PendingIntent callback = PendingIntent.getBroadcast(activity, 0, intent,
PendingIntent.FLAG_CANCEL_CURRENT | PendingIntent.FLAG_ONE_SHOT);
Intent chooserIntent = Intent.createChooser(sharingIntent,
activity.getString(R.string.share_link_chooser_title),
callback.getIntentSender());
activity.startActivity(chooserIntent);
}
@Override
public void onReceive(Context context, Intent intent) {
synchronized (LOCK) {
if (sLastRegisteredReceiver != this) return;
context.getApplicationContext().unregisterReceiver(sLastRegisteredReceiver);
sLastRegisteredReceiver = null;
}
if (!intent.hasExtra(EXTRA_RECEIVER_TOKEN)
|| intent.getIntExtra(EXTRA_RECEIVER_TOKEN, 0) != this.hashCode()) {
return;
}
ComponentName target = intent.getParcelableExtra(Intent.EXTRA_CHOSEN_COMPONENT);
if (target != null) {
setLastShareComponentName(context, target);
}
}
}