Как отфильтровать определенные приложения для намерения ACTION_SEND (и задать отдельный текст для каждого приложения)

187

Как вы можете отфильтровать определенные приложения при использовании намерения ACTION_SEND? Этот вопрос задавался по-разному, но я не смог найти решение на основе полученных ответов. Надеюсь, кто-то может помочь. Я хотел бы предоставить возможность поделиться в приложении. Следуя совету Android Dev Александра Лукаса , я бы предпочел сделать это с помощью намерений, а не с помощью API Facebook / Twitter.

Совместное использование с намерением ACTION_SEND

Совместное использование с помощью намерения ACTION_SEND - это замечательно, но проблема в том, что (1) я не хочу, чтобы там были доступны все параметры общего доступа , я бы предпочел ограничить его FB, Twitter и электронной почтой, и (2) я не хочу делиться то же самое для каждого приложения обмена . Например, в свою долю в твиттере я собираюсь включить некоторые упоминания, и хештеги ограничивают его до 140 символов или менее, в то время как доля в фейсбуке будет включать ссылку и изображение функции.

Можно ли ограничить параметры для намерения ACTION_SEND (поделиться)? Я видел кое-что об использовании PackageManager и queryIntentActivities, но не смог выяснить связь между PackageManager и намерением ACTION_SEND.

ИЛИ

Вместо того, чтобы фильтровать приложения для обмена, моя проблема также может быть решена, если бы я мог использовать намерение ACTION_SEND, чтобы перейти непосредственно в Facebook или Twitter, а не всплывать в диалоговом окне. Если бы это было так, то я мог бы создать свой собственный диалог, и когда они нажимают «Facebook», создают особые намерения Facebook и просто отправляют их на Facebook. То же самое с Twitter.

ИЛИ это не возможно? Являются ли API Facebook и Twitter единственным способом?

Кайл Клегг
источник
Возможный дубликат: [выборочная фильтрация-намерения-выбора-на-основе-установлен-имя-пакета-андроида] [1] [1]: stackoverflow.com/questions/5734678/…
Асаф Пинхасси
1
Этот пост, похоже, является идеальным ответом: hkdevtips.blogspot.com/2013/02/…
Виталий Ольшевский,
2
эй, друг ... когда я нажимаю кнопку «Отправить», открываю диалоговое окно «Поделиться», а список «Поделиться» - «gmail, электронная почта, zapiya, подключение» и т. д. но не показывать фейсбук, WhatsApp, фейсбук мессенджер, тусовки для походов ... как я могу показать его ??
GB_Bhayani ツ
как не показать селектор, когда есть только один пункт / вариант намеренного действия на Android 6.0? проблема не отображается на менее чем Android 6.0
Zys

Ответы:

324

Насколько мне известно, в StackOverflow есть много людей, которые задают этот вопрос по-разному, но никто еще не ответил на него полностью.

Моя спецификация требовала, чтобы пользователь мог выбирать электронную почту, твиттер, фейсбук или смс с индивидуальным текстом для каждого. Вот как я это сделал:

