【问题标题】:Sharing image and link through Intent for WhatsApp, Telegram, etc通过 Intent 为 WhatsApp、Telegram 等共享图像和链接
【发布时间】:2019-11-19 00:01:44
【问题描述】:

通过在网络上搜索,我发现有不止一种方法可以通过邀请他人下载来分享我的应用程序。

我尝试了这段代码,它向用户显示了应用选择器窗格。

Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("text/plain");
intent.putExtra(Intent.EXTRA_SUBJECT, "My subject");
intent.putExtra(Intent.EXTRA_TITLE, "My subject");
intent.putExtra(Intent.EXTRA_TEXT, "https://play.google.com/store/apps/details?id=" + BuildConfig.APPLICATION_ID);
startActivity(Intent.createChooser(intent, "Share App"));

当用户选择与 WhatsApp、Telegram、SMS、电子邮件等共享消息时,我必须在 Intent 中包含哪些信息才能正确显示消息?

例如,此代码将在 Telegram 中显示预览(带有突出显示的链接和预览图像),但在 WhatsApp 中不显示(它仅显示作为消息发送的纯文本):为什么?

我也试过这段代码,但它适用于电报,但不适用于 Whatsapp(它发送的消息只有一个附件,无法打开文本“无标题”):

Intent shareIntent = new Intent();
shareIntent.setAction(Intent.ACTION_SEND);
shareIntent.putExtra(Intent.EXTRA_TITLE, "title test");
shareIntent.putExtra(Intent.EXTRA_SUBJECT, "subject test");
String shareMessage= "message test\n\n";
shareMessage = shareMessage + "https://play.google.com/store/apps/details?id=" + BuildConfig.APPLICATION_ID +"\n\n";
shareIntent.putExtra(Intent.EXTRA_TEXT, shareMessage);
shareIntent.putExtra(Intent.EXTRA_HTML_TEXT, "HTML " + shareMessage);
Uri imageUri = Uri.parse(ContentResolver.SCHEME_ANDROID_RESOURCE + "://"
        + res.getResourcePackageName(R.drawable.testjpg) + '/'
        + res.getResourceTypeName(R.drawable.testjpg) + '/'
        + res.getResourceEntryName(R.drawable.testjpg));
Toast.makeText(this, imageUri.toString(), Toast.LENGTH_LONG).show();
shareIntent.putExtra(Intent.EXTRA_STREAM, imageUri);
shareIntent.setType("image/jpg");
shareIntent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
startActivity(Intent.createChooser(shareIntent, getString(R.string.share)));

如何使其适用于 WhatsApp、Telegram、FB、电子邮件和其他纯文本(如 SMS)?

【问题讨论】:

  • @ManojPerumarath,没有。我尝试了一些代码,但仍然在whatsapp中没有出现图像...... Whatsapp以一种奇怪的方式处理通过意图的信息......相反,电报正确处理它
  • 这很奇怪,尝试添加赏金,它会到达

标签: android android-intent uri share


【解决方案1】:

当用户选择与 WhatsApp、Telegram、SMS、电子邮件等共享消息时,我必须在 Intent 中包含哪些信息才能正确显示消息?

“正确”的定义取决于其他应用的开发者,而不是您。他们如何处理您的 Intent 上的额外内容取决于他们,而不是您。他们对这些附加功能的处理方式将根据应用程序、应用程序版本以及可能的设备/操作系统特征而有所不同。你无法控制其中的任何一个。您只需提供数据,让其他应用程序的开发人员用它做他们想做的事。

此代码将在 Telegram 中显示预览(带有突出显示的链接和预览图像),但在 WhatsApp 中不显示(它仅显示作为消息发送的纯文本):为什么?

因为这是 Telegram 和 WhatsApp 开发人员选择做的事情。

我也试过这段代码,但它适用于电报,但不适用于 whatsapp

