尝试将SD卡中的文件附加到电子邮件


69

我正在尝试启动一个意图来发送电子邮件。所有这些都有效,但是当我尝试实际发送电子邮件时,会发生一些“奇怪”的事情。

这是代码

Intent sendIntent = new Intent(Intent.ACTION_SEND);
sendIntent.setType("image/jpeg");
sendIntent.putExtra(Intent.EXTRA_SUBJECT, "Photo");
sendIntent.putExtra(Intent.EXTRA_STREAM, Uri.parse("file://sdcard/dcim/Camera/filename.jpg"));
sendIntent.putExtra(Intent.EXTRA_TEXT, "Enjoy the photo");
startActivity(Intent.createChooser(sendIntent, "Email:"));

因此,如果我使用Gmail菜单上下文启动,它将显示附件,让我键入电子邮件的收件人,并编辑正文和主题。没什么大不了的。我点击发送,它发送。唯一的事情是附件不会被发送。

所以。我想到了,为什么不尝试使用电子邮件菜单上下文(对于手机上的备用电子邮件帐户)呢?它显示附件,但在正文或主题中根本没有文本。当我发送邮件时,附件发送正确。那会让我相信有些不对劲。我需要在清单中启动新的许可以启动带有附件的电子邮件发送意图吗?我究竟做错了什么?


1
谢谢Chrispix !,此代码在我的moto cliq中有效。
Jana,

Answers:


96

也遇到同样的问题

码:

Intent emailIntent = new Intent(android.content.Intent.ACTION_SEND); 
    emailIntent.setType("image/jpeg");
    emailIntent.putExtra(android.content.Intent.EXTRA_EMAIL, new String[] 
    {"me@gmail.com"}); 
    emailIntent.putExtra(android.content.Intent.EXTRA_SUBJECT, 
    "Test Subject"); 
    emailIntent.putExtra(android.content.Intent.EXTRA_TEXT, 
    "go on read the emails"); 
    Log.v(getClass().getSimpleName(), "sPhotoUri=" + Uri.parse("file:/"+ sPhotoFileName));
    emailIntent.putExtra(Intent.EXTRA_STREAM, Uri.parse("file:/"+ sPhotoFileName));
    startActivity(Intent.createChooser(emailIntent, "Send mail..."));

从adb logcat:

V/DumbDumpersMain( 3972):   sPhotoUri=file://sdcard/DumbDumpers/DumbDumper.jpg
I/ActivityManager(   56):   Starting activity: Intent { action=android.intent.action.CHOOSER comp={android/com.android.internal.app.ChooserActivity} (has extras) }
I/ActivityManager(   56):   Starting activity: Intent { action=android.intent.action.SEND type=jpeg/image flags=0x3000000 comp={com.google.android.gm/com.google.android.gm.ComposeActivityGmail} (has extras) }
I/ActivityManager(   56):   Starting activity: Intent { action=android.intent.action.SEND type=jpeg/image flags=0x2800000 comp={com.google.android.gm/com.google.android.gm.ComposeActivity} (has extras) }
D/gmail-ls(  120):      MailProvider.query: content://gmail-ls/labels/me@gmail.com(null, null)
D/Gmail   ( 2507):      URI FOUND:file://sdcard/DumbDumpers/DumbDumper.jpg

电子邮件提供商似乎附加了一个长度为0的文件。当我检查文件系统时,文件在那里并正确。创建图像文件的代码在尝试通过电子邮件发送之前已经完成。

任何人都可以解决此问题,而无需重新启动魔术(我已经尝试过了)?

问候,

更新资料

我的道路应该是

file:///sdcard/DumbDumpers/DumbDumper.jpg

您需要额外的内容,/因为它指向根目录,即:

file:// + /sdcard/DumbDumpers/DumbDumper.jpg

合并为

file:///sdcard/DumbDumpers/DumbDumper.jpg

在以上代码段中,您需要:

emailIntent.putExtra(Intent.EXTRA_STREAM, Uri.parse("file://"+ sPhotoFileName));

我希望这有帮助。我花了很长时间调试。

问候,
芬利


6
我赞成,但是如果您对此进行重新设计,它将更好,因此最终的解决方案将被纳入代码中。解决方案比这里的故事更重要。
Patrick O'Leary

3
我更改了答案以反映需要3个斜杠的事实。我也对此投了赞成票。
Chrispix

支持,我不会重做,因为人们实际上应该知道错误在哪里。感谢您的解决方案。
疯狂

upvote,但EXTRA_TEXT在使用Facebook的情况下不起作用,发布后只有图像出现在我的墙上。任何想法我该如何解决。
varun bhardwaj 2012年

您不应使用“硬编码”路径,因为它们可能会因设备而异。因此,我建议您对代码进行一些更改:File filelocation = new File(Environment.getExternalStorageDirectory()。getAbsolutePath(),filename); 然后定义:Uri path = Uri.fromFile(filelocation); 并将其放入您的意图中:emailIntent .putExtra(Intent.EXTRA_STREAM,path);
卡洛斯·波劳

21

我这边只说几句。我在GMail上遇到了同样的问题,但是当我首先将有问题的文件存储在SD卡上并从那里而不是从资产中检索文件时,它似乎可以工作。所以我的代码如下:

Intent i = new Intent(Intent.ACTION_SEND);
i.putExtra(Intent.EXTRA_SUBJECT, "Title");
i.putExtra(Intent.EXTRA_TEXT, "Content");
i.putExtra(Intent.EXTRA_STREAM, uri);
i.setType("text/plain");
startActivity(Intent.createChooser(i, "Send mail"));