public void onShareClick(View v) {
    Resources resources = getResources();

    Intent emailIntent = new Intent();
    emailIntent.setAction(Intent.ACTION_SEND);
    // Native email client doesn't currently support HTML, but it doesn't hurt to try in case they fix it
    emailIntent.putExtra(Intent.EXTRA_TEXT, Html.fromHtml(resources.getString(R.string.share_email_native)));
    emailIntent.putExtra(Intent.EXTRA_SUBJECT, resources.getString(R.string.share_email_subject));
    emailIntent.setType("message/rfc822");

    PackageManager pm = getPackageManager();
    Intent sendIntent = new Intent(Intent.ACTION_SEND);     
    sendIntent.setType("text/plain");


    Intent openInChooser = Intent.createChooser(emailIntent, resources.getString(R.string.share_chooser_text));

    List<ResolveInfo> resInfo = pm.queryIntentActivities(sendIntent, 0);
    List<LabeledIntent> intentList = new ArrayList<LabeledIntent>();        
    for (int i = 0; i < resInfo.size(); i++) {
        // Extract the label, append it, and repackage it in a LabeledIntent
        ResolveInfo ri = resInfo.get(i);
        String packageName = ri.activityInfo.packageName;
        if(packageName.contains("android.email")) {
            emailIntent.setPackage(packageName);
        } else if(packageName.contains("twitter") || packageName.contains("facebook") || packageName.contains("mms") || packageName.contains("android.gm")) {
            Intent intent = new Intent();
            intent.setComponent(new ComponentName(packageName, ri.activityInfo.name));
            intent.setAction(Intent.ACTION_SEND);
            intent.setType("text/plain");
            if(packageName.contains("twitter")) {
                intent.putExtra(Intent.EXTRA_TEXT, resources.getString(R.string.share_twitter));
            } else if(packageName.contains("facebook")) {
                // Warning: Facebook IGNORES our text. They say "These fields are intended for users to express themselves. Pre-filling these fields erodes the authenticity of the user voice."
                // One workaround is to use the Facebook SDK to post, but that doesn't allow the user to choose how they want to share. We can also make a custom landing page, and the link
                // will show the <meta content ="..."> text from that page with our link in Facebook.
                intent.putExtra(Intent.EXTRA_TEXT, resources.getString(R.string.share_facebook));
            } else if(packageName.contains("mms")) {
                intent.putExtra(Intent.EXTRA_TEXT, resources.getString(R.string.share_sms));
            } else if(packageName.contains("android.gm")) { // If Gmail shows up twice, try removing this else-if clause and the reference to "android.gm" above
                intent.putExtra(Intent.EXTRA_TEXT, Html.fromHtml(resources.getString(R.string.share_email_gmail)));
                intent.putExtra(Intent.EXTRA_SUBJECT, resources.getString(R.string.share_email_subject));               
                intent.setType("message/rfc822");
            }

            intentList.add(new LabeledIntent(intent, packageName, ri.loadLabel(pm), ri.icon));
        }
    }

    // convert intentList to array
    LabeledIntent[] extraIntents = intentList.toArray( new LabeledIntent[ intentList.size() ]);

    openInChooser.putExtra(Intent.EXTRA_INITIAL_INTENTS, extraIntents);
    startActivity(openInChooser);       
}

Я нашел кое-что о том, как сделать это в разных местах, но я не видел всего этого в одном месте где-либо еще.

Обратите внимание, что этот метод также скрывает все глупые варианты, которые я не хочу, например, обмен через Wi-Fi и Bluetooth.

Надеюсь, это кому-нибудь поможет.

Изменить: в комментарии меня попросили объяснить, что делает этот код. По сути, он создает ACTION_SENDнамерение ТОЛЬКО для нативного почтового клиента, а затем связывает другие намерения с выбором. Создание оригинального намерения, специфичного для электронной почты, избавляет от всего лишнего мусора, такого как Wi-Fi и Bluetooth, затем я беру другие намерения, которые я хочу, от общего ACTION_SENDтипа обычного текста, и прикрепляю их перед показом выбора.

Когда я беру дополнительные намерения, я устанавливаю собственный текст для каждого.

Edit2: прошло много времени с тех пор, как я опубликовал это, и все немного изменилось. Если вы видите gmail дважды в списке параметров, попробуйте удалить специальную обработку для «android.gm», как это предлагается в комментарии @h_k ниже.

Поскольку этот один ответ является источником почти всех очков репутации стека переполнения, я должен, по крайней мере, постараться поддерживать его в актуальном состоянии.