该代码中存在各种错误:

  • 您在EXTRA_HTML_TEXT中提供的不是HTML

  • image/jpg 不是有效的 MIME 类型(它是 image/jpeg

  • 您的Uri 具有android.resource 方案,而不是content 方案

修复这些错误是否会改变 WhatsApp 的行为取决于 WhatsApp 的开发人员,而这一行为可能会在接下来的一个小时内发生七次变化,据您所知。因此,虽然我建议修复这些错误,但不要假设任何给定应用程序的行为必然会有所不同,或者以您想要的某种方式。

【讨论】:

  • 通过从 ContentResolver.SCHEME_ANDROID_RESOURCE 更改为 ContentResolver.SCHEME_CONTENT whatsapp 说“请求失败,重试”,Telegram 什么也不做。相反,使用ContentResolver.SCHEME_ANDROID_RESOURCE,它在 Telegram 中也可以显示图像,而 Whatsapp 不会说错误(但仍然不显示图像)。
  • @user2342558:您不能只更改方案。 Uri 必须是有效的Uri。使用FileProvider
  • 您能否编辑您的答案,提供使用FileProvider 文件R.drawable.testjpg 的代码示例?我尝试了一些代码,但它不起作用。
  • @user2342558: FileProvider 适用于文件,而不是可绘制资源。您需要将可绘制资源的字节复制到某个文件以与FileProvider 一起使用。或者,创建您自己的ContentProvider,以某种方式为您的可绘制资源提供服务。或者,只需从您的第二个代码 sn-p 中删除 EXTRA_STREAM 和 MIME 类型,以避免所有这些麻烦。
  • FileProvider 建议有效,但未显示预览。谢谢。我会尽快发布工作代码。
【解决方案2】:

这是一个可能的答案 -

Intent waIntent = new Intent(Intent.ACTION_SEND);
waIntent.setType("text/plain");
String text = "Sorry For Interruption,I'm Just Trying Something";
waIntent.setPackage("com.whatsapp");

if (waIntent != null) {
    waIntent.putExtra(Intent.EXTRA_TEXT, text);
    waIntent.putExtra(Intent.EXTRA_SUBJECT, "My subject");
    waIntent.putExtra(Intent.EXTRA_TITLE, "My subject");
    waIntent.putExtra(Intent.EXTRA_TEXT, "https://play.google.com/store/apps/details?id=" + BuildConfig.APPLICATION_ID);
    waIntent.putExtra(Intent.EXTRA_STREAM, attachment);
    startActivity(Intent.createChooser(waIntent,"Share with"));

希望这会有所帮助!

来源 - Sending message through WhatsApp By intent

https://developer.android.com/guide/components/intents-common#java

【讨论】:

    【解决方案3】:

    对我来说,以下是使用FileProvider 的工作代码(在装有Android 6.1 的真实设备上测试)。

    通过使用FileProvider,我可以允许其他应用读取我的图像。

    AndroidManifest.xml

    <?xml version="1.0" encoding="utf-8"?>
    <manifest xmlns:android="http://schemas.android.com/apk/res/android"
        package="app.example.com">
        <application
            ...>
            <activity
                ...></activity>
            <provider
                android:name="android.support.v4.content.FileProvider"
                android:authorities="app.example.com"
                android:exported="false"
                android:grantUriPermissions="true"
                android:readPermission="app.example.com.fileprovider.READ">
                <meta-data
                    android:name="android.support.FILE_PROVIDER_PATHS"
                    android:resource="@xml/provider_paths"/>
            </provider>
        </application>
    </manifest>
    

    provider_paths.xml

    <?xml version="1.0" encoding="utf-8"?>
    <paths>
        <external-files-path name="files" path="/" />
    </paths>
    

    Activity.java

    String nomeApp = getString(R.string.app_name);
    String titoloApp = getString(R.string.titolo_app);
    String shareMessage = "Text message\n\n";
    shareMessage = shareMessage + "https://play.google.com/store/apps/details?id=" + BuildConfig.APPLICATION_ID +"\n\n";
    
    // use the dedicated external directory so the App doesn't need to ask for permission in manifest
    File dirSaveFile = getApplicationContext().getExternalFilesDir(Environment.DIRECTORY_PICTURES);
    
    // create needed dirs for file path
    File imagePath = new File(dirSaveFile, "external_files");
    imagePath.mkdir();
    
    // create empty file
    File imageFile = new File(imagePath.getPath(), "test.jpg");
    
    // get the Bitmap of the drawable to show
    final Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(), R.drawable.testjpg);
    
    // write in the file the drawable image
    try {
        FileOutputStream fos = new FileOutputStream(imageFile);
        bitmap.compress(Bitmap.CompressFormat.JPEG, 100, fos);
        fos.flush();
        fos.close();
    } catch (Exception e) {
        e.printStackTrace();
    }
    
    // create the uri
    Uri uri = FileProvider.getUriForFile(this, BuildConfig.APPLICATION_ID, imageFile);
    
    // create the Intent
    Intent shareIntent = new Intent();
    shareIntent.setAction(Intent.ACTION_SEND);
    shareIntent.putExtra(Intent.EXTRA_TITLE, "Title test");
    shareIntent.putExtra(Intent.EXTRA_SUBJECT, "Subject test");
    shareIntent.putExtra(Intent.EXTRA_TEXT, shareMessage);
    shareIntent.putExtra(Intent.EXTRA_STREAM, uri);
    shareIntent.setType("text/plain");
    
    startActivity(Intent.createChooser(shareIntent, getString(R.string.share)));
    

    注意:正如@CommonsWare 在他的回答中所说:

    他们如何处理你 Intent 上的额外内容取决于他们,而不是你。

    因此,此代码将来可能不再有效。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-01-18
      • 1970-01-01
      • 2014-10-04
      • 1970-01-01
      • 2022-06-20
      • 2012-05-05
      相关资源
      最近更新 更多