Android Fundamentals - Part 1 Alexander Nelson September 1, 2017 University of Arkansas - Department of Computer Science and Computer Engineering
Reminders
Projects Project 1 due Wednesday, September 13th Link Choose a project idea and team for the final project ASAP First project report is due September 15th
Android OS Platform Architecture
Android Stack https://developer.android.com/guide/platform/index.html Used by Fair Use under Creative Commons Attribution 2.5
Android Stack
Linux Kernel Android is based on the Linux kernel All lower-level functionality is handled by Kernel Provides consistent functionality across devices Maintains standard security practices No need to reinvent the wheel
Hardware Abstraction Layer (HAL) Standard set of interfaces from device hardware to Java APIs Consists of library modules Modules are loaded when API makes call to access hardware
Android Runtime (ART) Managed runtime environment of an application Beginning with Android 5.0, each app runs in its own process and its own instance of ART Each process runs in its own VM, and is thus isolated from other applications Includes core Java libraries for most of the Java functionality
Native C/C++ Libraries Android system components are built from native code and require support libraries Android provides Java framework APIs to expose some funcitonality to these libraries e.g. OpenGL ES can be accessed through Java OpenGL API for graphics
Java API Framework Entire Android OS feature-set available through Java APIs including: View System to build UI (XML defined) Resource manager - Access to non-code resources Notification manager - All apps can display alerts Activity manager - Manage lifecycle of apps Content Providers - Enable cross application sharing
System Applications Core set of applications provided by OS e.g. Camera, SMS, Email, Calendar, Calls, etc... No special status among apps Provide capabilities developers can access from their own app
Application Fundamentals
Application & OS OS Security Features: Multi-user Linux system each app is a different user System assigns each app a unique user ID Permissions are set for files such that only the assigned app can access them Each process has own VM App code run in isolation https://developer.android.com/guide/components/fundamentals.html
Application & OS Process Cycle: Each app runs in its own Linux process Android starts the process when any app component is needed Shuts down process when finished, or memory is needed elsewhere
Principle of Least Privilege Each app, by default, has acess only to the components that it requires, and nothing more! Exceptions: Two apps can share the same Linux user ID Can access each other s files Can run in the same process and same VM Must be signed with the same certificate e.g. Facebook & Messenger App can request permission to access device data User must grant these permissions explicitly
Application Components Four different types of Application components: Activities Services Broadcast Receivers Content Providers
Activities
Activity Entry point for interacting with the user Typically represents a single screen with a UI Mutliple activities can come together to create a single application Example: e-mail application Inbox Screen Compose e-mail Settings
Activies (continued) An activity facilitates key interactions between the system and the application, including: Keeping track of what the user is currently focused on Helping the app handle having its process killed Providing a way for apps to implement user flowss between each other
Activities (continued) To be used, an activity must be declared in the application manifest Example: <m a n i f e s t... > <a p p l i c a t i o n... > < a c t i v i t y android:name=. E x a m p l e A c t i v i t y />... </ a p p l i c a t i o n... >... </ m a n i f e s t >
Activitiy Attributes Attributes can define certain interactions about the activity Contained inside the activity tag The only required attribute for an activity is android:name This specifies the class name of the activity Think these names through! They should not change after publishing your applications!
Activitiy Attributes (continued) Other attributes you may want to include in the manifest: Intent filters (Will discuss later) Permissions Screen Orientation Icon
Activity Lifecycle
Activity Lifecycle An activity will transition through a number of states during its lifetime A series of callbacks are used to handle transitions oncreate() onstart() onresume() onrestart() onpause() onstop() ondestroy()
oncreate() Callback which fires when the system creates the activity You must implement this callback! This callback should initialize the essential components: Create views Bind data Calls setcontentview() which defines the layout for the UI After returining, the next callback is always onstart()
onstart() Activity becomes visible to the user Final preparations before coming to the foreground and becoming interactive Followed by onresume()
onresume() Invoked when the activity starts interacting with the user Most of the App s core functionality implemented here At this point the activity is on the top of the activity stack and captures all user input
onpause() Called when activity loses focus and enters Paused state e.g. When the user hits the back button The activity is still partially visible and can (should?) continue to update If the user returns to the activity, onresume() will be called onstop() is called if the activity beomes no longer visible
onstop() Called when activity becomes no longer visible to user e.g. When activity being destroyed, new activity starting, existing activity being resumed If the activity comes back to the foreground, onrestart() is called ondestroy() is called if the activity is completely termininating.
onrestart() Called when a stopped actibity is about to restart e.g. When activity is brought back to the foreground Restores the state of the activity from when it was stopped Always followed by onstart()
ondestroy() ondestroy() is invoked before the activity is destroyed Implemented to ensure that all the activities resources are released This is the final state in the activity lifecycle Must be recreated to start again
Services
Service Application component that can perform long-running operations in the background Does not provide a user interface! Another app component can start a service The service continues to run in the background even after activity change Components can bind to a service to interact & perform interprocess communication
Services There are three different types of services: Foreground Background Bound
Foreground Service Performs some operation that is noticable to the user e.g. Audio app uses foreground service to play music Must display a status bar icon Continue running even when user isn t interacting with the app
Background Service Performs operations not directly noticed by user e.g. Compress file storage for application Caveat: Starting with API 26, background services have restrictions when the app is not in the foreground Often better to use a scheduled job instead
Bound Service A service becomes bound when app component uses bindservice() Offers a client-server interface for interacting with the service Only runs when another application is bound to it!
Declaring Services To be used, an service must be declared in the application manifest Example: <m a n i f e s t... > <a p p l i c a t i o n... > <s e r v i c e android:name=. E x a m p l e S e r v... </ a p p l i c a t i o n... > </ m a n i f e s t >
Service Lifecycle
onstartcommand() One way to start an Android service System invokes this by calling startservice() from another component startservice() takes Intent as argument onstartcommand() takes Intent, flags, and startid If this is implemented, you must stop the service when work is complete by calling stopself() or stopservice()
Started Services A started service is one that is created when a component calls startservice() Lifecycle of the service is independent of the component which creates it! App components create services by calling startservice() and passing an Intent object specifying the targeted Service
Started Services (continued) By default started services run in the same process in the main thread of the application in which it is declared If the service is blocking while the user is to be interacting with the app, start a new thread within the service
Started Services (continued) It is best to start a service by extending the IntentService class The IntentService class does the following: Creates default worker thread that executes all intents delivered to the onstartcommand() Creates a work queue that passes one intent at a time to your onhandleintent() implementation, so you never have to worry about multi-threading Stops the service after all of the start requests are handled, so you never have to call stopself() Provides a default implementation of onbind() that returns null Provides a default implementation of onstartcommand() that sends the intent to the work queue and then to your onhandleintent() implementation
Example IntentService
Extending Intent Service All you need (as shown by previous example): Constructor Implementation of onhandleintent() You may also override callbacks, but you must call the super implementation
Starting a Service You create a Started Service by calling startservice() and passing an intent object
Stopping a Service Started services must manage their own lifecycle The system will not stop or destory a service unless it must recover memory Services must stop itself by calling stopself() or another component may stop it by calling stopservice() If your service is potentially used by multiple components concurrently: Use stopself(int) where the passed integer is the ID of the start request
onbind() Other way to start an Android Service Calledc when another component calls bindservice() You must provide an interface to communicate between client and service IBinder object provides this, by extending the Binder class
Bound Services Bound services are to be used when you want your service to interact with other components through Interprocess Communication (IPC) Use onbind() callback to create a bound service onbind() returns an IBinder object defining the interface for communication
Bound Services Multiple components may bind with a service, and have a reference to the same IBinder object When a client is finished with the service, it calls unbindservice() to unbind You do not need to stop a bound service! Bound services terminate when no clients are connected
oncreate() Invoked by the system before onstartcommand() or onbind() Perform one-time setup procedures Not called if service is already running!
ondestroy() Invoked by the system before when Service is no longer needed Should be implemented to clean up any resources (threads, registered listeners, receivers) Last call that the service will receive
Service Stop Conditions Service started by calling startservice() will run until stopped by stopself() or another component calls stopservice() Service started by bindservice() will run as long as the component is bound to it Force-stop conditions If memory is low and system resources must be recovered Bound services to app in focus less likely to be killed Foreground services are rarely killed Long-running started services are highly susceptible to being killed
Notifications Services may communicate to the user with: Toast Notifications Status Bar Notifications
Foreground Services Foreground services are services the user is actively aware of Must provide a notification for the status bar under the Ongoing heading! Notification cannot be dismissed unless service is stopped or removed from foreground ex. Music player should be foreground Notification shows current song Can interact to launch the music player
Starting a foreground service Request to run service in foreground with startforeground() Takes two parameters: Integer to uniquely identify the notification A Notification object for the status bar Notification object must have priority of PRIORITY LOW or higher
Foreground Service Example
Removing Service from Foreground To remove service from foreground: Call stopforeground() stopforeground() takes a boolean argument which indicates whether to remove the status bar notification Removing service from foreground does not stop the service!