dacoinminster
источник
1
Я использую этот код, но каким-то образом evernote пробирается в список. Когда я проверяю имена пакетов, это com.evernote, поэтому я не уверен, почему это происходит.
Джеймс Харп
1
@ user2249287 Я бы посоветовал вам пройтись по коду, пока не увидите пропущенное приложение для обмена сообщениями, а затем посмотрите имя пакета, чтобы определить, какую строку необходимо добавить в белый список, чтобы появилось это приложение.
dacoinminster
1
@ Гилбоу Привет! Извините, я давно не смотрел этот код. , , Насколько я помню, команда setPackage выбирает единственное намерение, к которому вы добавите все остальное. Чтобы включить или исключить различные другие намерения, я рекомендую пройтись по коду и посмотреть на названия пакетов.
dacoinminster
2
Чтобы отфильтровать ТОЛЬКО почтовые приложения, которые есть у пользователя, вы можете использовать второй ответ на этот вопрос: stackoverflow.com/questions/8701634/send-email-intent . Это не требует использования типа данных message / rfc822, который также используют другие приложения, такие как EverNote в этом случае.
mpellegr
2
@dacoinminster Ваш код был великолепен тем, что позволил мне определять различный текст для таких приложений, как Twitter и Whatsapp. Чтобы удалить дубликат gmail, я просто вынул «android.gm» из уравнения. Я все еще получаю gmail и встроенное почтовое приложение в списке выбора, а тема и текст остаются нетронутыми.
h_k
26

Если вам нужна настраиваемая опция, вам не следует полагаться на диалоговое окно по умолчанию, предоставляемое android для этого действия.

Вместо этого вам нужно развернуть свое собственное. Вам нужно будет запросить PackageManager в каких пакетах обрабатывается действие, а затем на основе ответа вы примените фильтрацию и настроенный текст.

В частности, обратите внимание на метод queryIntentActivities в PackageManager класса. Вы строите намерение, которое запускает диалоговое окно по умолчанию (намерение ACTION_SEND), передаете его этому методу, и вы получите список объектов, которые содержат информацию о действиях, которые могут обработать это намерение. Используя это, вы можете выбрать те, которые вы хотите.

После того, как вы создадите свой список пакетов, которые вы хотите представить, вам нужно создать свой собственный диалог со списком (желательно с темой диалога), который будет отображать этот список.

Однако следует отметить, что сделать этот пользовательский диалог очень похожим на диалог по умолчанию. Проблема в том, что тема, используемая в этом диалоговом окне, является внутренней темой и не может использоваться вашим приложением. Вы можете либо попытаться сделать его максимально похожим на нативный, либо перейти на совершенно другой внешний вид (многие приложения делают это, например, приложение галереи и т. Д.)

Саввас Далкицис
источник
1
Пометка этого ответа правильная, так как он наиболее точно отвечает на первоначальный вопрос, хотя в итоге я пошел другим путем (см. Мой ответ). Спасибо.
Кайл Клегг
22

Попробуйте этот, чтобы поделиться только тремя приложениями - Facebook, Twitter, KakaoStory.

public void onShareClick(View v){
    List<Intent> targetShareIntents=new ArrayList<Intent>();
    Intent shareIntent=new Intent();
    shareIntent.setAction(Intent.ACTION_SEND);
    shareIntent.setType("text/plain");
    List<ResolveInfo> resInfos=getPackageManager().queryIntentActivities(shareIntent, 0);
    if(!resInfos.isEmpty()){
        System.out.println("Have package");
        for(ResolveInfo resInfo : resInfos){
            String packageName=resInfo.activityInfo.packageName;
            Log.i("Package Name", packageName);
            if(packageName.contains("com.twitter.android") || packageName.contains("com.facebook.katana") || packageName.contains("com.kakao.story")){
                Intent intent=new Intent();
                intent.setComponent(new ComponentName(packageName, resInfo.activityInfo.name));
                intent.setAction(Intent.ACTION_SEND);
                intent.setType("text/plain");
                intent.putExtra(Intent.EXTRA_TEXT, "Text");
                intent.putExtra(Intent.EXTRA_SUBJECT, "Subject");
                intent.setPackage(packageName);
                targetShareIntents.add(intent);
            }
        }
        if(!targetShareIntents.isEmpty()){
            System.out.println("Have Intent");
            Intent chooserIntent=Intent.createChooser(targetShareIntents.remove(0), "Choose app to share");
            chooserIntent.putExtra(Intent.EXTRA_INITIAL_INTENTS, targetShareIntents.toArray(new Parcelable[]{}));
            startActivity(chooserIntent);
        }else{
            System.out.println("Do not Have Intent");
            showDialaog(this);
        }
    }
}
user3098538
источник
этот код отлично работает, если вы пытаетесь поделиться с определенными приложениями
Orcun Sevsay
22

