Launching my app using the intent URI
Asked Answered
C

2

7

I know this has been asked a lot of times in StackOverflow already, but I haven't quite found a solution yet. My app sends an email with a link in it that when clicked should launch the app.

According to @hackbod, the best way to do it is to make use of the Intent URI (see this). Here's my code that sets the intent and puts it in the email body:

Intent customIntent = new Intent(CUSTOM_ACTION);
customIntent.setPackage(MY_PACKAGE);
customIntent.addCategory(MY_CAT_BROWSABLE);
customIntent.addCategory(MY_CAT_DEFAULT);

String customUri = customIntent.toUri(Intent.URI_INTENT_SCHEME);

String emailBody = getString(R.string.intent_link, customUri);

Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("text/html");
intent.putExtra(Intent.EXTRA_SUBJECT, "Recommending vid");
intent.putExtra(Intent.EXTRA_TEXT   , Html.fromHtml(emailBody));
try {
    startActivity(Intent.createChooser(intent, "Choose email client:"));
} catch (android.content.ActivityNotFoundException ex) {
    Toast.makeText(this, "There are no email clients installed.", Toast.LENGTH_SHORT).show();
}

This is what I get from LogCat:

08-25 17:01:23.333: VERBOSE/Test URI(16987): intent:#Intent;action=com.test.project.action.VIEW_VID_FROM_LINK;category=android.intent.category.DEFAULT;category=android.intent.category.BROWSABLE;package=com.test.project;end
08-25 17:01:23.338: VERBOSE/Test email text(16987): Hi,<br><br>Testing intents from an email.<br><br> A standard website: <a href=http://www.google.com>Go to Google</a>.<br><br> This link should launch the app: <a href=intent:#Intent;action=com.test.project.action.VIEW_VID_FROM_LINK;category=android.intent.category.DEFAULT;category=android.intent.category.BROWSABLE;package=com.test.project;end>Click link to launch</a>.

When I view the email from my phone using the GMail app, I can click on the Google link and it launches the browser, no problem with that.

But the link for the intent is not even clickable (While from the draft it looks like it should be clickable). Has anybody tried this and made it work?

From draft: link looks clickableSent email: link not clickable

EDIT #1: I have also tried setting the action to Intent.ACTION_VIEW but the link is still not clickable.

EDIT #2: Apparently, the link really is clickable. I tried using another email client, and the links are clickable! Seems like there is a bug in GMail. Oh well. But apparently, this is harder than I thought. I tried using:

Uri.Builder builder = new Uri.Builder();
builder.scheme("my.own.scheme");
builder.authority("my.authority");
Uri newUri = builder.build();
Intent customIntent = new Intent(CUSTOM_ACTION, newUri);

As suggested by @CommonsWare, I tried checking if there are receivers of this customIntent. Apparently there is one, which is what I was expecting. So next step is to make this intent into a URI that I can use in the email. I used:

String customUri = customIntent.toUri(Intent.URI_INTENT_SCHEME);

which, based on my understanding of the documentation, should give me something like the usual http links, only with the scheme set to intent. I can then use this customUri as the value for the links in the email. BUT, it looks like this is not the case. Does anybody have an example of what .toUri must return?

Continuity answered 25/8, 2010 at 9:20 Comment(4)
This is getting long, but I think I found the problem. This is the Intent I want the link to spawn: Intent { act=com.test.project.action.CUSTOM_ACTION dat=com.test.project://my.authority }. Instead, I am getting this Intent when I click on the link in the email: Intent { act=android.intent.action.VIEW dat=intent://my.authority#Intent;scheme=com.test.project;action=com.test.project.action.CUSTOM_ACTION;end (has extras) }. Based on the Intent.parseUri(String uri, int flags) documentation, the email client is interpreting my URI as NOT generated by toUri(). Is my assumption correct?Continuity
were you able to get this to work and what was the solution? Thanks!Senghor
@Senghor I haven't tried this again in a long time. You can look at the comments between me and CommonsWare below to look at my findings during investigation. You can also try out the newer answer below (haven't tried it yet). :)Continuity
Yes, I just tried the suggestions and none seem to work. I'm beginning to think intent: scheme is not supported by the android browser. I can actually start the activity from the command line via adb shell am start "intent:#Intent;action=...."Senghor
A
4

You could try quotes around your URLs in your <a> elements, since that is how HTML is supposed to be written.

You might also try confirming, via parseUri(), PackageManager, and queryIntentActivities(), if your generated URL resolves to something -- if it does not, then there is a problem with the URL.

Here is a sample project showing the use of URI_INTENT_SCHEME, in case it gives you any ideas.

Admass answered 25/8, 2010 at 9:50 Comment(8)
I have quotes in the <a href>s, though they seem to be not showing in LogCat. Here's the viewsource of the email: Content-Type: text/html; charset=ISO-8859-1 <p>Hi,</p> <p>Testing intents from an email.</p> <p>A standard website: <a href="google.com">Go to Google</a>.</p> <p>This link should launch the app: <a href="intent:#Intent;action=android.intent.action.VIEW;category=android.intent.category.DEFAULT;category=android.intent.category.BROWSABLE;package=com.test.project;end">Click link to launch</a>.</p>Continuity
(whooops, something wrong with the formatting up there). Will check out your link for the URL handler, thanks! But I think I will face that hurdle once I get the link to be clickable. Will also try validating the URL, will let you know. :) Thanks as always! :)Continuity
@Zarah: My point is that the link might not be clickable if Android can't find anything to handle the click.Admass
@CommonsWare: I tried switching the email app I use to check my mail, instead of using the GMail app, I tried using the built-in app in the phone. The link is clickable, after all. But you are right, looks like the OS does not know which activity/package to handle the click. I am getting the Web page not available screen.Continuity
These are my findings on this, maybe I am doing something wrong or missing something, I don't know what. I tried checking the intent if there are receivers before doing .toUri. The OS finds the intent receiver so I proceed to put it in the email body. However, when I click on the link in the email, I am still getting the webpage not available screen. Seems contradictory to me. Would you have any idea why?Continuity
@CommonsWare: I compared the intent sent by linking to a regular webpage to the intent sent by my app. My app sends this intent: intent:#Intent;action=com.test.project.action.CUSTOM_ACTION. It looks like it's missing the //<host> after the scheme (intent:). I think that is why in <a href> i am seeing the same string (a href=intent:#Intent;action=com.test.project.action.CUSTOM_ACTION;end). So I think nnow my question is, how can I set the host programatically? Thank you so much!Continuity
@Zarach: AFAIK, you should not need a host. The sample project I linked to does not have a host, and the URL works when viewed in the Browser app. My guess is that when the email clients are parsing out the URL, they are slightly mangling it along the way. I do not know what you can do about that. If the link works when clicked on in the Browser, but does not work when clicked on in email clients, my suspicion is that the problem lies in the email clients.Admass
@CommonsWare: That's what I think so to. I looked at the source code of toUri() and it looks like I am getting the correct string after all. When the email clients parse the link, however, they do not do use the correct flag for the parsing method (parseUri(String, int)), w/c accdg to the API should be set to URI_INTENT_SCHEME. I also opened the email using the phone's browser, and I think it doesn't recognize schemes other than http or https, hence there is no link.Continuity
B
3

Use zero flag to create URI with your custom scheme. Intent.URI_INTENT_SCHEME flag forces "intent:" scheme (and overall intent URI crazy syntax) to be used.

String customUri = customIntent.toUri(0);
Baseler answered 6/6, 2011 at 17:45 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.