commontasks.jd revision 9066cfe9886ac131c34d59ed0e2d287b0e3c0087
1page.title=Common Tasks and How to Do Them in Android 2parent.title=FAQs, Tips, and How-to 3parent.link=index.html 4@jd:body 5 6<ul> 7 <li><a href="#neweclipseandroidproject">Creating an Android Application using 8 the Eclipse plugin</a></li> 9 <li><a href="#newandroidprojectnoeclipse">Creating an Android Application without 10 the Eclipse plugin</a></li> 11 <li><a href="#addexternallibrary">Adding an External Library (.jar) using Eclipse</a></li> 12 <li><a href="#implementcallbacks">Implementing Activity callbacks</a> (Android 13 calls your activity at various key moments in its life cycle. You must know 14 how to handle each of these to draw your screen, initialize class members, 15 and acquire data.)</li> 16 <li><a href="#opennewscreen">Opening a new screen</a></li> 17 <li><a href="#listening">Listening for button clicks </a></li> 18 <li><a href="#configurewindowproperties">Configuring general window properties </a></li> 19 <li><a href="#localhostalias">Referring to localhost from the emulated environment</a></li> 20 <li><a href="#appstate">Storing and retrieving state</a></li> 21 <li><a href="{@docRoot}guide/topics/data/data-storage.html#preferences">Storing and retrieving preferences</a></li> 22 <li><a href="#storingandretrieving">Storing and retrieving larger or more complex 23 persistent data</a> (files and data) </li> 24 <li><a href="#playback">Playing audio, video, still, or other media files</a></li> 25 <li><a href="#broadcastreceivers">Listening for and broadcasting global messages 26 and setting alarms</a></li> 27 <li><a href="#alerts">Displaying alerts </a></li> 28 <li><a href="#progressbar">Displaying a progress bar</a> </li> 29 <li><a href="#addmenuitems">Adding items to the screen menu</a> </li> 30 <li><a href="#webpage">Display a web page</a> </li> 31 <li><a href="#binding">Binding to data</a></li> 32 <li><a href="#handle">Getting a Handle to a Screen Element</a></li> 33 <li><a href="#captureimages">Capture images from the phone camera </a></li> 34 <li><a href="#threading">Handling expensive operations in the UI thread</a></li> 35 <li><a href="#selectingtext">Selecting, highlighting, or styling portions of 36 text</a></li> 37 <li><a href="#querymap">Utilizing attributes in a Map query</a></li> 38 <li><a href="#filelist">List of files for an Android application</a></li> 39 <li><a href="#logging">Print messages to a log file</a></li> 40</ul> 41<p>The ApiDemos sample application includes many, many examples of common 42tasks and UI features. See the code inside 43<code><sdk>samples/ApiDemos</code> and the other sample applications 44under the <code>samples/</code> folder in the SDK.</p> 45 46 47<h2 id="neweclipseandroidproject">Creating an Android Application using the Eclipse Plugin</h2> 48 49<p>Using the Android Eclipse plugin is the fastest and easiest way 50to start creating a new Android application. The plugin automatically generates 51the correct project structure for your application, and keeps the resources 52compiled for you automatically.</p> 53 54<p>It is still a good idea to know what is going on though. Take a look at <a 55href="{@docRoot}guide/topics/fundamentals.html">Application Fundamentals</a> 56to understand the basics of how an Android application works.</p> 57 58<p>You should also take a look at the ApiDemos application and the other sample 59applications included in the SDK, in the <code><sdk>/samples/ 60folder in the SDK.</p> 61 62<p>Finally, a great way to started with Android development in Eclipse is to 63follow both the <a href="{@docRoot}guide/tutorials/hello-world.html">Hello, 64World</a> and <a 65href="{@docRoot}guide/tutorials/notepad/index.html">Notepad</a> code 66tutorials. In particular, the start of the Hello Android tutorial is an 67excellent introduction to creating a new Android application in Eclipse.</p> 68 69<h2 id="newandroidprojectnoeclipse">Creating an Android Application without the Eclipse Plugin</h2> 70 71<p>This topic describes the manual steps in creating an Android application. 72Before reading this, you should read <a 73href="{@docRoot}guide/topics/fundamentals.html">Application Fundamentals</a> 74to understand the basics of how an Android application works. You might also 75want to look at the sample code included with the Android SDK, in the 76<code><sdk>/samples/</code> directory. </p> 77 78<p>Here is a list of the basic steps in building an application.</p> 79<ol> 80 <li><strong>Create your required resource files</strong> This includes 81 the AndroidManifest.xml global description file, string files that your application 82 needs, and layout files describing your user interface. A full list of optional 83 and required files and syntax details for each is given in <a href="#filelist">File 84 List for an Android Application</a>. </li> 85 <li><strong>Design your user interface</strong> See <a 86 href="{@docRoot}guide/topics/ui/index.html">User Interface</a> for 87 details on elements of the Android screen. </li> 88 <li><strong>Implement your Activity </strong>(this page)<strong> </strong> You 89 will create one class/file for each screen in your application. Screens will 90 inherit from an {@link android.app android.app} class, typically {@link android.app.Activity 91 android.app.Activity} for basic screens, {@link android.app.ListActivity 92 android.app.ListActivity} for list screens, or {@link android.app.Dialog 93 android.app.Dialog} for dialog boxes. You will implement the required callbacks 94 that let you draw your screen, query data, and commit changes, and also perform 95 any required tasks such as opening additional screens or reading data from 96 the device. Common tasks, such as opening a new screen or reading data from 97 the device, are described below. 98 The list of files you'll need for your application are described in <a href="#filelist">List 99 of Files for an Android Application</a>. </li> 100 <li><strong><a href="{@docRoot}guide/developing/other-ide.html#buildingwithant">Build and install your 101 package</a>.</strong> The Android SDK has some nice tools for generating 102 projects and debugging code. </li> 103</ol> 104 105<h2 id="addexternallibrary">Adding an External Library (.jar) using Eclipse</h2> 106<p> 107You can use a third party JAR in your application by adding it to your Eclipse project as follows: 108</p> 109<ol> 110<li> 111In the <strong>Package Explorer</strong> panel, right-click on your project and select <strong>Properties</strong>. 112<li> 113Select <strong>Java Build Path</strong>, then the tab <strong>Libraries</strong>. 114<li> 115Press the <strong>Add External JARs...</strong> button and select the JAR file. 116</ol> 117<p> 118Alternatively, if you want to include third party JARs with your package, create a new directory for them within your project and select <strong>Add Library...</strong> instead.</p> 119<p> 120It is not necessary to put external JARs in the assets folder. 121</p> 122 123<a name="implementcallbacks" id="implementcallbacks"></a> 124<h2>Implementing Activity Callbacks</h2> 125<p>Android calls a number of callbacks to let you draw your screen, store data before 126 pausing, and refresh data after closing. You must implement at least some of 127 these methods. See <a href="{@docRoot}guide/topics/fundamentals.html#lcycles">Lifecycles</a> 128 discussion in Application Fundamentals to learn when and in what order these methods 129 are called. Here are some of the standard types of screen classes that Android provides:</p> 130<ul> 131 <li>{@link android.app.Activity android.app.Activity} - This is a standard screen, 132 with no specialization.</li> 133 <li>{@link android.app.ListActivity android.app.ListActivity} - This is a screen 134 that is used to display a list of something. It hosts a ListView object, 135 and exposes methods to let you identify the selected item, receive callbacks 136 when the selected item changes, and perform other list-related actions. </li> 137 <li>{@link android.app.Dialog android.app.Dialog} - This is a small, popup dialog-style 138 window that isn't intended to remain in the history stack. (It is not resizeable 139 or moveable by the user.)</li> 140</ul> 141 142<a name="opennewscreen" id="opennewscreen"></a><h2>Opening a New Screen</h2> 143<p>Your Activity will often need to open another Activity screen as it progresses. 144 This new screen can be part of the same application or part of another application, 145 the new screen can be floating or full screen, it can return a result, and you 146 can decide whether to close this screen and remove it from the history stack 147 when you are done with it, or to keep the screen open in history. These next 148 sections describe all these options. </p> 149<h3>Floating or full?<a name="floatingorfull" id="floatingorfull"></a></h3> 150<p>When you open a new screen you can decide whether to make it transparent or floating, 151 or full-screen. The choice of new screen affects the event sequence of events 152 in the old screen (if the new screen obscures the old screen, a different 153 series of events is called in the old screen). See <a 154 href="{@docRoot}guide/topics/fundamentals.html#lcycles">Lifecycles</a> discussion 155 in Application Fundamentals for details. </p> 156<p>Transparent or floating windows are implemented in three 157 standard ways: </p> 158<ul> 159 <li>Create an {@link android.app.Dialog app.Dialog} class </li> 160 <li>Create an {@link android.app.AlertDialog app.AlertDialog} class </li> 161 <li>Set the {@link android.R.style#Theme_Dialog} <em>theme</em> attribute to <code>@android:style/Theme.Dialog</code> 162 in your AndroidManifest.xml file. For example: 163</ul> 164<blockquote> 165 <pre><activity class="AddRssItem" android:label="Add an item" android:theme="@android:style/Theme.Dialog"/> 166</pre> 167</blockquote> 168<p>Calling startActivity() or startActivityForResult() will open a new screen in whatever 169 way it defines itself (if it uses a floating theme it will be floating, 170 otherwise it will be full screen). </p> 171<h3>Opening a Screen </h3> 172<p>When you want to open a new screen, you can either explicitly specify the activity 173 class to open, or you can let the operating system decide which screen to open, 174 based upon the data and various parameters you pass in. A screen is opened by 175 calling {@link android.app.Activity#startActivity(android.content.Intent) startActivity} 176 and passing in an {@link android.content.Intent Intent} object, which specifies 177 the criteria for the handling screen. To specify a specific screen, call Intent.setClass 178 or setClassName with the exact activity class to open. Otherwise, set a variety 179 of values and data, and let Android decide which screen is appropriate to open. 180 Android will find one or zero Activities that match the specified requirements; 181 it will never open multiple activities for a single request. More information 182 on Intents and how Android resolves them to a specific class is given in the 183 {@link android.content.Intent Intent} topic. </p> 184<a name="intentexamples" id="intentexamples"></a><h3>Some Intent examples </h3> 185<p>The following snippet loads the com.android.samples.Animation1 class, and 186 passes it some arbitrary data.:</p> 187<pre>Intent myIntent = new Intent(); 188myIntent.setClassName("com.android.samples", "com.android.samples.Animation1"); 189myIntent.putExtra("com.android.samples.SpecialValue", "Hello, Joe!"); // key/value pair, where key needs current package prefix. 190startActivity(myIntent); </pre> 191<p>The next snippet requests that a Web page be opened by specifying the VIEW action, 192 and a URI data string starting with "http://" schema:</p> 193<pre>Intent myIntent = new Intent(Intent.VIEW_ACTION, Uri.parse("http://www.google.com"));</pre> 194<p>Here is the intent filter from the AndroidManifest.xml file for com.android.browser:</p> 195<pre><intent-filter> 196 <action android:name="android.intent.action.VIEW" /> 197 <category android:name="android.intent.category.DEFAULT" /> 198 <scheme android:name="http" /> 199 <scheme android:name="https" /> 200 <scheme android:name="file" /> 201</intent-filter> </pre> 202<p>Android defines a number of standard values, for instance the action constants 203 defined by {@link android.content.Intent}. You can define custom values, but 204 both the caller and handler must use them. See the <intent-filter> 205 tag description in <a href="{@docRoot}guide/topics/manifest/manifest-intro.html">The AndroidManifest.xml 206 File</a> for more information on the manifest syntax for the handling 207 application. </p> 208<a name="returningaresult" id="returningaresult"></a><h3>Returning a Result from a Screen</h3> 209<p>A window can return a result after it closes. This result will be passed back 210 into the calling Activity's {@link android.app.Activity#onActivityResult(int,int,android.content.Intent) 211 onActivityResult()} method, which can supply an Intent containing arbitrary data, along with 212 the request code passed to startActivityForResult(). Note that you must call the {@link 213 android.app.Activity#startActivityForResult(android.content.Intent,int) startActivityForResult()} 214 method that accepts a request code parameter to get this callback. The following 215 code demonstrates opening a new screen and retrieving a result. </p> 216<pre>// Open the new screen. 217public void onClick(View v){ 218 // Start the activity whose result we want to retrieve. The 219 // result will come back with request code GET_CODE. 220 Intent intent = new Intent(this, com.example.app.ChooseYourBoxer.class); 221 startActivityForResult(intent, CHOOSE_FIGHTER); 222} 223 224// Listen for results. 225protected void onActivityResult(int requestCode, int resultCode, Intent data){ 226 // See which child activity is calling us back. 227 switch (resultCode) { 228 case CHOOSE_FIGHTER: 229 // This is the standard resultCode that is sent back if the 230 // activity crashed or didn't doesn't supply an explicit result. 231 if (resultCode == RESULT_CANCELED){ 232 myMessageboxFunction("Fight cancelled"); 233 } 234 else { 235 myFightFunction(data); 236 } 237 default: 238 break; 239 } 240} 241 242// Class SentResult 243// Temporary screen to let the user choose something. 244 private OnClickListener mLincolnListener = new OnClickListener(){ 245 public void onClick(View v) { 246 Bundle stats = new Bundle(); 247 stats.putString("height","6\'4\""); 248 stats.putString("weight", "190 lbs"); 249 stats.putString("reach", "74\""); 250 setResult(RESULT_OK, "Lincoln", stats); 251 finish(); 252 } 253 }; 254 255 private OnClickListener mWashingtonListener = new OnClickListener() { 256 public void onClick(View v){ 257 Bundle stats = new Bundle(); 258 stats.putString("height","6\'2\""); 259 stats.putString("weight", "190 lbs"); 260 stats.putString("reach", "73\""); 261 setResult(RESULT_OK, "Washington", Bundle); 262 finish(); 263 } 264 }; 265 </pre> 266<h3>Lifetime of the new screen </h3> 267<p>An activity can remove itself from the history stack by calling {@link android.app.Activity#finish() 268 Activity.finish()} on itself, or the activity that opened the screen can call 269 {@link android.app.Activity#finishActivity(int) Activity.finishActivity()} 270 on any screens that it opens to close them. </p> 271<a name="listening" id="listening"></a><h2>Listening for Button Clicks</h2> 272<p>Button click and other UI event capturing are covered in <a href="{@docRoot}guide/topics/ui/ui-events.html">Handling UI Events</a> on the UI Design page.</p> 273<a name="configurewindowproperties" id="configurewindowproperties"></a><h2>Configuring General Window Properties</h2> 274<p>You can set a number of general window properties, such as whether to display 275 a title, whether the window is floating, and whether it displays an icon, by 276 calling methods on the {@link android.view.Window Window} member 277 of the underlying View object for the window. Examples include calling {@link 278 android.app.Activity#getWindow() getWindow().requestFeature()} (or the convenience 279 method {@link android.app.Activity#requestWindowFeature(int) requestWindowFeature(<em>some_feature</em>)}) 280 to hide the title. Here is an example of hiding the title bar:</p> 281<pre>//Hide the title bar 282requestWindowFeature(Window.FEATURE_NO_TITLE); 283</pre> 284<a name="localhostalias" id="localhostalias"></a><h2>Referring to localhost from the emulated environment</h2> 285<p> 286If you need to refer to your host computer's <em>localhost</em>, such as when you 287want the emulator client to contact a server running on the same host, use the alias 288<code>10.0.2.2</code> to refer to the host computer's loopback interface. 289From the emulator's perspective, localhost (<code>127.0.0.1</code>) refers to its own 290loopback interface. 291</p> 292<a name="appstate" id="appstate"></a><h2>Storing and Retrieving State</h2> 293<p>If your application is dumped from memory because of space concerns, it will lose 294 all user interface state information such as checkbox state and text box values 295 as well as class member values. Android calls {@link android.app.Activity#onSaveInstanceState(android.os.Bundle) 296 Activity.onSaveInstanceState} before it pauses the application. This method hands in a {@link 297 android.os.Bundle Bundle} that can be used to store name/value pairs that will 298 persist and be handed back to the application even if it is dropped from memory. 299 Android will pass this Bundle back to you when it calls {@link android.app.Activity#onCreate(android.os.Bundle) 300 onCreate()}. This Bundle only exists while the application is still in the history 301 stack (whether or not it has been removed from memory) and will be lost when 302 the application is finalized. See the topics for {@link android.app.Activity#onSaveInstanceState} and 303 {@link android.app.Activity#onCreate} for 304 examples of storing and retrieving state.</p> 305<p>Read more about the lifecycle of an application in <a href="{@docRoot}guide/topics/fundamentals.html">Application Fundamentals</a>.</p> 306<h3>Storing and Retrieving Larger or More Complex Persistent Data<a name="storingandretrieving" id="storingandretrieving"></a></h3> 307<p>Your application can store files or complex collection objects, and reserve them 308 for private use by itself or other activities in the application, or it can expose 309 its data to all other applications on the device. See <a href="{@docRoot}guide/topics/data/data-storage.html">Storing, 310 Retrieving, and Exposing Data</a> to learn how to store and retrieve private data, 311 how to store and retrieve common data from the device, and how to expose your 312 private data to other applications.</p> 313<a name="playback" id="playback"></a><h2>Playing Media Files</h2> 314<p>Please see the document <a href="{@docRoot}guide/topics/media/index.html">Audio and Video</a> for more details.</p> 315<a name="broadcastreceivers" id="broadcastreceivers"></a><h2>Listening For and Broadcasting Global Messages, and Setting Alarms</h2> 316<p>You can create a listening class that can be notified or even instantiated whenever 317 a specific type of system message is sent. 318</p> 319<p>The listening classes, called broadcast receivers, extend {@link android.content.BroadcastReceiver 320 BroadcastReceiver}. If you want Android to instantiate the object whenever an appropriate 321 intent notification is sent, define the receiver with a <code><receiver></code> element 322 in the AndroidManifext.xml file. If the caller is expected to instantiate the 323 object in preparation to receive a message, this is not required. The receiver 324 will get a call to their {@link android.content.BroadcastReceiver#onReceive(android.content.Context,android.content.Intent) 325 BroadcastReceiver.onReceive()} method. A receiver can define an <code><intent-filter></code> tag 326 that describes the types of messages it will receive. Just as Android's IntentResolver 327 will look for appropriate Activity matches for a startActivity() call, it will 328 look for any matching Receivers (but it will send the message to all matching 329 receivers, not to the "best" match). </p> 330<p>To send a notification, the caller creates an {@link android.content.Intent Intent} 331 object and calls {@link android.app.Activity#sendBroadcast(android.content.Intent) 332 Context.sendBroadcast()} with that Intent. Multiple recipients can receive 333 the same message. You can broadcast an Intent message to an intent receiver in 334 any application, not only your own. If the receiving class is not registered 335 using <code><receiver></code> in its manifest, you can dynamically instantiate 336 and register a receiver by calling {@link android.content.Context#registerReceiver(android.content.BroadcastReceiver,android.content.IntentFilter) 337 Context.registerReceiver()}. </p> 338<p>Receivers can include intent filters to specify what kinds of intents they are 339 listening for. Alternatively, if you expect a single known caller to contact 340 a single known receiver, the receiver does not specify an intent filter, and 341 the caller specifies the receiver's class name in the Intent by calling {@link 342 android.content.Intent#setClassName(java.lang.String, java.lang.String) Intent.setClassName()} 343 with the recipient's class name. The recipient receives a {@link android.content.Context 344 Context} object that refers to its own package, not to the package of the sender.</p> 345<p><em><strong>Note:</strong></em> If a receiver or broadcaster 346 enforces permissions, your application might need to request permission 347 to send or receive messages from that object. You can request permission by using 348 the <uses-permission> tag in the manifest. </p> 349<p>Here is a code snippet of a sender and receiver. This example does not demonstrate 350 registering receivers dynamically. For a full code example, see the AlarmService 351 class in the ApiDemos project.</p> 352<h3>Sending the message</h3> 353<pre>// We are sending this to a specific recipient, so we will 354// only specify the recipient class name. 355Intent intent = new Intent(this, AlarmReceiver.class); 356intent.putExtra("message","Wake up."); 357sendBroadcast(intent); 358</pre> 359<h3>Receiving the message</h3> 360<p><strong>Receiver AndroidManifest.xml </strong>(because there is no intent filter 361 child, this class will only receive a broadcast when the receiver class is specified 362 by name, as is done in this example):</p> 363<pre> 364<receiver class=".AlarmReceiver" /></pre> 365<p><strong>Receiver Java code: </strong></p> 366<pre> 367public class AlarmReceiver extends BroadcastReceiver{ 368 // Display an alert that we've received a message. 369 @Override 370 public void onReceive(Context context, Intent intent){ 371 // Send a text notification to the screen. 372 NotificationManager nm = (NotificationManager) 373 context.getSystemService(Context.NOTIFICATION_SERVICE); 374 nm.notifyWithText(R.id.alarm, 375 "Alarm!!!", 376 NotificationManager.LENGTH_SHORT, 377 null); 378 } 379} </pre> 380<h3>Other system messages</h3> 381<p>You can listen for other system messages sent by Android as well, such as USB 382 connection/removal messages, SMS arrival messages, and timezone changes. See 383 {@link android.content.Intent} for a list of broadcast messages to listen for. 384 Messages are marked "Broadcast Action" in the documentation. </p> 385<h3>Listening for phone events<a name="phoneevents" id="phoneevents"></a></h3> 386<p>The {@link android.telephony android.telephony} package overview page describes how to 387 register to listen for phone events. </p> 388<a name="alarms" id="alarms"></a><h3>Setting Alarms </h3> 389<p>Android provides an {@link android.app.AlarmManager AlarmManager} service that 390 will let you specify an Intent to send at a designated time. This intent is typically 391 used to start an application at a preset time. (Note: If you want to send 392 a notification to a sleeping or running application, use {@link android.os.Handler 393 Handler} instead.)</p> 394<a name="alerts" id="alerts"></a><h2>Displaying Alerts</h2> 395<p>There are two major kinds of alerts that you may display to the user: 396(1) Normal alerts are displayed in response to a user action, such as 397trying to perform an action that is not allowed. (2) Out-of-band alerts, 398called notifications, are 399displayed as a result of something happening in the background, such as the 400user receiving new e-mail.</p> 401 402<a name="dialogsandalerts" id="dialogsandalerts"></a><h3>Normal Alerts</h3> 403 404<p>Android provides a number of ways for you to show popup notifications to your 405 user as they interact with your application. </p> 406<table width="100%" border="1"> 407 <tr> 408 <th scope="col">Class</th> 409 <th scope="col">Description</th> 410 </tr> 411 <tr> 412 <td>{@link android.app.Dialog app.Dialog}</td> 413 <td>A generic floating dialog box with a layout that you design. </td> 414 </tr> 415 <tr> 416 <td><p>{@link android.app.AlertDialog app.AlertDialog}</p></td> 417 <td>A popup alert dialog with two buttons (typically OK and Cancel) that 418 take callback handlers. See the section after this table for more details. </td> 419 </tr> 420 <tr> 421 <td>{@link android.app.ProgressDialog ProgressDialog} </td> 422 <td>A dialog box used to indicate progress of an operation with a known progress 423 value or an indeterminate length (setProgress(bool)). See <strong>Views</strong> > <strong>Progress Bar</strong> in 424 ApiDemos for examples. </td> 425 </tr> 426 <tr> 427 <td>Activity</td> 428 <td>By setting the theme of an activity to 429 {@link android.R.style#Theme_Dialog 430 android:theme="android:style/Theme.Dialog"}, 431 your activity will take on 432 the appearance of a normal dialog, floating on top of whatever was 433 underneath it. You usually set the theme through the 434 {@link android.R.attr#theme android:theme} attribute in your AndroidManifest.xml. 435 The advantage of this 436 over Dialog and AlertDialog is that Application has a much better managed 437 life cycle than dialogs: if a dialog goes to the background and is killed, 438 you cannot recapture state, whereas Application exposes a {@link android.os.Bundle 439 Bundle} of saved values in <code>onCreate()</code> to help you maintain state.</td> 440 </tr> 441</table> 442<h3>AlertDialog</h3> 443<p>This is a basic warning dialog box that lets you configure a message, button text, 444 and callback. You can create one by calling using the {@link 445 android.app.AlertDialog.Builder} class, as shown here. </p> 446<pre>private Handler mHandler = new Handler() { 447 public void handleMessage(Message msg) { 448 switch (msg.what) { 449 case ACCEPT_CALL: 450 answer(msg.obj); 451 break; 452 453 case BOUNCE_TO_VOICEMAIL: 454 voicemail(msg.obj); 455 break; 456 457 } 458 } 459}; 460 461 462private void IncomingMotherInlawCall(Connection c) { 463 String Text; 464 465 // "Answer" callback. 466 Message acceptMsg = Message.obtain(); 467 acceptMsg.target = mHandler; 468 acceptMsg.what = ACCEPT_CALL; 469 acceptMsg.obj = c.getCall(); 470 471 // "Cancel" callback. 472 final Message rejectMsg = Message.obtain(); 473 rejectMsg.target = mHandler; 474 rejectMsg.what = BOUNCE_TO_VOICEMAIL; 475 rejectMsg.obj = c.getCall(); 476 477 new AlertDialog.Builder(this) 478 .setMessage("Phyllis is calling") 479 .setPositiveButton("Answer", acceptMsg) 480 .setOnCanceListener(new OnCancelListener() { 481 public void onCancel(DialogInterface dialog) { 482 rejectMsg.sendToTarget(); 483 }}); 484 .show(); 485} </pre> 486 487<h3>Notifications</h3> 488 489<p>Out-of-band alerts should always be displayed using the 490{@link android.app.NotificationManager}, which allows you to tell the user 491about something they may be interested in without disrupting what they are 492currently doing. A notification can be anything from a brief pop-up box 493informing the user of the new information, through displaying a persistent 494icon in the status bar, to vibrating, playing sounds, or flashing lights to 495get the user's attention. In all cases, the user must explicitly shift their 496focus to the notification before they can interact with it.</p> 497 498<p>The following code demonstrates using NotificationManager to display a basic text 499 popup when a new SMS message arrives in a listening service, and provides the 500 current message count. You can see several more examples in the ApiDemos application, 501 under app/ (named <em>notification</em>*.java).</p> 502<pre>static void setNewMessageIndicator(Context context, int messageCount){ 503 // Get the static global NotificationManager object. 504 NotificationManager nm = NotificationManager.getDefault();</p> 505 506 // If we're being called because a new message has been received, 507 // then display an icon and a count. Otherwise, delete the persistent 508 // message. 509 if (messageCount > 0) { 510 nm.notifyWithText(myApp.NOTIFICATION_GUID, // ID for this notification. 511 messageCount + " new message" + messageCount > 1 ? "s":"", // Text to display. 512 NotificationManager.LENGTH_SHORT); // Show it for a short time only. 513 } 514}</pre> 515<p>To display a notification in the status bar and have it launch an intent when 516 the user selects it (such as the new text message notification does), call {@link 517 android.app.NotificationManager#notify(int, android.app.Notification) NotificationManager.notify()}, 518 and pass in vibration patterns, status bar icons, or Intents to associate with 519 the notification. </p> 520<a name="progressbar" id="progressbar"></a><h2>Displaying a Progress Bar</h2> 521<p>An activity can display a progress bar to notify the user that something is happening. 522 To display a progress bar in a screen, call {@link android.app.Activity#requestWindowFeature(int) 523 Activity.requestWindowFeature(Window.FEATURE_PROGRESS)}. To set the value 524 of the progress bar, call {@link android.view.Window#setFeatureInt(int,int) 525 Activity.getWindow().setFeatureInt(Window.FEATURE_PROGRESS, <em>level</em>)}. 526 Progress bar values are from 0 to 9,999, or set the value to 10,000 to make the 527 progress bar invisible. </p> 528<p>You can also use the {@link android.app.ProgressDialog ProgressDialog} class, 529 which enables a dialog box with an embedded progress bar to send a "I'm working 530 on it" notification to the user. </p> 531<a name="addmenuitems" id="addmenuitems"></a><h2>Adding Items to the Screen Menu</h2> 532<p>See <a href="{@docRoot}guide/topics/ui/menus.html">Creating Menus</a>.</p> 533 534<a name="webpage" id="webpage"></a><h2>Display a Web Page</h2> 535<p>Use the {@link android.webkit.WebView webkit.WebView} object. </p> 536<a name="binding" id="binding"></a><h2>Binding to Data</h2> 537<p>You can bind a ListView to a set of underlying data by using a shim class called 538 {@link android.widget.ListAdapter ListAdapter} (or a subclass). ListAdapter subclasses 539 bind to a variety of data sources, and expose a common set of methods such as 540 getItem() and getView(), and uses them to pick View items to display in its list. 541 You can extend ListAdapter and override getView() to create your own custom list 542 items. There are essentially only two steps you need to perform to bind to data: </p> 543<ol> 544 <li>Create a ListAdapter object and specify its data source</li> 545 <li>Give the ListAdapter to your ListView object.</li> 546</ol> 547<p>That's it!</p> 548<p>Here's an example of binding a ListActivity screen to the results from a cursor 549 query. (Note that the setListAdapter() method shown is a convenience method that 550 gets the page's ListView object and calls setAdapter() on it.)</p> 551<pre>// Run a query and get a Cursor pointing to the results. 552Cursor c = People.query(this.getContentResolver(), null); 553startManagingCursor(c); 554 555// Create the ListAdapter. A SimpleCursorAdapter lets you specify two interesting things: 556// an XML template for your list item, and 557// The column to map to a specific item, by ID, in your template. 558ListAdapter adapter = new SimpleCursorAdapter(this, 559 android.R.layout.simple_list_item_1, // Use a template that displays a text view 560 c, // Give the cursor to the list adapter 561 new String[] {People.NAME} , // Map the NAME column in the people database to... 562 new String[] {"text1"}); // The "text1" view defined in the XML template 563setListAdapter(adapter);</pre> 564<p>See view/List4 in the ApiDemos project for an example of extending ListAdapter 565 for a new data type. </p> 566 567<a name="handle"></a> 568 569<h2>Getting a Handle to a Screen Element</h2> 570<p>You can get a handle to a screen element by calling {@link 571android.app.Activity#findViewById(int) Activity.findViewById}. You can then use 572the handle to set or retrieve any values exposed by the object. </p> 573<a name="captureimages" id="captureimages"></a><h2>Capture Images from the Phone Camera</h2> 574<p>You can hook into the device's camera onto your own Canvas object by using the 575 {@link android.hardware.Camera Camera} class. See that class's documentation, 576 and the ApiDemos project's Camera Preview application (Graphics/Camera Preview) 577 for example code. </p> 578 579 580<a name="threading" id="threading"></a><h2>Handling Expensive Operations in the UI Thread</h2> 581<p>Avoid performing long-running operations (such as network I/O) directly in the UI thread — 582the main thread of an application where the UI is run — or your application may be blocked 583and become unresponsive. Here is a brief summary of the recommended approach for handling expensive operations:</p> 584<ol> 585<li>Create a Handler object in your UI thread</li> 586<li>Spawn off worker threads to perform any required expensive operations</li> 587<li>Post results from a worker thread back to the UI thread's handler either through a Runnable or a {@link android.os.Message}</li> 588<li>Update the views on the UI thread as needed</li> 589</ol> 590 591<p>The following outline illustrates a typical implementation:</p> 592 593<pre> 594public class MyActivity extends Activity { 595 596 [ . . . ] 597 // Need handler for callbacks to the UI thread 598 final Handler mHandler = new Handler(); 599 600 // Create runnable for posting 601 final Runnable mUpdateResults = new Runnable() { 602 public void run() { 603 updateResultsInUi(); 604 } 605 }; 606 607 @Override 608 protected void onCreate(Bundle savedInstanceState) { 609 super.onCreate(savedInstanceState); 610 611 [ . . . ] 612 } 613 614 protected void startLongRunningOperation() { 615 616 // Fire off a thread to do some work that we shouldn't do directly in the UI thread 617 Thread t = new Thread() { 618 public void run() { 619 mResults = doSomethingExpensive(); 620 mHandler.post(mUpdateResults); 621 } 622 }; 623 t.start(); 624 } 625 626 private void updateResultsInUi() { 627 628 // Back in the UI thread -- update our UI elements based on the data in mResults 629 [ . . . ] 630 } 631} 632</pre> 633 634<p>For further discussions on this topic, see 635<a href="{@docRoot}guide/practices/design/responsiveness.html">Designing for Responsiveness</a> 636and the {@link android.os.Handler} documentation.</p> 637 638<a name="selectingtext" id="selectingtext"></a><h2>Selecting, Highlighting, or Styling Portions of Text</h2> 639<p>You can highlight or style the formatting of strings or substrings of text in 640 a TextView object. There are two ways to do this:</p> 641<ul> 642 <li>If you use a <a href="{@docRoot}guide/topics/resources/available-resources.html#stringresources">string resource</a>, 643 you can add some simple styling, such as bold or italic using HTML notation. 644 The currently supported tags are: <code>B</code> (bold), 645 <code>I</code> (italic), <code>U</code> (underline), 646 <code>TT</code> (monospace), <code>BIG</code>, <code>SMALL</code>, 647 <code>SUP</code> (superscript), <code>SUB</code> (subscript), 648 and <code>STRIKE</code> (strikethrough). 649 So, for example, in res/values/strings.xml you could declare this:<br /> 650 <code><resource><br /> 651 <string>id="@+id/styled_welcome_message">We 652 are <b><i>so</i></b> glad to see you.</string><br /> 653 </resources></code></li> 654 <li>To style text on the fly, or to add highlighting or more complex styling, 655 you must use the Spannable object as described next. </li> 656</ul> 657<p>To style text on the fly, you must make sure the TextView is using {@link android.text.Spannable} 658 storage for the text (this will always be true if the TextView is an EditText), 659 retrieve its text with {@link android.widget.TextView#getText}, and call {@link 660 android.text.Spannable#setSpan}, passing in a new style class from the {@link 661 android.text.style} package and the selection range. </p> 662<p>The following code snippet demonstrates creating a string with a highlighted section, 663 italic section, and bold section, and adding it to an EditText object. </p> 664<pre>// Get our EditText object. 665EditText vw = (EditText)findViewById(R.id.text); 666 667// Set the EditText's text. 668vw.setText("Italic, highlighted, bold."); 669 670// If this were just a TextView, we could do: 671// vw.setText("Italic, highlighted, bold.", TextView.BufferType.SPANNABLE); 672// to force it to use Spannable storage so styles can be attached. 673// Or we could specify that in the XML. 674 675// Get the EditText's internal text storage 676Spannable str = vw.getText(); 677 678// Create our span sections, and assign a format to each. 679str.setSpan(new StyleSpan(android.graphics.Typeface.ITALIC), 0, 7, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE); 680str.setSpan(new BackgroundColorSpan(0xFFFFFF00), 8, 19, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE); 681str.setSpan(new StyleSpan(android.graphics.Typeface.BOLD), 21, str.length() - 1, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE); 682</pre> 683 684<a name="querymap" id="querymap"></a><h2>Utilizing attributes in a Map query</h2> 685<p> 686When using a search intent to ask the Maps activity to search for something, the Maps activity responds to the following attributes in the optional context bundle: 687</p> 688<pre> 689 float "centerLatitude" default 0.0f 690 float "centerLongitude" default 0.0f 691 float "latitudeSpan" default 0.0f 692 float "longitudeSpan" default 0.0f 693 int "zoomLevel" default 10 694</pre> 695<p> 696This context information is used to center the search result in a particular area, and is equivalent to adjusting the Map activity to the described location and zoom level before issuing the query. 697</p> 698<p> 699If the latitudeSpan, longitudeSpan, and zoomLevel attributes are not consistent, then it is undefined which one takes precedence. 700</p> 701 702<a name="filelist" id="filelist"></a><h2>List of Files for an Android Application</h2> 703<p>The following list describes the structure and files of an Android application. 704 Many of these files can be built for you (or stubbed out) by the activitycreator 705 application shipped in the tools/ menu of the SDK. </p> 706<table width="100%" border="0"> 707 <tr> 708 <td width="28%" valign="top">MyApp/<br /></td> 709 <td width="72%" valign="top"> </td> 710 </tr> 711 <tr> 712 <td valign="top"> AndroidManifest.xml</td> 713 <td valign="top">(<em>required</em>) Advertises the screens that this application provides, 714 where they can be launched (from the main program menu or elsewhere), 715 any content providers it implements and what kind of data they handle, 716 where the implementation classes are, and other application-wide 717 information. Syntax details for this file are described in <a href="{@docRoot}guide/topics/manifest/manifest-intro.html">The AndroidManifest.xml File</a>.</td> 718 </tr> 719 <tr> 720 <td valign="top"> src/<br /> 721 /<em>myPackagePath</em>/.../<em>MyClass</em>.java</td> 722 <td valign="top">(<em>required</em>) This folder holds all the source code files for your 723 application, inside the appropriate package subfolders. </td> 724 </tr> 725 <tr> 726 <td valign="top"> res/</td> 727 <td valign="top">(<em>required</em>) This folder holds all the <em>resources</em> for 728 your application. Resources are external data files or description files 729 that are compiled into your code at build time. Files in different folders 730 are compiled differently, so you must put the proper resource into the 731 proper folder. (See <a href="{@docRoot}guide/topics/resources/resources-i18n.html">Resources</a> for details.)</td> 732 </tr> 733 <tr> 734 <td valign="top"> anim/<br /> 735 <em>animation1</em>.xml<br /> 736 <em>...</em></td> 737 <td valign="top">(<em>optional</em>) Holds any animation XML description files that the 738 application uses. The format of these files is described in <a href="{@docRoot}guide/topics/resources/resources-i18n.html">Resources</a>. </td> 739 </tr> 740 <tr> 741 <td valign="top"> drawable/<br /> 742 <em>some_picture</em>.png<br /> 743 <em>some_stretchable</em>.9.png<br /> 744 <em>some_background</em>.xml<br /> 745 ...</td> 746 <td valign="top">(<em>optional</em>) Zero or more files that will be compiled to {@link 747 android.graphics.drawable android.graphics.drawable} resources. Files 748 can be image files (png, gif, or other) or XML files describing other 749 graphics such as bitmaps, stretchable bitmaps, or gradients. Supported 750 bitmap file formats are PNG (preferred), JPG, and GIF (discouraged), 751 as well as the custom 9-patch stretchable bitmap format. These formats 752 are described in <a href="{@docRoot}guide/topics/resources/resources-i18n.html">Resources</a>. </td> 753 </tr> 754 <tr> 755 <td valign="top"> layout/<br /> 756 <em>screen_1_layout</em>.xml<br /> 757 ...<br /></td> 758 <td valign="top">(<em>optional</em>) Holds all the XML files describing screens or parts 759 of screens. Although you could create a screen in Java, defining them 760 in XML files is typically easier. A layout file is similar in concept 761 to an HTML file that describes the screen layout and components. See <a href="{@docRoot}guide/topics/ui/index.html">User Interface</a> for more information about designing screens, and <a href="{@docRoot}guide/topics/resources/available-resources.html#layoutresources">Available Resource Types</a> for the syntax of these files.</td> 762 </tr> 763 <tr> 764 <td valign="top"> values/<br /> 765 arrays<br /> 766 classes.xml<br /> 767 colors.xml<br /> 768 dimens.xml<br /> 769 strings.xml<br /> 770 styles.xml<br /> 771 values.xml<br /></td> 772 <td valign="top"><p>(<em>optional</em>) XML files describing additional resources 773 such as strings, colors, and styles. The naming, quantity, and number 774 of these files are not enforced--any XML file is compiled, but these 775 are the standard names given to these files. However, the syntax 776 of these files is prescribed by Android, and described in <a href="{@docRoot}guide/topics/resources/resources-i18n.html">Resources</a>. </p> 777 </td> 778 </tr> 779 <tr> 780 <td valign="top"> xml/</td> 781 <td valign="top">(<em>optional</em>) XML files that can be read at run time on the device. </td> 782 </tr> 783 <tr> 784 <td valign="top"> raw/</td> 785 <td valign="top">(<em>optional</em>) Any files to be copied directly to the device. </td> 786 </tr> 787</table> 788 789 790<a name="logging" ></a> 791<h2>Print Messages to a Log File</h2> 792 793<p>To write log messages from your application:</p> 794<ol><li>Import <code>android.util.Log</code>.</li> 795 <li>Use <code>Log.v()</code>, <code>Log.d()</code>, <code>Log.i()</code>, 796 <code>Log.w()</code>, or <code>Log.e()</code> to log messages. 797 (See the {@link android.util.Log} class.)<br/> E.g., 798 <code>Log.e(this.toString(), "error: " + err.toString())</code></li> 799 <li>Launch <a href="{@docRoot}guide/developing/tools/ddms.html">DDMS</a> from a terminal 800 by executing <code>ddms</code> in your Android SDK <code>/tools</code> path.</li> 801 <li>Run your application in the Android emulator.</li> 802 <li>From the DDMS application, select the emulator 803 (e.g., "emulator-5554") and click <b>Device > Run logcat...</b> 804 to view all the log data.</li> 805</ol> 806<p class="note"><strong>Note:</strong> If you are running Eclipse and 807encounter a warning about the VM debug port when opening DDMS, you can ignore it 808if you're only interested in logs. However, if you want to further inspect and 809control your processes from DDMS, then you should close Eclipse before launching DDMS so that 810it may use the VM debugging port.</p> 811 812 813