Нашел решение, которое работает для меня, посмотрев здесь (см. Третий комментарий к первому ответу). Этот код ищет действующий клиент Twitter и использует его для публикации твита. Примечание: он не дает вам намерения с различными клиентами Twitter и позволяет вам выбирать.

Поделиться через твиттер:

Intent shareIntent = findTwitterClient(); 
shareIntent.putExtra(Intent.EXTRA_TEXT, "test");
startActivity(Intent.createChooser(shareIntent, "Share"));

Вызов этого метода:

public Intent findTwitterClient() {
    final String[] twitterApps = {
            // package // name - nb installs (thousands)
            "com.twitter.android", // official - 10 000
            "com.twidroid", // twidroid - 5 000
            "com.handmark.tweetcaster", // Tweecaster - 5 000
            "com.thedeck.android" }; // TweetDeck - 5 000 };
    Intent tweetIntent = new Intent();
    tweetIntent.setType("text/plain");
    final PackageManager packageManager = getPackageManager();
    List<ResolveInfo> list = packageManager.queryIntentActivities(
            tweetIntent, PackageManager.MATCH_DEFAULT_ONLY);

    for (int i = 0; i < twitterApps.length; i++) {
        for (ResolveInfo resolveInfo : list) {
            String p = resolveInfo.activityInfo.packageName;
            if (p != null && p.startsWith(twitterApps[i])) {
                tweetIntent.setPackage(p);
                return tweetIntent;
            }
        }
    }

    return null;
}

Facebook будет похож на « com.facebook.katana », хотя вы все еще не можете установить текст сообщения (устарело в июле 2011 г.).

Источник кода: Намерение открыть клиент Twitter на Android

Кайл Клегг
источник
4
Мне не нравится этот ответ, потому что он основан на знании имен пакетов всех приложений Twitter. Для другого способа см. Stackoverflow.com/questions/6827407/…
Эд Бернетт
Я согласен с вами, хотя в ответе, на который вы ссылались, есть похожая проблема. Мне никогда не нравится полагаться на сравнение строк, особенно когда у меня нет контроля или гарантии, что строка не изменится.
Кайл Клегг
11

Благодаря @dacoinminster. Я делаю некоторые изменения в его ответе, включая имена пакетов популярных приложений и сортировку этих приложений.

List<Intent> targetShareIntents = new ArrayList<Intent>();
Intent shareIntent = new Intent();
shareIntent.setAction(Intent.ACTION_SEND);
shareIntent.setType("text/plain");
PackageManager pm = getActivity().getPackageManager();
List<ResolveInfo> resInfos = pm.queryIntentActivities(shareIntent, 0);
if (!resInfos.isEmpty()) {
    System.out.println("Have package");
    for (ResolveInfo resInfo : resInfos) {
        String packageName = resInfo.activityInfo.packageName;
        Log.i("Package Name", packageName);

        if (packageName.contains("com.twitter.android") || packageName.contains("com.facebook.katana")
                || packageName.contains("com.whatsapp") || packageName.contains("com.google.android.apps.plus")
                || packageName.contains("com.google.android.talk") || packageName.contains("com.slack")
                || packageName.contains("com.google.android.gm") || packageName.contains("com.facebook.orca")
                || packageName.contains("com.yahoo.mobile") || packageName.contains("com.skype.raider")
                || packageName.contains("com.android.mms")|| packageName.contains("com.linkedin.android")
                || packageName.contains("com.google.android.apps.messaging")) {
            Intent intent = new Intent();

            intent.setComponent(new ComponentName(packageName, resInfo.activityInfo.name));
            intent.putExtra("AppName", resInfo.loadLabel(pm).toString());
            intent.setAction(Intent.ACTION_SEND);
            intent.setType("text/plain");
            intent.putExtra(Intent.EXTRA_TEXT, "https://website.com/");
            intent.putExtra(Intent.EXTRA_SUBJECT, getString(R.string.share_text));
            intent.setPackage(packageName);
            targetShareIntents.add(intent);
        }
    }
    if (!targetShareIntents.isEmpty()) {
        Collections.sort(targetShareIntents, new Comparator<Intent>() {
            @Override
            public int compare(Intent o1, Intent o2) {
                return o1.getStringExtra("AppName").compareTo(o2.getStringExtra("AppName"));
            }
        });
        Intent chooserIntent = Intent.createChooser(targetShareIntents.remove(0), "Select app to share");
        chooserIntent.putExtra(Intent.EXTRA_INITIAL_INTENTS, targetShareIntents.toArray(new Parcelable[]{}));
        startActivity(chooserIntent);
    } else {
        Toast.makeText(getActivity(), "No app to share.", Toast.LENGTH_LONG).show();
    }
}
Огуз Озджан
источник
9

