However, the Android system is based upon lots of loosely-coupled components. What you might accomplish in a desktop GUI via dialog boxes, child windows, and the like are mostly supposed to be independent activities. While one activity will be “special”, in that it shows up in the launcher, the other activities all need to be reached . . . somehow.
The “how” is via intents.
What is Intent
Intent
object, is a passive data structure holding an abstract description of an operation to be performed. From official doc page, Intent is an abstract description of an operation to be performed. It can be used with startActivity()
to launch an Activity
, broadcastIntent()
to send it to any interested BroadcastReceiver
components, and startService(Intent)
or bindService(Intent, ServiceConnection, int)
to communicate with a background Service
.Parts of Intents
Intent
is "action" and "data". These are almost exactly analogous to HTTP verbs and URLs - the action is the verb, and the “data” is a Uri
, such as content://contact/people/1
representing a contact in the contacts database in your device. Actions are constants, such as ACTION_VIEW
(to bring up a viewer for the resource), ACTION_EDIT
(to edit the resource), or ACTION_PICK
(to choose an available item given a Uri
representing a collection, such as content://contact/people
).If you were to create an intent combining
ACTION_VIEW
with a content Uri
of content://contact/people/1
, and pass that intent to Android, system would know to find and open an activity capable of viewing that resource.There are other criteria you can place inside an intent (represented as an
Intent
object), besides the action and “data” Uri
, such as:- A category. Your “main” activity will be in the
LAUNCHER
category, indicating it should show up on the launcher menu. Other activities will probably be in theDEFAULT
orALTERNATIVE
categories. - A MIME type, indicating the type of resource you want to operate on, if you don’t know a collection
Uri
. - A component, which is to say, the class of the activity that is supposed to receive this intent. Using components this way obviates the need for the other properties of the intent. However, it does make the intent more fragile, as it assumes specific implementations.
- “Extras”, which is a
Bundle
of other information you want to pass along to the receiver with the intent, that the receiver might want to take advantage of. What pieces of information a given receiver can use is up to the receiver and (hopefully) is well-documented.
Intent Routing
- The activity must support the specified action.
- The activity must support the stated MIME type (if supplied).
- The activity must support all of the categories named in the intent.
Starting an Intent
intent-filter
elements to your AndroidManifest.xml
file. For example:
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="info.devexchanges.example">
<application>
<activity
android:name=".MainActivity"
android:label="@string/app_name">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
Note the intent-filter element under the activity element:- This is the main activity for this application.
- This is in the LAUNCHER category, meaning it gets an icon in the Android main menu.
You are welcome to have more than one action or more than one category in your intent filters. That indicates that the associated component (e.g., activity) handles multiple different sorts of intents.
More than likely, you will also want to have your secondary (non-MAIN) activities specify the MIME type of data they work on. Then, if an intent is targeted for that MIME type - either directly, or indirectly by the
Uri
referencing something of that type - Android will know that the component handles such data. For example:
<activity android:name=".TourActivity">
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<data android:mimeType="vnd.android.cursor.item" />
</intent-filter>
</activity>
This activity will get launched by an intent requesting to view a Uri
representing a vnd.android.cursor.item
piece of content. That intent could come from another activity in the same application (e.g., the MAIN activity for this application) or from another activity in another Android application that happens to know a Uri
that this activity handles.Narrow Receivers
- Some system events might cause us to want to trigger something in a service rather than an activity.
- Some events might need to launch different activities in different circumstances, where the criteria are not solely based on the intent itself, but some other state (e.g., if we get intent X and the database has a Y, then launch activity A; if the database does not have a Y, then launch activity B).
BroadcastReceiver
interface. Intent receivers are disposable objects designed to receive intents - particularly broadcast intents - and take action, typically involving launching other intents to trigger logic in an activity, service, or other component.The
BroadcastReceiver
interface has only one method: onReceive()
. Intent receivers implement that method, where they do whatever it is they wish to do upon an incoming intent. To declare an intent receiver, add a receiver element to your AndroidManifest.xml
file:
An intent receiver is only alive for as long as it takes to process onReceive()
— as soon as that method returns, the receiver instance is subject to garbage collection and will not be reused. This means intent receivers are somewhat limited in what they can do, mostly to avoid anything that involves any sort of callback. For example, they cannot bind to a service, and they cannot open a dialog box.The exception is if the
BroadcastReceiver
is implemented on some longer-lived component, such as an activity or service - in that case, the intent receiver lives as long as its “host” does (e.g., until the activity is stop). However, in this case, you cannot declare the intent receiver via AndroidManifest.xml
. Instead, you need to call registerReceiver()
on your Activity’s onResume()
callback to declare interest in an intent, then call unRegisterReceiver()
from your Activity’s onPause()
when you no longer need those intents.Conclusions
Intent
object. Hope this helpful for readers!