How to export an activity so other apps can call it? - android

Well I searched a lot, but I didn't find a precise answer how to export an Activity, so an app can start it with startActivityforResult.
How do I achieve that? Do I have to change the Manifest in some ways?

As an alternate to Dalmas' answer, you can actually export an Activity without creating an <intent-filter> (along with the hassle of coming up with a custom action).
In the Manifest edit your Activity tag like so:
<activity
android:name=".SomeActivity"
....
android:exported="true" />
The important part is android:exported="true", this export tag determines "whether or not the activity can be launched by components of other applications". If your <activity> contains an <intent-filter> then this tag is set to true automatically, if it does not then it is set to false by default.
Then to launch the Activity do this:
Intent i = new Intent();
i.setComponent(new ComponentName("package name", "fully-qualified name of activity"));
startActivity(i);
Of course with this method you will need to know the exact name of the Activity you are trying to launch.

You need to declare an intent-filter in your Manifest (I took the following example from Barcode Scanner) :
<activity android:name="...">
<intent-filter>
<action android:name="com.google.zxing.client.android.SCAN" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
Then create an intent with the same action string :
Intent intent = new Intent("com.google.zxing.client.android.SCAN");
startActivityForResult(intent, code);
Android should start your activity (or it will show a drop-down box if there are multiple apps sharing the same action string).

Related

specifying a different home activity at run-time

To specify my "Home" activity at compile-time, I can use the following code in my AndroidManifest.
<activity
android:name=".HomeActivity"
<intent-filter android:label="#string/home_activity">
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.HOME" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
I have a requirement though where I need to be able to specify the activity I would like to use as my "Home" screen at "run-time". Does anyone know if this is possible? Basically, I want to replace "HomeActivity" with something else.
I looked into using an "activity-alias" where I can specify the target activity using the "targetActivity" attribute but I didn't quite get how I can use this.
Thanks!
#Jon you can conditionally call separate activity from splash.Like you have a condition that on first app launch you need to open a tutorial screen and then onwards your home Activity then you can create different intents.
if (!sharedPreferences.contains(DiceConstants.FIRST_TIME_PREFS)) {
intent = new Intent(this, TutorialActivity.class);
sharedPreferences.edit().putBoolean(DiceConstants.FIRST_TIME_PREFS, true).commit();
} else {
intent = new Intent(this, HomeActivity.class);
}

startActivity using android:name

Manifest definition:
<activity android:name="com.gannett.democratandchronicle.billstrainingcamp.PlayersActivity" />
WORKS:
startActivity(new Intent(this, PlayersActivity.class));
DOESN'T WORK: (No activity found)
startActivity(new Intent("com.gannett.democratandchronicle.billstrainingcamp.PlayersActivity"));
Why can't I use the full android:name to startActivity? Is the string parameter expecting something different?
It is an action, not a name. If you want to be able to launch your activity that way, add
<intent-filter>
<action android:name="com.gannett.democratandchronicle.billstrainingcamp.PlayersActivity" />
</intent-filter>
to your activity, or you can use any name you want for the action, it does not have to be the name of the class. It does, however, have to have a namespace.

How to start another Activity when you have the Activity name String but not the Activity.Class?

I'm running into a problem starting other activities from mine. I know this must be being done elsewhere as there are so many launcher apps out there which much use package manager to start specific activities...
I can get an Acitivity name I would like to start from the package manager, but how can I somehow parse this and turn it into an intent? Baring in mind I can't access the class... Also I would like to start that specific activity and not launch the MAIN intent from the package...
I'm sure someone must be doing this somewhere... It's kind of the point in activities isn't it?
Assuming you have following in your AndroidManifest.xml
<!-- The askUser dialog activity -->
<activity android:theme="#android:style/Theme.Dialog"
android:name="my.app.AskUserActivity"
android:excludeFromRecents="true"
android:screenOrientation="portrait">
<intent-filter>
<action android:name="my.app.intents.AskUserConfirmConnect"/>
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
</activity>
Then you can call this Activity by name, like this:
Intent dlgIntent = null;
dlgIntent = new Intent("my.app.intents.AskUserConfirmConnect");
dlgIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
dlgIntent.addFlags(Intent.FLAG_ACTIVITY_MULTIPLE_TASK);
context.startActivity(dlgIntent);
You can use setClassName(String, String) on the Intent to avoid needing the other class.

Start Activity with action, but no category

I am trying to start an activity defined in another apk, in its AndroidManifest.xml, it defines an activity and with an action, but no category defined.
The format is like
<activity name="...">
<intent-filter>
<action android:name="action name">
<intent-filter>
</activity>
My code is following
Intent i = new Intent("action name");
startActivity(i);
However my apk crashed with uncaught ActivityNotFound exception, the logs read
No Activity found to handle intent ... "
Any thoughts?
Thanx a lot.
Looking at the Intent documentation, it says Note also the DEFAULT category supplied here: this is required for the Context.startActivity method to resolve your activity when its component name is not explicitly specified. If the activity's IntentFilter definition does not include that category then you can't start it with startActivity. Try using the setClassName method, and pass it the package class and the activity class you're trying to launch.
you cannot have empty category when you use startActivity(...).
add a default category and this will do the job:
<intent-filter>
<action android:name="action name" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
You need to define the activity you are starting in your Manifest. Make sure you have provided same <intent-action (and name of the activity) that has the activity in the other apk you want to start.
android: how do i open another app from my app?

android check if an activity was started from an action or from another activity?

In my manifest file, I have an activity declaration which looks something like this:
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
This activity is obviously launched on application start. User can navigate from this activity to another activity and from that one to another etc.
In another activity, I start MainActivity by using 'startActivity' method, ie. something like:
Intent intent = new Intent(AnotherActivity.this, MainActivity.class);
startActivity(intent);
In my MainActivity (in onCreate() method maybe), can I determine whether an activity was started from a action of from another activity? Is there something like "launcher listener"? I would like to avoid putting any extra content in the intent.
Can I simply put String s = getIntent().getAction(); in onCreate method and check whether it is has a value of MAIN?
Well the stock android launcher does send Intent.ACTION_MAIN as as the action. However, you can't be sure that some other launcher will have the same behaviour. Your best bet will be to pass some extra data with the Intent.

Categories

Resources