Вы можете попробовать код ниже, он работает отлично.

Здесь мы делимся некоторыми конкретными приложениями, такими как Facebook, Messenger, Twitter, Google Plus и Gmail.

public void shareIntentSpecificApps() {
        List<Intent> intentShareList = new ArrayList<Intent>();
        Intent shareIntent = new Intent();
        shareIntent.setAction(Intent.ACTION_SEND);
        shareIntent.setType("text/plain");
        List<ResolveInfo> resolveInfoList = getPackageManager().queryIntentActivities(shareIntent, 0);

        for (ResolveInfo resInfo : resolveInfoList) {
            String packageName = resInfo.activityInfo.packageName;
            String name = resInfo.activityInfo.name;
            Log.d(TAG, "Package Name : " + packageName);
            Log.d(TAG, "Name : " + name);

            if (packageName.contains("com.facebook") ||
                    packageName.contains("com.twitter.android") ||
                    packageName.contains("com.google.android.apps.plus") ||
                    packageName.contains("com.google.android.gm")) {

                if (name.contains("com.twitter.android.DMActivity")) {
                    continue;
                }

                Intent intent = new Intent();
                intent.setComponent(new ComponentName(packageName, name));
                intent.setAction(Intent.ACTION_SEND);
                intent.setType("text/plain");
                intent.putExtra(Intent.EXTRA_SUBJECT, "Your Subject");
                intent.putExtra(Intent.EXTRA_TEXT, "Your Content");
                intentShareList.add(intent);
            }
        }

        if (intentShareList.isEmpty()) {
            Toast.makeText(MainActivity.this, "No apps to share !", Toast.LENGTH_SHORT).show();
        } else {
            Intent chooserIntent = Intent.createChooser(intentShareList.remove(0), "Share via");
            chooserIntent.putExtra(Intent.EXTRA_INITIAL_INTENTS, intentShareList.toArray(new Parcelable[]{}));
            startActivity(chooserIntent);
        }
    }
Данг Нгуен
источник
в чем причина "if (name.contains (" com.twitter.android.DMActivity ")) {continue;}?
isJulian00
8

Это решение показывает список приложений в диалоге ListView, который похож на селектор:

Скриншот

Вам решать:

  1. получить список соответствующих пакетов приложений
  2. учитывая имя пакета, вызвать соответствующее намерение

Класс адаптера:

import java.util.List;

import android.content.Context;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageManager.NameNotFoundException;
import android.graphics.drawable.Drawable;
import android.util.TypedValue;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.TextView;

public class ChooserArrayAdapter extends ArrayAdapter<String> {
    PackageManager mPm;
    int mTextViewResourceId;
    List<String> mPackages;

