News:
- In an internet driven environment, it is imperative for a company to keep its product or business to the forefront of potential customers' minds. The ...
- A successful enterprise is all about constantly reinventing ways to work more efficiently. In today’s techno age, this translates to testing new too...
- The IT industry plays a pivotal role in providing application development solutions and custom software development to a wide range of industries, i...
- Royal Victorian Eye and Ear Hospital, 2010 Atcomm has been contracted to implement a complex IOP glaucoma management tool which will be distribut...
- We are pleased to announce another implementation of a CMS system for a large Melbourne based fitness center - Star Plate Studio. Atcomm has depl...
Wednesday, 28 July 2010 23:32
Examining the Application Lifecycle
-
font size
decrease font size
increase font size
The lifecycle of Android applications differs greatly from the lifecycle of web-based J2EE applications. J2EE apps are loosely managed by the container they run in. For example, a J2EE container can remove an application from memory if it sits idle for a predetermined time period. But the container generally won’t move applications in and out of memory based on load and/or available resources. In other words, it’s up to the application owners to ensure that resources are available.
The lifecycle of an Android application, on the other hand, is strictly managed by the system, based on the user’s needs, available resources, and so on. A user might want to launch a web browser, for example, but the system ultimately decides whether to start the application.Although the system is the ultimate manager, it adheres to some defined and logical guidelines
to determine whether an application can be loaded, paused, or stopped. If the user is currently working with an activity, the system will give high priority to that application. Conversely, if an activity is not visible and the system determines that an application must be shut down to free up resources, it will shut down the lower-priority application.
The concept of application lifecycle is logical, but a fundamental aspect of Android applications complicates matters. Specifically, the Android application architecture is component-and integration-oriented. This allows a rich user experience, seamless reuse, and easy application integration, but creates a complex task for the application-lifecycle manager.
Let’s consider a typical scenario. A user is talking to someone on the phone and needs to open an e-mail message to answer a question. She goes to the home screen, opens the mail application, opens the e-mail message, clicks a link in the e-mail, and answers her friend’s question by reading a stock quote from a web page. This scenario would require four applications: the home application, a talk application, an e-mail application, and a browser application. As the user navigates from one application to the next, her experience is seamless. In the background, however, the system is saving and restoring application state. For instance,when the user clicks the link in the e-mail message, the system saves metadata on the running
e-mail–message activity before starting the browser-application activity to launch a URL. In fact, the system saves metadata on any activity before starting another, so that it can come back to the activity (when the user backtracks, for example). If memory becomes an issue, the system will have to shut down a process running an activity and resume it as necessary.
Android is sensitive to the lifecycle of an application and its components. Therefore, you’ll need to understand and handle lifecycle events in order to build a stable application. The processes running your Android application and its components go through various lifecycle events, and Android provides callbacks that you can implement to handle state changes. For
starters, you’ll want to become familiar with the various lifecycle callbacks for an activity (see Listing 2-7).
Listing 2-7. Lifecycle Methods of an Activity
protected void onCreate(Bundle savedInstanceState);
protected void onStart();
protected void onRestart();
protected void onResume();
protected void onPause();
protected void onStop();
protected void onDestroy();
Listing 2-7 shows the list of lifecycle methods that Android calls during the life of an activity. It’s important to understand when each of the methods is called by the system to ensure that you implement a stable application. Note that you do not need to react to all of these methods. If you do, however, be sure to call the superclass versions as well. Figure 2-9 shows
the transitions between states.
The system can start and stop your activities based on what else is happening. Android calls the onCreate() method when the activity is freshly created. onCreate() is always followed by a call to onStart(), but onStart() is not always preceded by a call to onCreate() because onStart() can be called if your application was stopped (from onStop()). When onStart() is called, your activity is not visible to the user, but it’s about to be. onResume() is called after onStart(), just when the activity is in the foreground and accessible to the user. At this point, the user is interacting with your activity.
When the user decides to move to another activity, the system will call your activity’s onPause() method. From onPause(), you can expect either onResume() or onStop() to be called. onResume() is called, for example, if the user brings your activity back to the foreground.onStop() is called if your activity becomes invisible to the user. If your activity is brought back
to the foreground, after a call to onStop(), then onRestart() will be called. If your activity sits on the activity stack but is not visible to the user, and the system decides to kill your activity, onDestroy() will be called.
The state model described for an activity appears complex, but you are not required to deal with every possible scenario. In fact, you will mostly handle onCreate() and onPause().You will handle onCreate() to create the user interface for your activity. In this method, you will bind data to your widgets and wire up any event handlers for your UI components. In
onPause(), you will want to persist critical data to your application’s data store. It’s the last safe method that will get called before the system kills your application. onStop() and onDestroy() are not guaranteed to be called, so don’t rely on these methods for critical logic.
The takeaway from this discussion? The system manages your application, and it can start, stop, or resume an application component at any time. Although the system controls your components, they don’t run in complete isolation with respect to your application. In other words, if the system starts an activity in your application, you can count on an application context in your activity. For example, it’s not uncommon to have global variables shared among the activities in your application. You can share a global variable by writing an extension of the android.app.Application class and then initializing the global
variable in the onCreate() method (see Listing 2-8). Activities and other components in your application can then access these references with confidence when they are executing.
Listing 2-8. An Extension of the Application Class
public class MyApplication extends Application
{
// global variable
private static final String myGlobalVariable;
@Override
public void onCreate()
{
super.onCreate();
//... initialize global variables here
myGlobalVariable = loadCacheData();
}
public static String getMyGlobalVariable() {
return myGlobalVariable;
}
}
In the next section, we’ll give you some armor to help you develop Android applications—we will discuss debugging.
Debugging Your App
After you write a few lines of code for your first application, you’ll start wondering if it’s possible to have a debug session while you interact with your application in the emulator. Shortly after that, you’ll instinctively run to System.out.println(), which will fail because the code is running on the emulator and the sys-out statement is not fed back to the IDE. But don’t worry; the Android SDK includes a host of applications that you can use for debugging purposes.
To log messages from your application, you’ll want to use the android.util.Log class. This class defines the familiar informational, warning, and error methods. You can also get detailed tracing information by using the android.os.Debug class, which provides a start-tracing method (Debug.startMethodTracing()) and a stop-tracing method (Debug.stopMethodTracing()). You can then view the tracer output using the trace-viewer tool included in the Android SDK. The SDK also includes a file-explorer tool that you can use to view files on the device. These tools are integrated with the Eclipse IDE (see Figure 2-10).
You can view the tools by selecting the Debug perspective in Eclipse. You can also launch each tool by going to Window ➤ Show View ➤ Other ➤ Android.One of the tools that you’ll use throughout your Android development is LogCat. This tool
displays the log messages that you emit using android.util.Log, exceptions, and so on. We will introduce the other tools throughout the book.
The lifecycle of an Android application, on the other hand, is strictly managed by the system, based on the user’s needs, available resources, and so on. A user might want to launch a web browser, for example, but the system ultimately decides whether to start the application.Although the system is the ultimate manager, it adheres to some defined and logical guidelines
to determine whether an application can be loaded, paused, or stopped. If the user is currently working with an activity, the system will give high priority to that application. Conversely, if an activity is not visible and the system determines that an application must be shut down to free up resources, it will shut down the lower-priority application.
The concept of application lifecycle is logical, but a fundamental aspect of Android applications complicates matters. Specifically, the Android application architecture is component-and integration-oriented. This allows a rich user experience, seamless reuse, and easy application integration, but creates a complex task for the application-lifecycle manager.
Let’s consider a typical scenario. A user is talking to someone on the phone and needs to open an e-mail message to answer a question. She goes to the home screen, opens the mail application, opens the e-mail message, clicks a link in the e-mail, and answers her friend’s question by reading a stock quote from a web page. This scenario would require four applications: the home application, a talk application, an e-mail application, and a browser application. As the user navigates from one application to the next, her experience is seamless. In the background, however, the system is saving and restoring application state. For instance,when the user clicks the link in the e-mail message, the system saves metadata on the running
e-mail–message activity before starting the browser-application activity to launch a URL. In fact, the system saves metadata on any activity before starting another, so that it can come back to the activity (when the user backtracks, for example). If memory becomes an issue, the system will have to shut down a process running an activity and resume it as necessary.
Android is sensitive to the lifecycle of an application and its components. Therefore, you’ll need to understand and handle lifecycle events in order to build a stable application. The processes running your Android application and its components go through various lifecycle events, and Android provides callbacks that you can implement to handle state changes. For
starters, you’ll want to become familiar with the various lifecycle callbacks for an activity (see Listing 2-7).
Listing 2-7. Lifecycle Methods of an Activity
protected void onCreate(Bundle savedInstanceState);
protected void onStart();
protected void onRestart();
protected void onResume();
protected void onPause();
protected void onStop();
protected void onDestroy();
Listing 2-7 shows the list of lifecycle methods that Android calls during the life of an activity. It’s important to understand when each of the methods is called by the system to ensure that you implement a stable application. Note that you do not need to react to all of these methods. If you do, however, be sure to call the superclass versions as well. Figure 2-9 shows
the transitions between states.
The system can start and stop your activities based on what else is happening. Android calls the onCreate() method when the activity is freshly created. onCreate() is always followed by a call to onStart(), but onStart() is not always preceded by a call to onCreate() because onStart() can be called if your application was stopped (from onStop()). When onStart() is called, your activity is not visible to the user, but it’s about to be. onResume() is called after onStart(), just when the activity is in the foreground and accessible to the user. At this point, the user is interacting with your activity.
When the user decides to move to another activity, the system will call your activity’s onPause() method. From onPause(), you can expect either onResume() or onStop() to be called. onResume() is called, for example, if the user brings your activity back to the foreground.onStop() is called if your activity becomes invisible to the user. If your activity is brought back
to the foreground, after a call to onStop(), then onRestart() will be called. If your activity sits on the activity stack but is not visible to the user, and the system decides to kill your activity, onDestroy() will be called.
The state model described for an activity appears complex, but you are not required to deal with every possible scenario. In fact, you will mostly handle onCreate() and onPause().You will handle onCreate() to create the user interface for your activity. In this method, you will bind data to your widgets and wire up any event handlers for your UI components. In
onPause(), you will want to persist critical data to your application’s data store. It’s the last safe method that will get called before the system kills your application. onStop() and onDestroy() are not guaranteed to be called, so don’t rely on these methods for critical logic.
The takeaway from this discussion? The system manages your application, and it can start, stop, or resume an application component at any time. Although the system controls your components, they don’t run in complete isolation with respect to your application. In other words, if the system starts an activity in your application, you can count on an application context in your activity. For example, it’s not uncommon to have global variables shared among the activities in your application. You can share a global variable by writing an extension of the android.app.Application class and then initializing the global
variable in the onCreate() method (see Listing 2-8). Activities and other components in your application can then access these references with confidence when they are executing.
Listing 2-8. An Extension of the Application Class
public class MyApplication extends Application
{
// global variable
private static final String myGlobalVariable;
@Override
public void onCreate()
{
super.onCreate();
//... initialize global variables here
myGlobalVariable = loadCacheData();
}
public static String getMyGlobalVariable() {
return myGlobalVariable;
}
}
In the next section, we’ll give you some armor to help you develop Android applications—we will discuss debugging.
Debugging Your App
After you write a few lines of code for your first application, you’ll start wondering if it’s possible to have a debug session while you interact with your application in the emulator. Shortly after that, you’ll instinctively run to System.out.println(), which will fail because the code is running on the emulator and the sys-out statement is not fed back to the IDE. But don’t worry; the Android SDK includes a host of applications that you can use for debugging purposes.
To log messages from your application, you’ll want to use the android.util.Log class. This class defines the familiar informational, warning, and error methods. You can also get detailed tracing information by using the android.os.Debug class, which provides a start-tracing method (Debug.startMethodTracing()) and a stop-tracing method (Debug.stopMethodTracing()). You can then view the tracer output using the trace-viewer tool included in the Android SDK. The SDK also includes a file-explorer tool that you can use to view files on the device. These tools are integrated with the Eclipse IDE (see Figure 2-10).
You can view the tools by selecting the Debug perspective in Eclipse. You can also launch each tool by going to Window ➤ Show View ➤ Other ➤ Android.One of the tools that you’ll use throughout your Android development is LogCat. This tool
displays the log messages that you emit using android.util.Log, exceptions, and so on. We will introduce the other tools throughout the book.
Read 31 times
Published in
Java