Survey
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
Android Basics Mobile Application Development Selected Topics – CPIT 490 30-Apr-17 Overview Review Android Activities Android Intents User Interface / Views User Notifications 2 Developing for Android Eclipse Android SDK Android Development Tools (ADT) Android Virtual Devices (AVD) & SDK Manager The Android Emulator Dalvik Debug Monitor Services (DDMS) The Android Debug Bridge (ADB) 3 Android Software Stack 4 Android Project Structure src/ - Java packages. Each package can have multiple .java files representing different classes. res/layout/ - XML files that specify the layout of each screen. main.xml defines the layout of the application. Default view is Layout view. res/values/ - XML files used as references by other files. res/drawable-hdpi/ , res/drawable-mdpi/ , and res/drawable-ldpi/ - high, medium, and low dots-per-inch resolution pictures. res/color, res/menu, res/anim assets/ - additional non-media files. Assets used by application. Ex. HTML, database, etc AndroidManifest.xml specifies the project to the Android OS. Permissions and other features are specified here. Auto-generated files (do not modify): gen/ contains auto-generated code. Class R.java generated by Android Asset Packaging Tool (aapt). ). If you delete R.java, it will auto-generated again. R.java is based on AndroidManifest.xml file. default.properties contains project settings. 5 Android Application Components i) Activity: Activity is a visual screen for interaction of user with the application. Depends upon design, an application may consists of one or more activities Fragments: "miniature" activities that could be grouped to form an activity ii) Views: The User interface of an Activities is build with widgets. iii) Service: Service do not have a visual interface, it runs in the back ground, like play back music and fetching data from the network. iv) Broadcast Receiver: Broadcast receiver receive broadcast announcements and response to them according to the situation. v) Content Provider: Content provider is a SQLite database, which supports the sharing and accessing of data among applications. vi) Intents: Asynchronous messages which allow the application to request functionality from other services or activities. vii) Others parts are Android widgets / Live Folders and Live Wallpapers. 6 Android Activity http://developer.android.com/reference/android/app/Activity An "activity" is an application component that provides a screen with which users can interact Activity is usually a single screen Implemented as a single class extending Activity Displays user interface controls (views) Reacts on user input / events An application typically consists of several activities Each screen is typically implemented by one activity Each activity can then start another activity (new screen) An activity may return a result to the previous activity "main" activity is presented to the user when launching the application for the first time. Each activity receives callbacks due to a change in its state during its lifecycle — whether the system is creating it, stopping it, resuming it, or destroying it. 7 Activity Lifecycle 8 Activity Lifecycle Foreground Lifetime is until onPause() Visible Lifetime is until onStop() Entire Lifetime is until onDestroy() Create an activity by extending Activity base class 9 Activity Example extends Activity base class UI from res/layout folder R.layout.main refers to main.xml AndroidManifest.xml must declare all activities in the application @string refers to strings.xml in res/values folder onCreate() is involved when the activity is loaded 10 Activity Callbacks public class Activity extends ApplicationContext { protected void onCreate(Bundle savedInstanceState); // Called when the activity is first created. Provides you with a Bundle containing the activity's previously frozen state, if there was one. Always followed by onStart(). protected void onStart(); // Called when the activity is becoming visible to the user. Followed by onResume() if the activity comes to the foreground, or onStop() if it becomes hidden. protected void onRestart(); // Called after your activity has been stopped, prior to it being started again. Always followed by onStart() 11 Activity Callbacks protected void onResume(); // Called when the activity will start interacting with the user. At this point your activity is at the top of the activity stack, with user input going to it. Always followed by onPause(). protected void onPause(); // Called when the system is about to start resuming a previous activity. Implementations of this method must be very quick because the next activity will not be resumed until this method returns. Followed by either onResume() or onStop(). protected void onStop(); // Called when the activity is no longer visible to the user. Followed by either onRestart() if this activity is coming back to interact with user, or onDestroy() if this activity is going away. protected void onDestroy(); // The final call you receive before your activity is destroyed. This can happen either because the activity is finishing or someone called finish() on it, or because the system is temporarily destroying this instance of the activity to save space. You can distinguish between these two scenarios with the isFinishing() method. } 12 Activity Life cycle Activity is destroyed when the back button is pressed. So, if you want to preserve the state, we need to store the information before the application is destroyed onPause() is called when the application is send to background or when the application is killed onCreate() is invoked when the activity is loaded for the first time onStart() and onResume() are invoked when an activity is started, either from background or newly started Use the onCreate() method to create and instantiate the objects that you will be using in your application Use the onResume() method to start any services or code that needs to run while your activity is in the foreground. Use the onPause() method to stop any services or code that does not need to run when your activity is not in the foreground. Use the onDestroy() method to free up resources before your activity is 13 destroyed. Utilizing Activity Lifecycle Functions Simple exercise to see the activity lifecycle in action each overridden function is explicit and a Toast command is added to show on screen when the function is entered Run it on an Android device and try various cases: Changing the screen orientation destroys and recreates the activity from scratch. Pressing the Home button pauses the activity, but does not destroy it. Pressing the Application icon might start a new instance of the activity, even if the old one was not destroyed. Letting the screen sleep pauses the activity and the screen awakening resumes it. (This is similar to taking an incoming phone call.) 14 Activity Lifecycle Samples Turn Display onCreate(null) -> onStart -> onResume() -> [Turn Display] > onSaveInstanceState() -> onPause() -> onStop() -> onDestroy() -> onCreate() -> onStart() -> onRestoreInstanceState() -> onResume() Home onCreate(null) -> onStart -> onResume() -> [Home Button] > onSaveInstanceState() -> onPause() -> onStop() -> [Start App] > onRestart() -> onStart() -> onResume() Phone Call Interrupt onCreate(null) -> onStart -> onResume() -> [Phone Call] > onSaveInstanceState() -> onPause() -> onStop() -> [Hang Up or press Back] > onRestart() -> onStart() -> onResume() 15 Notes on Activity Starting Activity: void startActivity (Intent intent) void startActivityForResult (Intent intent, int requestCode) void onActivityResult (int requestCode, int resultCode, Intent data) Shutting Down Activity: void finish () void finishActivity (int requestCode) Saving Activity Status void onSaveInstanceState (Bundle outState) void onRestoreInstanceState (Bundle savedInstanceState) Activity A starts Activity B: A's onPause() B's onCreate() , onStart() , and onResume() (Activity B now has user focus.) A’s onStop() , if A is no longer visible 16 Starting Activity 17 Saving Activity’s State 18 Back Stack Tasks and Activities Multiple Tasks Multiple Activity Instances 19 Activity and AndroidManifest.xml Any new activity must be defined in AndroidManifest.xml file 20 AndroidManifest.xml and main.xml versionCode: used to indicate the version number of the application versionNumber: Represented as <major>.<minor> version numbers. This is displayed to the user Minimum, target and maximum SDK versions are specified here Icon of the application is provided via @drawable, which refers to the res/drawable folder The name of the main activity is provided. Also, the package name is provided android.intent.action.MAIN means that the current activity is the first activity that will be loaded when the application runs Under intent-filter <action android:name="a.b.c.d" /> means this specific activity could be invoked using a.b.c.d as the name android:windowSoftInputMode="stateHidden" is used to disable soft keyboard from appearing automatically for EditText main.xml android:onClick="onClick" is used to say which method to call when the view is clicked. The one in the quotes indicate the name of the method. This method is to be implemented in the java program. 21 Notes on Activity Contd… Killing an activity does not remove the application from memory, even if the application has only one activity Context class is used to provide references to your application. Activity class is a subclass of Context class. To draw progress dialogs, you could use progressDialog class. Applying dialog themes to an activity (in AndroidManifest.xml) (BAAD Pg 41) android:theme="@android:style/Theme.Dialog"> Hides a feature (in *.java file) – Hide the title based on a state (BAAD Pg 42) import android.view.Window; //---hides the title bar-- requestWindowFeature(Window.FEATURE_NO_TITLE); Dialog box (BAAD Pg 42) Creating multiple activities and linking them using Intent (BAAD Pg 54) Passing parameters through intents (BAAD Pg 63) 22 Intents http://developer.android.com/reference/android/content/Intent.html Intents are used as a message-passing mechanism within your application and between applications. Intents are used to call built-in applications like Map, Browser, etc. Explicit start Activity/Service using its class name Start Activity/Service for an action with specific data Broadcast that an event has occurred Consists of Component name (name of component/activity to handle the intent) Action to be performed (MAIN / VIEW / EDIT / PICK / DELETE) Data to act on (expressed as URI) or Bundle Categories Extras (primitives / Strings / Serializable) Flags 23 Component Name Field Specifies the name of the component (name of the activity if the component is activity) that should handle the intent Class name of the target component (for example "FirstActivity") <activity android:name =".FirstActivity" android:labe l="@string/app_name"> <intent-filter > <action android:name = "edu.odu.examples.IntentActivity" /> <category android:name = "android.intent.category.LAUNCHER" /> </intent-filter > </activity > Setting component name is optional Explicit Intent: If it is set, the Intent object is delivered to an instance of the designated class. Intent intent = new Intent (this, FirstActivity.class); Implicit Intent: If it is not set, Android uses other information (i.e., action field) in the Intent object to locate a suitable target - this is called "intent resolution" Intent intent = new Intent ("edu.odu.examples.IntentActivity"); 24 Launching Activity Intent Invocation Launch new activity (without receiving a result) Launch new activity and expect result requestCode is simply an integer value that identifies an activity you are calling. This is to used to identify the activity that returns For example, you may be calling multiple activities at the same time, and some activities may not return immediately (for example, waiting for a reply from a server) requestCode of -1 is like startActivity(intent) When activity exits, onActivityResult() method is called with given requestCode (int > 0) onActivityResult(int requestCode, int resultCode, Intent result) 25 Intents and Intent Filters Intent Filters Description of what intents an activity can handle Activities publish their intent filters in a manifest file <intent-filter > <action android:name="android.intent.action.VIEW"/> <category android:name="android.intent.category.DEFAULT"/> <category android:name="android.intent.category.BROWSABLE"/> <data android:scheme="geo"/> </intent-filter> Upon invocation of startActivity(intent) the system looks at the intent filters of all installed applications Candidate activity that owns the filter must pass matching tests for action, category, and data fields http://developer.android.com/guide/topics/intents/intents-filters.html 26 .MAIN Action & .LAUNCHER Category Activities that can initiate applications have filters with "android.intent.action.MAIN" specified as the action This is a way an application gets started fresh, without a reference to any particular data. If they are to be represented in the application launcher, they also specify the "android.intent.category.LAUNCHER" category: <intent-filter . . . > <action android:name="code android.intent.action.MAIN" /> <category android:name="code android.intent.category.LAUNCHER" /> </intent-filter> The Android system populates the application launcher by finding all the activities with intent filters that specify the "android.intent.action.MAIN" action and "android.intent.category.LAUNCHER" category. It then displays the icons and labels of those activities in the launcher. 27 Action Field In Android, intents usually come in pairs: action and data. The action describes what is to be performed, such as editing an item, viewing the content of an item, and so on. The data specifies what is affected, such as a person in the Contacts database. The data is specified as an Uri object. Intent Resolution: Android OS looks for the activities which could satisfy the given request. For ex., when we specify Intent i = new Intent("android.intent.action.VIEW"); the appropriate activity should be used to view. A string naming the action to be performed The Intent class defines a number of predefined action constants, including ACTION_CALL, ACTION_EDIT, ACTION_MAIN, ACTION_SYNC, ACTION_BATTERY_LOW, etc. You can also define your own action strings for activating the components in your application The action largely determines how the rest of the intent is structured - particularly the data and extras fields - much as a method name determines a set of arguments and a return value. 28 Intent Actions Note that Actions’ "Constant" could be replaced with an equivalent String constant. e.g.,: ACTION_CALL = "android.intent.action.CALL" 29 Data Field The URI of the data to be acted on and the MIME type of that data. Use Uri.parse to convert string to an uri object Different actions are paired with different kinds of data specifications. If the action field is ACTION_EDIT, the data field would contain the URI of the document to be displayed for editing. If the action is ACTION_CALL, the data field would be a tel: URI with the number to call. If the action is ACTION_VIEW and the data field is an http: URI, the receiving activity would be called upon to download and display whatever data the URI refers to. Examples of Action/Data Pairs ACTION_VIEW content://contacts/people/ -- Display a list of people to browse through. ACTION_VIEW content://contacts/people/1 – Display information about person whose id is "1". ACTION_DIAL content://contacts/people/1 – Display the phone dialer with the person filled in. ACTION_VIEW tel:123 -- Display the phone dialer with the given number filled in. ACTION_DIAL tel:123 -- Dial the phone dialer with the given number filled in. 30 Example of Actions Starting Activity: void startActivity (Intent intent) Intent i = new Intent (this, OtherActivity.class); startActivity(i); void startActivityForResult (Intent intent, int requestCode) void onActivityResult (int requestCode, int resultCode, Intent data) Shutting Down Activity: void finish() Intent intent = new Intent (this, FirstActivity.class); startActivity (intent); 31 Notes on Activity and Intents use the putExtra() method of an Intent object to add a name/value pair Two parameters in putExtra(): one of type string and one of type integer you can also create a Bundle object and then attach it using the putExtras() method getIntent() method is used to get Intent object When a fragment is being created, it goes through the following states: onAttach(), onCreate(), onCreateView(), onActivityCreated() When the fragment becomes visible, it goes through these states: onStart(), onResume() When the fragment goes into the background mode, it goes through these states: onPause(), onStop() When the fragment is destroyed (when the activity it is currently hosted in is destroyed), it goes through the following states: onPause(), onStop(), onDestroyView(), onDestroy(), onDetach() Like activities, you can restore an instance of a fragment using a Bundle object, in the following states: onCreate(), onCreateView(), onActivityCreated() 32 Notes on Activity and Intents onAttached() — Called when the fragment has been associated with the activity onCreateView() — Called to create the view for the fragment onActivityCreated() — Called when the activity’s onCreate() method has been returned onDestroyView() — Called when the fragment’s view is being removed onDetach() — Called when the fragment is detached from the activity <category android:name="android.intent.category.DEFAULT" /> should be used if you want an activity to be invoked by others Intents can be specified with categories in AndrodManifest.xml file. You could specify the category in the code using addCategory(). If no category is specified in the java code, the DEFAULT category is invoked. If the category specified in the java code is not matched, then a runtime exception is generated and the activity will not be started Creating multiple activities and linking them using Intent (BAAD Pg 54) Passing parameters through intents (BAAD Pg 63) 33 Notes on Activity and Intents Using intents to start a second activity Remember to add new Activity(s) to AndroidManifest.xml ! Intent intent = new Intent(Context packageContext, Class<?> class); packageContext = the activity we’re coming from Class: the Activity in our app we’re going to Intent intent = new Intent(this, AnotherActivity.class); startActivity(i); Requesting and starting another application’s activity Intent intent = new Intent(<action>, <data>); ACTION_VIEW, ACTION_EDIT, ACTION_DIAL scheme://host/data/segments Intent intent = new Intent(Intent.ACTION_DIAL, Uri.parse(“tel:1234567890”)); 34 Notes on Activity and Intents Activity Results startActivityForResult(intent) allows us to “return” data to the calling Activity onActivityResult(int requestCode, int resultCode, Intent data); requestCode: unique integer to determine what Activity returned resultCode: RESULT_OK, RESULT_CANCELED data: Intent to receive additional data setResult(int resultCode, Intent data); resultCode: RESULT_OK, RESULT_CANCELED data: Intent to pass additional data finish() pops from stack and sends control back to previous Activity 35 Notes on Activity and Intents Bundle objects store key and value pairs via the put<type> methods and get<type> methods Basic data types: boolean, byte, char, double, float, int, long, etc. Non-primitives: String, Serializable, Arrays Can get size() and keySet() intent.putExtras(Bundle bundle); Associate a bundle with an intent getIntent().getExtras(); Get bundle associated with an intent intent.putExtra(String key, value); intent.getExtra(String key); 36 Fragments Fragments are mini-activities Fragments contain views as like Activities Fragments are contained within an activity. Fragments could be dynamically added or removed from the activity the FragmentManager class is used to add fragments to an activity. the FragmentTransaction class is used to perform fragment transactions in your activity (such as add, remove or replace) the WindowManager to determine whether the device is currently in portrait mode or landscape mode android.R.id.content refers to the content view of the activity commit() method is to make changes to effect Add frames at run-time (BAAD Pg 74) When an activity goes background, it is moved to back state automatically. For fragments, moving to back state has to be done using addToBackStack(). Call inbuilt applications using Intent (BAAD Pg 85) 37 Fragments Three subclasses of fragments: ListFragment, DialogFragment, and PreferenceFragment A list fragment is a fragment that contains a ListView, displaying a list of items from a data source such as an array or a Cursor In the onCreate() event, you use the setListAdapter() method to programmatically fill the ListView with the content of the array The ArrayAdapter object manages the array of strings that will be displayed by the ListView 38 User Interfaces and Views Views are loaded from res/layout/main.xml file in the onCreate() method handler in your Activity class, using the setContentView() method of the Activity class Sometimes, you need to code the views in the java code itself because you need to generate the views at runtime. Ex. Games http://developer.android.com/guide/topics/ui/index.html Views and View Groups Views (Widgets) Layouts Events Menus Dialogs Styles and themes 39 Fundamental UI Design Views Visual interface element (controls or widgets) A view derives from the base class android.view.View ViewGroup Contains multiple widgets. Layouts inherit the ViewGroup class. Ex LinearLayout, AbsoluteLayout (deprecated), TableLayout, FrameLayout, etc A ViewGroup derives from the base class android.view.ViewGroup Activities Screen being displayed to the user. Assign a View or layout to an Activity 40 Layouts http://developer.android.com/guide/topics/ui/declaring-layout.html Layout contains Views FrameLayout Each child view is in reference to the top left corner. Use if only one View in screen at a time. LinearLayout Views in line, either vertically or horizontally. Single column or single row. Elements appear in order they are specified in the file RelativeLayout Define positions of each other child view relative to each other and screen boundaries TableLayout Rows and Columns Web View Display web pages 41 Layout Examples Linear Layout Relative Layout Grid Layout Tab Layout dp or dip — Density-independent pixel. 1 dp is equivalent to one pixel on a 160 dpi screen. Recommended for layout dimensions. sp — Scale-independent pixel. This is similar to dp and is recommended for specifying font sizes. pt — Point. A point is defined to be 1/72 of an inch, based on the physical screen size. px — Pixel. Corresponds to actual pixels on the screen. Not recommended. 42 Android Specifications Nexus S has a 4-inch screen (diagonally), with a screen width of 2.04 inches. Its resolution is 480 (width) 800 (height) pixels. With 480 pixels spread across a width of 2.04 inches, the result is a pixel density of about 235 dots per inch (dpi). The pixel density of a screen varies according to screen size and resolution. Android defines and recognizes four screen densities: Low density (ldpi) — 120 dpi Medium density (mdpi) — 160 dpi High density (hdpi) — 240 dpi Extra High density (xhdpi) — 320 dpi Nexus S is in hdpi as its dpi is close to 240 dpi. Actual pixels = dp * (dpi / 160), where dpi is either 120, 160, 240, or 320. 43 Defining Layout Using the dp unit ensures that your views are always displayed in the right proportion regardless of the screen density Portrait mode: res/layout/main.xml Landscape mode: res/layout-land/main.xml The default orientation layout is horizontal Each Activity can have it's own layout 44 Handling Orientation Changes Anchoring Anchor your views to the corners (edges of the screen) Achieved using RelativeLayout using options like android:layout_alignParentTop="true" android:layout_alignParentRight="true" Resizing and repositioning Resizing every view according to the orientation Write two main.xml files. One in res/layout folder and the other in res/layout-land folder Changing orientation kills an activity and recreates it. Only views that are named with android:id will persist orientation changes When an activity is killed, onPause() and onSaveInstanceState() methods are invoked Unlike the onPause() method, the onSaveInstanceState() method is not fired when an activity is being unloaded from the stack (such as when the user pressed the back button), because there is no need to restore its state later Preserve the state of your activity, such as using a database, internal or external file storage, and so on 45 Handling Orientation Changes Easier way to save state: onSaveInstanceState() method provides a Bundle object as an argument so that you can use it to save your activity’s state Information can only be saved in Bundle object and thus complex data structures cannot be stored @Override public void onSaveInstanceState(Bundle outState) { //---save whatever you need to persist--outState.putString(“ID”, “1234567890”); super.onSaveInstanceState(outState); } @ Override public void onRestoreInstanceState(Bundle savedInstanceState) { super.onRestoreInstanceState(savedInstanceState); //---retrieve the information persisted earlier--String ID = savedInstanceState.getString(“ID”); } 46 Handling Orientation Changes onRetainNonConfigurationInstance() method is fired when an activity is about to be destroyed due to a configuration change (such as a change in screen orientation, keyboard availability, etc.) @Override public Object onRetainNonConfigurationInstance() { //---save whatever you want here; it takes in an Object type--return(“Some text to preserve”); } To extract the saved data, you can extract it in the onCreate() method, using the getLastNonConfigurationInstance() method: @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.main); Log.d(“StateInfo”, “onCreate”); String str = (String) getLastNonConfigurationInstance(); } 47 Detecting Orientation Changes Use WindowManager class //---get the current display info--WindowManager wm = getWindowManager(); Display d = wm.getDefaultDisplay(); if (d.getWidth() > d.getHeight()) { //---landscape mode--Log.d(“Orientation”, “Landscape mode”); } else { //---portrait mode--Log.d(“Orientation”, “Portrait mode”); } Also, you could add android:screenOrientation=”landscape” to activity in AndroidManifest.xml If you wish to keep your application displayed in certain orientation, specify the below in onCreate() //---change to landscape mode--setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); For Portrait: ActivityInfo.SCREEN_ORIENTATION_PORTRAIT 48 Example of Layout fill_parent fills the entire width or height of the parent wrap_content make the width or height to the content 49 Common Attributes Refresh your Java programming The layout_gravity attribute indicates the positions the views should gravitate towards, while the layout_weight attribute specifies the distribution of available space 50 Example of Linear Layout <?xml version="1.0" encoding="utf-8"?> <LinearLayout android:layout_width="fill_parent" android:layout_height="fill_parent" xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:stretchcolumns="*" > <Button android:layout_width="100px" android:layout_height="wrap_content" android:text="Button A" android:layout_weight="0.1" /> <Button android:layout_width="100px" android:layout_height="wrap_content" android:text="Button B" android:layout_gravity="right" android:layout_weight="0.3" /> <EditText android:layout_width="fill_parent" android:layout_height="wrap_content" android:textSize="18sp" android:layout_weight="0.6" /> </LinearLayout> 51 Example of Table Layout <?xml version="1.0" encoding="utf-8"?> <TableLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_height="fill_parent" android:layout_width="fill_parent" android:background="#646464"> <TableRow> <TextView android:text="E-mail:" android:width="120px" /> <EditText android:id="@+id/email" android:width="200px" /> </TableRow> <TableRow> <TextView android:text="Password:" /> <EditText android:id="@+id/password" android:password="true" /> </TableRow> <TableRow> <TextView /> <CheckBox android:id="@+id/rememberMe" android:text="Remember Me" /> </TableRow> <TableRow> <Button android:id="@+id/signIn" android:text="Log In" android:layout_span="2" /> </TableRow> </TableLayout> 52 Example of Relative Layout <?xml version="1.0" encoding="utf-8"?> <RelativeLayout android:id="@+id/RLayout" android:layout_width="fill_parent" android:layout_height="fill_parent" xmlns:android="http://schemas.android.com/apk/res/android" > <TextView android:id="@+id/lblComments" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="Comments" android:layout_alignParentTop="true" android:layout_alignParentLeft="true" /> <EditText android:id="@+id/txtComments" android:layout_width="fill_parent" android:layout_height="170px" android:textSize="18sp" android:layout_alignLeft="@+id/lblComments" android:layout_below="@+id/lblComments" android:layout_centerHorizontal="true" /> <Button android:id="@+id/btnSave" android:layout_width="125px" android:layout_height="wrap_content" android:text="Save" android:layout_below="@+id/txtComments" android:layout_alignRight="@+id/txtComments" /> <Button android:id="@+id/btnCancel" android:layout_width="124px" android:layout_height="wrap_content" android:text="Cancel" android:layout_below="@+id/txtComments" android:layout_alignLeft="@+id/txtComments" /> </RelativeLayout> 53 Example of Frame Layout The FrameLayout is a placeholder on screen that you can use to display a single view <?xml version="1.0" encoding="utf-8"?> <RelativeLayout android:id="@+id/RLayout" android:layout_width="fill_parent" android:layout_height="fill_parent" xmlns:android="http://schemas.android.com/apk/res/android" > <TextView android:id="@+id/lblComments" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="Hello, Android!" android:layout_alignParentTop="true" android:layout_alignParentLeft="true" /> <FrameLayout android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignLeft="@+id/lblComments" android:layout_below="@+id/lblComments" android:layout_centerHorizontal="true" > <ImageView android:src = "@drawable/droid" android:layout_width="wrap_content" android:layout_height="wrap_content" /> </FrameLayout> </RelativeLayout> 54 ScrollView A ScrollView is a special type of FrameLayout in that it enables users to scroll through a list of views that occupy more space than the physical display The ScrollView can contain only one child view or ViewGroup, which normally is a LinearLayout The ListView is designed for showing a list of related information and is optimized for dealing with large lists. So, don’t use ListView with ScrollView <ScrollView android:layout_width=”fill_parent” android:layout_height=”fill_parent” xmlns:android=”http://schemas.android.com/apk/res/android” > <LinearLayout android:layout_width=”fill_parent” android:layout_height=”wrap_content” android:orientation=”vertical” android:focusable=”true” android:focusableInTouchMode=”true”> <Button android:id=”@+id/button1” android:layout_width=”fill_parent” android:layout_height=”wrap_content” android:text=”Button 1” /> <Button android:id=”@+id/button2” android:layout_width=”fill_parent” android:layout_height=”wrap_content” android:text=”Button 2” /> <Button android:id=”@+id/button3” android:layout_width=”fill_parent” android:layout_height=”wrap_content” android:text=”Button 3” /> <EditText android:id=”@+id/txt” android:layout_width=”fill_parent” android:layout_height=”600dp” /> <Button android:id=”@+id/button4” android:layout_width=”fill_parent” android:layout_height=”wrap_content” android:text=”Button 4” /> <Button android:id=”@+id/button5” android:layout_width=”fill_parent” android:layout_height=”wrap_content” android:text=”Button 5” /> </LinearLayout> </ScrollView> 55 Defining Styles Multiple Buttons Define style only once! ... <TableRow android:id="@+id/TableRow01" android:layout_weight="0.2" android:layout_width="fill_parent" android:layout_height="wrap_content"> <Button android:id="@+id/Button07" style="@style/mybutton" android:text="7" /> <Button android:id="@+id/Button08" style="@style/mybutton" android:text="8" /> <Button android:id="@+id/Button09" style="@style/mybutton" android:text="9" /> <Button android:id="@+id/ButtonDivide" style="@style/mybutton" android:text="/" /> </TableRow> … 56 Styles in values/styles.xml <?xml version="1.0" encoding="utf-8"?> <resources> <style name="mybutton" parent="@android:style/TextAppearance"> <item name="android:textSize">30sp</item> <item name="android:textColor">#000000</item> <item name="android:layout_width">fill_parent</item> <item name="android:layout_height">fill_parent</item> <item name="android:layout_weight">1</item> </style> </resources> 57 Styles and Themes Way of building and formatting layout to your app Style has formatting attributes to several elements The format for the value of the style attribute is as follows: ?[package:][type:]name Theme has formatting attributes to all activities Create the theme in xml (styles.xml) Apply the theme in manifest To hide the action bar, add android:theme="@android:style/Theme.Holo.NoActionBar" to AndroidManifest.xml Hide action bar programmatically import android.app.ActionBar; ActionBar actionBar = getActionBar(); actionBar.hide(); //actionBar.show(); //---show it again--58 ActionBar To add a home button at the ActionBar and move to the main activity when it is clicked. case android.R.id.home: Toast.makeText(this, “You clicked on the Application icon”, Toast.LENGTH_LONG).show(); Intent i = new Intent(this, MyActionBarActivity.class); i.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); startActivity(i); return true; The Intent.FLAG_ACTIVITY_CLEAR_TOP flag ensures that the series of activities in the back stack is cleared when the user clicks the application icon on the Action Bar. This way, if the user clicks the back button, the other activities in the application do not appear again. 59 ProgressBar Add ProgressBar in main.xml <ProgressBar android:id=”@+id/progressbar” android:layout_width=”wrap_content” android:layout_height=”wrap_content” style=”@android:style/Widget.ProgressBar.Horizontal” /> To display the progress, call its setProgress() method, passing in an integer indicating its progress Various ProgressBar styles: Widget.ProgressBar.Horizontal, Widget.ProgressBar.Small, Widget.ProgressBar.Large, Widget.ProgressBar.Inverse, Widget.ProgressBar.Small.Inverse, Widget.ProgressBar.Large.Inverse 60 UI Programmatically Comment setContentView(R.layout.main); in onCreate() Specify the layout parameters for the views using LayoutParams object //---param for views-- LayoutParams params = new LinearLayout.LayoutParams(LayoutParams.FILL_PARENT,LayoutParams.WRA P_CONTENT); The respective layout object should also be created LinearLayout layout = new LinearLayout(this); layout.setOrientation(LinearLayout.VERTICAL); Create TextView and Button and add them to the layout object, using addView() TextView tv = new TextView(this); Button btn = new Button(this); layout.addView(tv); layout.addView(btn); Create the parameters to be used by the layout Add the layout to the activity: this.addContentView(layout, layoutParam); 61 Views (Input Controls/Widgets) TextView Label EditText Editable text Button Standard push button CheckBox Standard checkbox RadioButton Standard radio button ListView View group that manages a group of Views. Spinner TextView associated with ListView. Let's you select an item from a list. 62 Other Views and Widgets Widget and Other View http://developer.android.com/resources/tutorials/views/index. html Package android.widget http://developer.android.com/reference/android/widget/packa ge-summary.html view - API Demos (Sample Code) http://developer.android.com/resources/samples/ApiDemos/sr c/com/example/android/apis/view/index.html 63 Event Listener (Input Events) An interface, in the View class, that contains a single callback method Called by the Android framework when the View is triggered Multiple EventListeners (Interfaces): View.OnClickListener - onClick() View.OnLongClickListener - onLongClick() View.OnFocusChangeListener - onFocusChange() View.OnKeyListener - onKey() View.OnTouchListener - onTouch() View.OnCreateContextMenuListener - onCreateContextMenu() When a menu item is selected, onOptionsItemSelected() method is called The Action Bar populates its action items by calling the onCreateOptionsMenu() method of an activity To set a menu in the action bar, use setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM) 64 Event Listener (Input Events) The onCheckedChanged() method can be used with RadioButton and ToggleButton. CheckBox checkBox = (CheckBox) findViewById(R.id.chkAutosave); checkBox.setOnClickListener(new View.OnClickListener() { public void onClick(View v) { if (((CheckBox)v).isChecked()) DisplayToast("CheckBox is checked"); else DisplayToast("CheckBox is unchecked"); } }); //---RadioButton--RadioGroup radioGroup = (RadioGroup) findViewById(R.id.rdbGp1); radioGroup.setOnCheckedChangeListener(new OnCheckedChangeListener() { public void onCheckedChanged(RadioGroup group, int checkedId) { RadioButton rb1 = (RadioButton) findViewById(R.id.rdb1); if (rb1.isChecked()) { DisplayToast("Option 1 checked!"); } else { DisplayToast("Option 2 checked!"); } } }); 65 UI Notifications onKeyDown — Called when a key was pressed and not handled by any of the views contained within the activity onKeyUp — Called when a key was released and not handled by any of the views contained within the activity onMenuItemSelected — Called when a panel’s menu item has been selected by the user onMenuOpened — Called when a panel’s menu is opened by the user 66 Example: onClick() for Button view public class ExampleActivity extends Activity implements OnClickListener { protected void onCreate (Bundle savedValues) { ... Button button = (Button) findViewById(R.id.button_1); button.setOnClickListener(this); } // Implement the OnClickListener callback public void onClick(View v) { switch (v.getId()) { case R.id.button_1: // do action when the button is clicked break; // handle more buttons in the activity } } ... } 67 Views with images Images could be brought into views using ImageView, Gallery, ImageSwitcher, GridView The Gallery is a view that shows items (such as images) in a center-locked, horizontal scrolling list The GridView shows items in a two-dimensional scrolling grid. You can use the GridView together with an ImageView to display a series of images ImageAdapter class (which extends the BaseAdapter class) is used to bind the Gallery view with a series of ImageView views. The BaseAdapter class acts as a bridge between an AdapterView and the data source that feeds data into it. Examples of AdapterViews are: ListView, GridView, Spinner, Gallery Subclasses of the BaseAdapter class: ListAdapter, ArrayAdapter, CursorAdapter, SpinnerAdapter 68 Menus Options Menu Compact menu bottom of the screen Information on current activity Context Menu Tap and hold on an element Information about particular view Popup Menu List of items based on the current view 69 Options Menus // The onCreateOptionsMenu() method is called when the MENU button is pressed. // When a menu item is selected, the onOptionsItemSelected() method is called public class MenuExample extends Activity { @Override public void onCreate(Bundle savedInstanceState) { ... } // Modify menu items dynamically. Disable/enable menu items. @Override public boolean onPrepareOptionsMenu(Menu menu) { ... } // Create your menu here @Override public boolean onCreateOptionsMenu(Menu menu) { ... } // When menu item is selected @Override public boolean onOptionsItemSelected(MenuItem item) { ... } } 70 Creating Menus in XML (res/menu/menu.xml) Creating a Menu Resource <? xml version = "1.0" encoding = "utf-8" ?> <menu xmlns:android = "http://schemas.android.com/apk/res/android" > <item android:id = "@+id/new_game" android:icon = "@drawable/ic_new_game" android:title = "@string/new_game" /> <item android:id = "@+id/help" android:icon = "@drawable/ic_help" android:title = "@string/help" /> </menu> Inflating a Menu Resource @Override public boolean onCreateOptionsMenu(Menu menu) { super.onCreateOptionsMenu(menu) ; MenuInflater inflater = getMenuInflater (); inflater.inflate(R.menu.game_menu, menu ); return true ; } 71 Responding to Menu Selection @Override public boolean onOptionsItemSelected (MenuItem item) { // Handle item selection switch(item.getItemId()) { case R.id.new_game : newGame(); return true ; case R.id.help : showHelp(); return true ; default: return super.onOptionsItemSelected(item); } } 72 Changing Menu Dynamically @Override public boolean onPrepareOptionsMenu(Menu menu){ super.onPrepareOptionsMenu(menu); MenuItem menuItem1 = menu.findItem(R.id.new_game); menuItem1.setEnabled(false); MenuItem menuItem2 = menu.getItem(0); menuItem2.setEnabled(false); return true; } 73 Submenu A sub menu can be added within any menu <? xml version="1.0" encoding="utf-8"?> <menu xmlns:android = "http://schemas.android.com/apk/res/android" > <item android:id = "@+id/file" android:icon = "@drawable/file" android:title = "@string/file" > <!-- "file" submenu --> <menu> <item android:id = "@+id/create_new" android:title = "@string/create_new" /> <item android:id = "@+id/open" android:title = "@string/open" /> </menu> </item> </menu> 74 Creating Menus in Java public class MenuExample extends Activity { // You can increment this for additional menuitems static final private int MENU_ITEM1 = Menu.FIRST; static final private int MENU_ITEM2 = Menu.FIRST + 1; // Create your menu here @Override public boolean onCreateOptionsMenu(Menu menu) { super.onCreateOptionsMenu(menu); // Specify group value to separate Menu Items for batch processing and // ordering. NONE = No group int groupId = Menu.NONE; // Unique identifier for each menu item (used for event handling) int menuItemId1 = MENU_ITEM1; int menuItemId2 = MENU_ITEM2; // Order value. Menu.NONE = I don't care int menuItemOrder = Menu.NONE; // Menu Text int menuItemText1 = R.string.menu_item1; int menuItemText2 = R.string.menu_item2; menu.add(groupId, menuItemId1, menuItemOrder, menuItemText1); menu.add(groupId, menuItemId2, menuItemOrder, menuItemText2); // groupId — The group identifier that the menu item should be part of. Use 0 if an item is not in a Group; itemId — A unique item ID; order — The order in which the item should be displayed; title — The text to display for the menu item; setAlphabeticShortcut() method can assign shortcut key to menu item return true; } } 75 Context Menu Context Menu = Long press setOnCreateContextMenuListener() is used to add context menu for an activity Override two methods on a Activity onCreateContextMenu(): Called when a user taps and holds the button onContextItemSelected(): Called when an item inside the context menu is selected Register the context menu to the view registerForContextMenu(view) For details on menu, and other resources: http://developer.android.com/guide/topics/resources/availableresources.html 76 Example public class MyContextMenu extends Activity { private TextView tv; @Override public void onCreate(Bundle savedInstanceState) { } @Override public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) { } @Override public boolean onContextItemSelected(MenuItem item) { } } 77 OnCreate @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); tv = new TextView(this); tv.setText("Context Menu!") ; registerForContextMenu(tv) ; //or //tv.setOnCreatContextMenuListener(this); setContentView(tv); } 78 OnCreateContextMenu @Override public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) { super.onCreateContextMenu(menu, v, menuInfo); if (v == tv) { MenuInflater inflater = getMenuInflater(); inflater.inflate(R.menu.mymenu, menu); } } 79 OnContextItemSelected @Override public boolean onContextItemSelected(MenuItem item) { super.onContextItemSelected(item) ; switch(item.getItemId()){ case R.id.a: Toast.makeText (this, "A", 1000).show(); return true; case R.id.b: Toast.makeText (this, "B", 1000).show(); return true; } return false; } 80 Menus – Summary Described in XML, stored in res/menu <menu> has many <item> children Accessed like other resources (R.menu.<filename>) onCreateOptionsMenu(Menu menu) User presses menu button on device onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) User holds down a view (right-clicking/long press) Need to registerForContextMenu(View v) onOptionsItemSelected(MenuItem item) User selects an option from the menu coming from the menu button onContextItemSelected(MenuItem item) User selected an option from a context menu Item.getItemId() Gets ID of selected item 81 Menus – Summary <item> elements can also contain other <menu> items! When <item> is selected, a submenu will open as a context menu 82 Other views For Clock view, in main.xml: <AnalogClock android:layout_width=”wrap_content” android:layout_height=”wrap_content” /> <DigitalClock android:layout_width=”wrap_content” android:layout_height=”wrap_content” /> WebView: Embed a web browser in your activity Handle website redirects within the application itself without opening the Browser application using shouldOverrideUrlLoading() method Dynamic loading of HTML is done using loadUrl(file:///) 83 User Notification Toast Notification Brief message Status Bar Notification Persistent reminder Dialog Notification Activity-related notification 84 User Notification Toast appears and disappears in few seconds. Thus, it is better to use Notifications A PendingIntent object helps you to perform an action on your application’s behalf, often at a later time, regardless of whether your application is running or not. The getActivity() method retrieves a PendingIntent object and you set it using the following arguments: context — Application context request code — Request code for the intent intent — The intent for launching the target activity flags — The flags in which the activity is to be launched 85 Toast Toast.makeText(this, "Reset", 1000).show(); 86 Status Bar Notification Adds an icon to the system's status bar Expanded message in the notification window Optional ticker-text message Highly configurable If your app is working in the background, give status bar notifications 87 The Basics Usually a Service is launching the status bar notification You must use two classes: Notification and NotificationManager Instance of Notification should have all the information about the notification (e.g., icon, the expanded message) NotificationManager is an Android system that executes and manages all the notifications You don't instantiate NotificationManager 88 Get Reference to NotificationManager String ref = Context.NOTIFICATION_SERVICE; NotificationManager mNotificationManager = (NotificationManager) getSystemService(ref); 89 Instantiate the Notification Notification notification = new Notification(R.drawable.notify_icon, "Hello", System.currentTimeMillis()); 90 Define the Notification’s expanded message and Intent Refresh your Java programming // Communication between status bar and this Activity Intent notificationIntent = new Intent(this, MyContextMenu.class); PendingIntent contentIntent = PendingIntent.getActivity(this, 0, notificationIntent, 0); notification.setLatestEventInfo(this, "My notification", "Hello World!", contentIntent); 91 Pass the Notification to the NotificationManager mNotificationManager.notify(1, notification); 92 Status Bar Notification String ns = NOTIFICATION_SERVICE; NotificationManager mNotificationManager = (NotificationManager) getSystemService(ns); int icon = R.drawable.icon; CharSequence tickerText = "Calculator Reseted!"; long when = System.currentTimeMillis(); Notification notification = new Notification(icon, tickerText, when); Intent notificationIntent = new Intent(this, MyActivity.class); PendingIntent contentIntent = PendingIntent.getActivity(this, 0, notificationIntent, 0); notification.setLatestEventInfo(this, "My Calculator", "The calculator was reseted!", contentIntent); mNotificationManager.notify(1, notification); http://developer.android.com/guide/topics/ui/notifiers/notifications.html 93 Dialogs AlertDialog ProgressDialog DatePickerDialog TimePickerDialog 94 Example of AlertDialog AlertDialog.Builder builder = new AlertDialog.Builder(this); builder.setMessage("Hello!") .setPositiveButton("Ok", new DialogInterface.OnClickListener() { public void onClick(DialogInterface dialog, int id) { dialog.cancel(); } }) .setNegativeButton("Cancel", new DialogInterface.OnClickListener() { public void onClick(DialogInterface dialog, int id) { dialog.cancel(); } }); AlertDialog alert = builder.create(); alert.show(); http://developer.android.com/guide/topics/ui/dialogs.html 95 Example of ProgressDialog ProgressDialog dialog = ProgressDialog.show(this, "", "Loading. Please wait..."); dialog.show(); 96 Android Logging Options The Log.e() method is used to log errors. The Log.w() method is used to log warnings. The Log.i() method is used to log informational messages. The Log.d() method is used to log debug messages. The Log.v() method is used to log verbose messages. The Log.wtf() method is used to log terrible failures that should never happen. ("WTF" stands for "What a Terrible Failure!" of course.) private static final String TAG = "MyApp"; Log.i(TAG, "I am logging something informational!"); 97 Debug (Window > Open Perspective > Debug) <application android:icon= "@drawable/icon" android:label="@string/app_name" android:debuggable="true" > 98 Tools DroidDraw: http://www.droiddraw.org/ Video: http://marakana.com/forums/android/general/212.html 99 Recommended to try p38: Understanding the Life Cycle of an Activity p42: Displaying a Dialogue Window using an Activity p50: Displaying the progress of an operation p54: Linking Activities with Intents p130: Understanding Activity Behavior when Orientation Changes p161: Using the Basic Views p168: Handling View Events p191: Displaying a Long List of Items using the ListView p197: Checking which Items are Selected p235 Creating the Menu Helper Methods p238: Displaying an Option Menu p240: Displaying a Context Menu 100 References App Development for Smart Devices http://www.cs.odu.edu/~cs495/ 101