    public ChooserArrayAdapter(Context context, int resource, int textViewResourceId, List<String> packages) {
        super(context, resource, textViewResourceId, packages);
        mPm = context.getPackageManager();
        mTextViewResourceId = textViewResourceId;
        mPackages = packages;
    }

    @Override
    public View getView(int position, View convertView, ViewGroup parent) {
        String pkg = mPackages.get(position);
        View view = super.getView(position, convertView, parent);

        try {
            ApplicationInfo ai = mPm.getApplicationInfo(pkg, 0);

            CharSequence appName = mPm.getApplicationLabel(ai);
            Drawable appIcon = mPm.getApplicationIcon(pkg);

            TextView textView = (TextView) view.findViewById(mTextViewResourceId);
            textView.setText(appName);
            textView.setCompoundDrawablesWithIntrinsicBounds(appIcon, null, null, null);
            textView.setCompoundDrawablePadding((int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 12, getContext().getResources().getDisplayMetrics()));
        } catch (NameNotFoundException e) {
            e.printStackTrace();
        }

        return view;
    }

}

и его использование:

    void doXxxButton() {
        final List<String> packages = ...;
        if (packages.size() > 1) {
            ArrayAdapter<String> adapter = new ChooserArrayAdapter(MyActivity.this, android.R.layout.select_dialog_item, android.R.id.text1, packages);

            new AlertDialog.Builder(MyActivity.this)
            .setTitle(R.string.app_list_title)
            .setAdapter(adapter, new DialogInterface.OnClickListener() {
                public void onClick(DialogInterface dialog, int item ) {
                    invokeApplication(packages.get(item));
                }
            })
            .show();
        } else if (packages.size() == 1) {
            invokeApplication(packages.get(0));
        }
    }

    void invokeApplication(String packageName) {
        // given a package name, create an intent and fill it with data
        ...
        startActivityForResult(intent, rq);
    }
18446744073709551615
источник
4

Самый простой способ - скопировать следующие классы: ShareActionProvider, ActivityChooserView, ActivityChooserModel. Добавьте возможность фильтрации намерений в ActivityChooserModel и соответствующие методы поддержки в ShareActionProvider. Я создал необходимые классы, вы можете скопировать их в свой проект ( https://gist.github.com/saulpower/10557956 ). Это не только добавляет возможность фильтровать приложения, которыми вы хотели бы поделиться (если вы знаете имя пакета), но и отключать историю.

private final String[] INTENT_FILTER = new String[] {
    "com.twitter.android",
    "com.facebook.katana"
};

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    MenuInflater inflater = getMenuInflater();
    inflater.inflate(R.menu.journal_entry_menu, menu);

    // Set up ShareActionProvider's default share intent
    MenuItem shareItem = menu.findItem(R.id.action_share);

    if (shareItem instanceof SupportMenuItem) {
        mShareActionProvider = new ShareActionProvider(this);
        mShareActionProvider.setShareIntent(ShareUtils.share(mJournalEntry));
        mShareActionProvider.setIntentFilter(Arrays.asList(INTENT_FILTER));
        mShareActionProvider.setShowHistory(false);
        ((SupportMenuItem) shareItem).setSupportActionProvider(mShareActionProvider);
    }

    return super.onCreateOptionsMenu(menu);
}
saulpower
источник
как добавить Google + и другие опции, которые содержат остальные приложения
Sunishtha Singh
3

Я улучшил ответ @dacoinminster, и вот результат с примером, чтобы поделиться вашим приложением:

// Intents with SEND action
PackageManager packageManager = context.getPackageManager();
Intent sendIntent = new Intent(Intent.ACTION_SEND);
sendIntent.setType("text/plain");
List<ResolveInfo> resolveInfoList = packageManager.queryIntentActivities(sendIntent, 0);

List<LabeledIntent> intentList = new ArrayList<LabeledIntent>();
Resources resources = context.getResources();