和这里,

uri = Uri.fromFile(new File(context.getFilesDir(), FILENAME));

没有工作,而

uri = Uri.fromFile(new File(Environment.getExternalStorageDirectory(), FILENAME));

做。

问候,迈克尔


我发现了同样的事情。我想知道Gmail(或其他邮件程序)读取文件是否存在权限问题?帮助我的一件事是,当我使用内置的“邮件”程序(不是Gmail)时,它表明附件为0字节。很高兴知道问题存在而不必发送和检查我的电子邮件。:-)
泰勒·科利尔

1
我会建议更换startActivity()startActivityForResult()和删除SD卡的根目录下的文件onActivityResult()
Paul Lammertsma 2011年

我认为这不是许可问题。这是Android的问题,已在2.3至4.2之间修正。在2.3上,如果我使内部存储上的文件可读,则其他应用程序可以打开它,但gmail仍然无法附加它。需要在外部存储上。在4.2上,我没有这个问题。
汤姆

7

代替“ Uri.parse”,使用“ Uri.fromFile(new File(Environment.getExternalStorageDirectory(),“ file name”))“

Environment.getExternalStorageDirectory()-SD卡或任何其他外部存储的路径


4

看来这实际上是正确的,不确定发生了什么,但是在重新启动后它开始工作:/


OP的代码有错别字:路径应该是file:///sdcard(注意三个斜杠,而不是两个)。
Paul Lammertsma

4
    Intent i = new Intent(Intent.ACTION_SEND);
    i.setType("message/rfc822");
    i.putExtra(Intent.EXTRA_EMAIL  , new String[]{"example@mail.com"});
    i.putExtra(Intent.EXTRA_SUBJECT, "Data from app");
    i.putExtra(Intent.EXTRA_TEXT   , "experience number x");
    i.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); 

    Uri uri = Uri.fromFile(new File(Environment.getExternalStorageDirectory(), "filename.txt"));
    i.putExtra(Intent.EXTRA_STREAM, uri);
    startActivity(Intent.createChooser(i, "Send email..."));

3

我遇到了同样的问题,到处都在寻找解决方案。最后,我通过找到一个开箱即用的开源应用程序解决了它,并研究了他们是如何做到的。该代码很长,因此在这里我不会引用它,但会发布一个链接。查看第449行的sendEmail函数

http://rehearsalassist.svn.sourceforge.net/viewvc/rehearsalassist/android/trunk/src/urbanstew/RehearsalAssistant/SessionPlayback.java?revision=94&view=markup

我将代码重构为相似的代码,现在可以正常工作了。我希望这会帮助处于相同情况的其他人。


3

RFC 1738第3.10节开始:

文件URL的格式为:

   file://<host>/<path>

其中host是可访问路径的系统的标准域名,而path是格式为directory / directory /.../ name的分层目录路径。

所以它是file:/// path / from / root,就像http:// host / path / from / root一样,因为在第二个和第三个斜杠之间有一个隐式的“ localhost”。但是如上所述,请使用Uri.FromFile()进行构建。


我想要的是大约3的斜线部分。谢谢。
Hoang Tran 2012年

0

我有相同的症状。就我而言,这是因为我最初是使用权限保存附件的MODE_PRIVATE。我将其更改为MODE_WORLD_READABLEGMail之后便可以访问该文件并正确发送附件了。

查看更多



0
public void sendMail(String path) {
        Intent emailIntent = new Intent(android.content.Intent.ACTION_SEND);
        emailIntent.putExtra(android.content.Intent.EXTRA_EMAIL,
        new String[] {AppConstant.server_mail});
        emailIntent.putExtra(android.content.Intent.EXTRA_SUBJECT,
        "IBPS ERROR Mail");
        emailIntent.putExtra(android.content.Intent.EXTRA_TEXT,
        "This is an autogenerated mail from IBPS app");
        emailIntent.setType("image/png");
        Uri myUri = Uri.parse("file://" + path);
        emailIntent.putExtra(Intent.EXTRA_STREAM, myUri);
        startActivity(Intent.createChooser(emailIntent, "Send mail..."));
        }

0

也尝试添加Intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); 这有助于解决我的问题。


0

4天后我已经解决了这个问题,请在提供指向Android(Java)中File类的路径时注意以下几点:

1)使用内部存储路径String path =“ / storage / sdcard0 / myfile.txt”;

2)path =“ / storage / sdcard1 / myfile.txt”;

3)在清单文件中提及权限。

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />

4)首先检查文件长度以进行确认。

5)检查ES File Explorer中有关sdcard0和sdcard1的路径是否相同...

例如

File file=new File(path); 
long=file.length();//in Bytes

0

发送带有附件的电子邮件:(按文档)

Intent emailIntent =新的Intent(Intent.ACTION_SEND);emailIntent.setType(HTTP.PLAIN_TEXT_TYPE);

emailIntent.putExtra(Intent.EXTRA_EMAIL,新的String [] {“ jon@example.com”});

emailIntent.putExtra(Intent.EXTRA_SUBJECT,“电子邮件主题”);emailIntent.putExtra(Intent.EXTRA_TEXT,“电子邮件文本”); emailIntent.putExtra(Intent.EXTRA_STREAM,Uri.parse(“ content:// path / to / email / attachment”));

//您还可以通过传递Uris的ArrayList附加多个项目

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.