我的Android手机的外部存储空间中有一个文件(在这种情况下是模拟的)。知道它的路径和/或有一个File
对象代表它,我如何使用Intent
在相应的应用程序中打开它?
我尝试的第一件事是:
startActivity(new Intent(Intent.ACTION_VIEW, Uri.fromFile(file)));
我确定这在某一点上有效,因为我测试了它并转移到应用程序的另一部分。现在它总是抛出ActivityNotFoundException
。该文件肯定存在,因为file.exists()
返回true
并且我知道它是正确的文件,但没有应用程序自愿打开它。
我仍然可以通过这种方式打开的唯一类型的文件是.pdf,其中选择了Adobe Reader,尽管它不是我设备上安装的唯一PDF阅读器,并且没有设置为默认值。我注意到Adobe Reader还提供了打开在线的pdf文件(它似乎是用Chrome下载pdf的替代方案)。这告诉我,只有Adobe Reader被认为是Intent
的匹配项,因为该位置被认为是远程的(虽然不在线,因为Chrome和其他文件下载应用程序不作为替代品列出)
我还尝试明确说明MIME类型:
Intent intent = new Intent(Intent.ACTION_VIEW);
intent.setDataAndType(Uri.fromFile(file), "application/msword");
startActivity(intent);
这会导致 Intent
与正确的应用匹配,但它们都无法实际打开文件。我已经使用MIME类型的硬编码字符串和使用MimeTypeMap.getSingleton().getMimeTypeFromExtension(extension)
测试了这一点,并传递了文件扩展名。对于各种文件类型,建议使用正确的应用程序,但它们都无法打开文件。
修改
显式设置MIME类型会有效,但我犯了一个非常愚蠢的错误,我应该在答案中解释。
我尝试打开的文件来自互联网,借助 DownloadManager
在我的应用中下载。我使用它的功能在完成下载后显示通知。单击其中一个通知可以完美打开文件。我已经尝试在点击Intent
完成通知时找到DownloadManager
触发的源代码,但没有运气。
此外,ES文件浏览器等应用程序可以导航到我的文件下载到的位置并打开它们没有问题。我做错了什么?
是否只是ACTION_VIEW不再可能在外部存储上的文件?我的应用程序还暂时将文件下载到内部存储器,这些仍然可以打开,没有类似的问题:
//This works for files on internal storage:
Uri uri = FileProvider.getUriForFile(context, AUTHORITY, file);
Intent intent = new Intent(Intent.ACTION_VIEW, uri);
intent.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
startActivity(intent);
至于它过去的工作,可以更新Eclipse,SDK Tools插件和Android SDK本身已经停止了我的原始解决方案吗?
答案 0 :(得分:3)
当我尝试setDataAndType
时,出于懒惰,我必须离开:
Intent intent = new Intent(Intent.ACTION_VIEW, Uri.fromFile(file));
并添加了另一行:
Intent intent = new Intent(Intent.ACTION_VIEW, Uri.fromFile(file));
intent.setType(theMimeType);
...假设它与:
相同Intent intent = new Intent(Intent.ACTION_VIEW);
intent.setDataAndType(Uri.fromFile(file), theMimeType);
我必须忘记我实际上没有尝试setDataAndType
并继续写下这个问题。单独使用setType
似乎删除了Uri
我作为参数传递给构造函数。使用LogCat查看记录的意图详细信息,我看到保留了要推断的MIME类型导致没有类型,在设置setType
之后使用Uri
导致没有Uri
由于某种原因而指定,并且使用setDataAndType
意味着它们都被指定,导致Intent
正常工作。
所以我错误的是分别设置类型和数据,而不是使用setDataAndType
。