for (int j = 0; j < resolveInfoList.size(); j++) {
    ResolveInfo resolveInfo = resolveInfoList.get(j);
    String packageName = resolveInfo.activityInfo.packageName;
    Intent intent = new Intent();
    intent.setAction(Intent.ACTION_SEND);
    intent.setComponent(new ComponentName(packageName,
    resolveInfo.activityInfo.name));
    intent.setType("text/plain");

    if (packageName.contains("twitter")) {
        intent.putExtra(Intent.EXTRA_TEXT, resources.getString(R.string.twitter) + "https://play.google.com/store/apps/details?id=" + context.getPackageName());
    } else {
        // skip android mail and gmail to avoid adding to the list twice
        if (packageName.contains("android.email") || packageName.contains("android.gm")) {
            continue;
        }
        intent.putExtra(Intent.EXTRA_TEXT, resources.getString(R.string.largeTextForFacebookWhatsapp) + "https://play.google.com/store/apps/details?id=" + context.getPackageName());
    }

    intentList.add(new LabeledIntent(intent, packageName, resolveInfo.loadLabel(packageManager), resolveInfo.icon));
}

Intent emailIntent = new Intent(Intent.ACTION_SENDTO, Uri.parse("mailto:"));
emailIntent.putExtra(Intent.EXTRA_SUBJECT, resources.getString(R.string.subjectForMailApps));
emailIntent.putExtra(Intent.EXTRA_TEXT, resources.getString(R.string.largeTextForMailApps) + "https://play.google.com/store/apps/details?id=" + context.getPackageName());

context.startActivity(Intent.createChooser(emailIntent, resources.getString(R.string.compartirEn)).putExtra(Intent.EXTRA_INITIAL_INTENTS, intentList.toArray(new LabeledIntent[intentList.size()])));

источник
3

У меня была та же проблема, и это принятое решение не помогло мне, если у кого-то есть такая же проблема, вы можете использовать мой фрагмент кода:

// example of filtering and sharing multiple images with texts
// remove facebook from sharing intents
private void shareFilter(){

    String share = getShareTexts();
    ArrayList<Uri> uris = getImageUris();

    List<Intent> targets = new ArrayList<>();
    Intent template = new Intent(Intent.ACTION_SEND_MULTIPLE);
    template.setType("image/*");
    List<ResolveInfo> candidates = getActivity().getPackageManager().
            queryIntentActivities(template, 0);

    // remove facebook which has a broken share intent
    for (ResolveInfo candidate : candidates) {
        String packageName = candidate.activityInfo.packageName;
        if (!packageName.equals("com.facebook.katana")) {
            Intent target = new Intent(Intent.ACTION_SEND_MULTIPLE);
            target.setType("image/*");
            target.putParcelableArrayListExtra(Intent.EXTRA_STREAM,uris);
            target.putExtra(Intent.EXTRA_TEXT, share);
            target.setPackage(packageName);
            targets.add(target);
        }
    }
    Intent chooser = Intent.createChooser(targets.remove(0), "Share Via");
    chooser.putExtra(Intent.EXTRA_INITIAL_INTENTS, targets.toArray(new Parcelable[targets.size()]));
    startActivity(chooser);

}
Джемо Мгебришвили
источник
3
Intent emailIntent = new Intent(Intent.ACTION_SENDTO, 
    Uri.fromParts("mailto", "android@gmail.com", null));
emailIntent.putExtra(Intent.EXTRA_SUBJECT, text);
startActivity(Intent.createChooser(emailIntent, "Send email..."));
Муруган
источник
0

Так просто и лаконично. Спасибо разработчику открытого исходного кода, cketti за то, что поделились этим решением:

String mailto = "mailto:bob@example.org" +
    "?cc=" + "alice@example.com" +
    "&subject=" + Uri.encode(subject) +
    "&body=" + Uri.encode(bodyText);

Intent emailIntent = new Intent(Intent.ACTION_SENDTO);
emailIntent.setData(Uri.parse(mailto));

try {
  startActivity(emailIntent);
} catch (ActivityNotFoundException e) {
  //TODO: Handle case where no email app is available
}

И это ссылка на его / ее суть.

user10496632
источник