In order to begin we must have the proper environment.  These apps are written in Java.  So, at a minimum we need to have the Java SDK installed so we have access to the “javac” compiler.  But, with so many great environments out there, we would be adding an undue burden on ourselves by not taking advantage of them. 

One such IDE is Eclipse (http://www.eclipse.org). Eclipse has many version and flavors.  For this I am using the standard Eclipse Java EE IDE for Web Developers (Version: Mars.1 Release (4.5.1)).  Mars is the most recent release at this time.  The EE/Web flavor gives me other perks not directly needed for a simple Android app.  But any good IDE will do. 

Installing Java 

Before installing the IDE, you will want to install the Java SDK and Runtime Environment.  For Eclipse Mars, we must have at least Java 7.  Java 7 is reaching its end of life so I would go with 8.  Just go out to Oracle (http://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html) and pull down the zip/installer.  Select a place and install it.  Then you will need to go into your Environment Variables and update PATH to include the C:\%pathToJava%\bin; to the value. 

Installing Eclipse 

Eclipse is very easy to install.  Starting with Mars, there are a few options; you can download the actual distribution, or you can download the new Eclipse Installer.   

Once you download the Installer, just run it and search for the web version: 

 Android1.png

Just follow the prompts and you should be set. 

 

Setting up the Android Development Kit 

You now need to install and configure the Android SDK.  This gives you the libraries and tools needed to actually write code for Android.   

Installing the SDK 

Things are changing on this, so your mileage may vary, but at the moment the preferred way is to use the install wizard in Eclipse to pull it in and configure it. 

Go to Help -> Install New Software…  Then put in the URL for the development kit (https://dl-ssl.google.com/android/eclipse/) and select all 

 Android2.png

Once it is installed, you will need to restart Eclipse. 

Configuring the SDK 

Once the Android SDK is set up, you should have 2 new options in your Windows menu: 

 Android3.png

You first need to run the Android SDK Manager to set up what items you need.  You can select what version(s) of Android OS you want to target.  Be sure to also go down to Extras.   

Creating virtual phone to test 

In order to test your app, you will need a virtual phone to test on.  There are many options, but this worked for me. 

 Android4.png

The important ones I have found are Target (needs to be the OS you are writing for) and CPU/ABI which I found that selecting ARM vs Intel will keep you from having to configure accelerators.  

So, now we have our environment set up and we can create our project and actually get coding! 

 

Android Architecture 

OS Architecture 

Android is built as a stack of layers, like most other operating systems.  It is, at its core a Linux kernel.  The kernel handles the low level OS functions like hardware drivers (camera, display, etc.) power management, and so forth.  On top of this is a layer of libraries.  This would include things like SQLite or OpenGL|ES (a 2D/3D vector graphics library).  Also part of the library layer would be the “Android runtime” libraries.  The Java libraries would be there.  Sitting on top of this is the Application Framework layer.  Here are programs that our application code will deal directly with.  This would include things like Activity Manager (program lifecycle), Location Manager (GPS), etc. Finally, there is the Applications layer.  This is where our program resides. 

  Android5.jpg

(image stolen from: http://www.zdnet.com/article/how-android-works-the-big-picture/) 

Application Architecture 

Android programs are defined as a loosely coupled group of “Application Components”.  The components for a program are defined in the AndroidManifest.xml.  This file describes each component and how it interacts with the others. 

There are 4 main component types used in applications. 

  1. Activities.  These handle the user interface.  An activity represents a single screen and associated actions.  So for each screen of the application, there is an activity.  They can layer on top of each other where one activity causes another activity to present and then control can return back to the previous.   
  2. Services.  These handle background processing.  These are for long running operations that run without the need for direct user interaction.  Playing music, or pulling in asynchronous data would be examples. 
  3. Broadcast Receivers.  These handle communication between the Android OS and the actual application.  They are designed to respond to messages from other applications or the OS.   
  4. Content Providers.  These handle database issues.  They supply data as requested. 

There are also some other “minor” component types worth mentioning. 

  1. Views.  These are pieces of the user interface.  It would include things like buttons, edit boxes and so forth 
  2. Intents.  These are messages that enable components to communicate with each other.  Like events. 
  3. Manifest.  This is the XML configuration file for the application. 
  4. Resources.  Static items used for the application.  This would include things like image files or other XML configuration files. 

User Interface architecture 

The Android GUI is comprised of views and view groups.  As mentioned above, a View is a UI object, like a button or text field.  The View Group is a container that defines how the View objects are laid out on the screen. 

Each “page” is an Activity, with a default View-Group, upon which there are 0-n View objects.  As stated before, the application is just a collection of Activities, and is much more loosely an “app” than other traditional targets.  An Activity in Android can invoke any other Activity on the device.  The Activity on top of the stack is the one with focus to the user.  If the user “completes” that Activity, then control can pass back to the next item on the stack.  

For example, if one is on the Facebook app, the default Facebook activity is on top, showing the feed, which consists of many View objects.  If the user selects a View object representing an external URL, then the browser Activity will be pushed to the stack and have focus.  The user will then interact with that Activity (the View-Group).  If the user selects the back arrow, the browser activity closes itself and returns focus to the calling activity, here the Facebook Activity.   

Other examples could be a login “page” where the user is presented with a special Activity asking for credentials, validating, and passing those results back to the calling Activity. 

Because Android is really a collection of Activities, these Activities can exist after the user has completed them, but they are marked inactive so they do not take resources.  They will remain within the OS until such time as they are ultimately destroyed.  This is different than most OS configurations where any loaded application will take resources (CPU, etc.) until officially ended.  Android can have Activities in existence but not taxing the system as a whole. 

Application call stack 

We now have a very simple interface that does nothing.  We next need to wire it up.  In Android, everything is handled by the Activity and it processes events.  The events need to be constructed and bound to the View objects.  Much like a regular application is started with the main(…){} method, an Android Activity is started with the onCreate(…){} method.  This will be where any event wiring needs to happen. 

There are then a number of other methods that represent events happening at the application level: 

  • onCreate:  called when the Activity is first created 
  • onStart:  called with the Activity becomes visible to the user (this can be after created, or after another Activity has finished and control returns to this Activity. 
  • onResume:  called when the user begins interacting with this Activity 

(in the control flow, here is where this Activity is active to the user and the user is interacting with the activity’s View objects) 

  • onPause:  called when this activity is being paused and the previous activity is being resumed. 
  • onStop:  called when this activity is no longer visible 
  • onDestroy:  called with the Activity is officially removed by the operating system 
  • onRestart:  called when the Activity is restarted after having been stopped. 

Android6.png

(image stolen from: http://www.techotopia.com/index.php/Handling_Android_Activity_State_Changes_in_Android_Studio) 

Note: onRestoreInstanceState() and onSaveInstanceState() are to deal with the dynamic state of the Activity. 

 

Coding the interface 

Laying out the default Activity 

To create a simple screen, we start with a new activity.  The Activity will automatically be associated with a default View-Group, which is the opening window where our View objects will reside.   To create an activity, open the new [Symbol] other… and select Android > Android Activity 

Android7.png

Select a Blank Activity, give it a name, accept the defaults, and Finish.  Eclipse now shows you your (mostly) empty page 

Android8.png

It defaults to the Graphical Layout, but you can flip to the xml tab to see how it is truly constructed. 

If you click on the “Hello World!” you will see that it is a view (a TextView literally which is derived from the View object).  You can update the name the View is known in the Java code by updating the Id property on the right.     

You can then add different views (GUI objects using the Form Widgets on the left.  I have added an edit box and a button to my view.  You can drag the View objects where you want them to appear on the screen.  Everything is then translated into the XML, which you can also directly maintain. 

 Android9.png

And here is my underlying XML 

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" 
    xmlns:tools="http://schemas.android.com/tools" 
    android:layout_width="match_parent" 
    android:layout_height="match_parent" 
    android:paddingBottom="@dimen/activity_vertical_margin" 
    android:paddingLeft="@dimen/activity_horizontal_margin" 
    android:paddingRight="@dimen/activity_horizontal_margin" 
    android:paddingTop="@dimen/activity_vertical_margin" 
    tools:context="com.moser.notetaker.MainActivity" > 
 
    <TextView 
        android:id="@+id/textView1" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:text="@string/hello_world" /> 
 
    <EditText 
        android:id="@+id/editText" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:layout_alignLeft="@+id/textView1" 
        android:layout_below="@+id/textView1" 
        android:layout_marginTop="24dp" 
        android:ems="10" > 
 
        <requestFocus /> 
    </EditText> 
 
    <Button 
        android:id="@+id/button1" 
        android:layout_width="wrap_content" 
        android:layout_height="wrap_content" 
        android:layout_alignLeft="@+id/editText" 
        android:layout_below="@+id/editText" 
        android:layout_marginLeft="40dp" 
        android:layout_marginTop="68dp" 
        android:text="Button" /> 
 
</RelativeLayout> 

You can see each View object defined, with their Id, size and alignment in the Layout. 

Java Code 

As stated earlier, everything relies upon events.  This is accomplished using “listener” classes that implement specific interfaces which, when attached to our View object, let us attach code to specific events on that View object.  In this example, we want to handle the click event of our button.  So we create an onclick event and bind it to a member variable. 

private OnClickListener buttonListener = new OnClickListener() { 
@Override 
public void onClick(View view) { 
}; 

Here we have several things happening.  We have created an anonymous class of type OnClickListener. This anonymous class overrides the onClick method.   We are also instantiating this class into a private variable, buttonListenerThis variable is class level member variable in our Activity.java class.  Since the new method to create our listener object is invoked at the time the class is instantiated, it exists prior to the calling of onCreate.   

Now we need to attach this object to our button.  This is done in our onCreate so at the time the Activity is created, it is bound, prior to any user interaction.   

@Override 
protected void onCreate(Bundle savedInstanceState) { 
super.onCreate(savedInstanceState); 
setContentView(R.layout.activity_main); 
 
Button button = (Button)findViewById(R.id.button1); 
button.setOnClickListener(buttonListener); 

 

The first step is to find our button.  Our Activity class has a parent method findViewById, which lets us get our View object.  The “R” here refers to an auto-generated class R.java, which has static variables that map to the View object by the object name from the properties.  Eclipse builds and maintains R.java for us so we do not need to worry about it.  We just use it as though it were an Enum 

Once we have our View object, here the button, we then attach the listener to the event using its methods.  So, we have attached our buttonListener private variable to the button’s onClick event.  It is now wired together. 

But, although they are wired together, our onClick method contains no body so nothing happens.  We’d like to have the value in our edit box get written to our text View object when the user clicks the button.  To do that we need to get the View objects inside our event handler and update the one with the value of the other. 

@Override 
public void onClick(View view) { 
EditText editText = (EditText)findViewById(R.id.editText); 
TextView textView = (TextView)findViewById(R.id.textView1); 
 
textView.setText(editText.getText().toString()); 

In the code above, each View object is bound to a local variable (editText and textView) and the contents of the edit box are set to the text area using the getText() and setText() methods provided. 

   Android10.png

We now have a simple application.  But, if the user was to not input anything into the edit box and merely hit the button, it would just erase the label.  I’d prefer to give the user feedback that they need to input text first.  And, I’d like to do this with a pop-up screen. 

 

Intents 

Overview 

Intents are, in a nutshell, the “glue” that holds Android activities together.  As stated before, an Android application is really just a progression of independent Activities that rise to the top, perform their function, and provide feedback to the previous Activity.  Android does not really care if the “next” Activity was written by the same developers or not.  So, when you are in your Facebook app and click on the external link, read the webpage, then go back to Facebook, what has happened is that the Facebook Activity has caused the browser Activity to rise, you then interact with it.  When you are done and hit the back button, the browser Activity finishes its lifecycle and control goes back one on the stack so the Facebook Activity arises.   

It’s also good to remember the lifecycle of Activities within the Android OS.  While you are on your web browser Activity, onPause() has been called on the Facebook Activity so state is saved and the app is no longer active.  If you go on to other things, onStop() will be called to free up additional resources. 

An Intent is the current Activity stating that it wants to perform some action without necessarily knowing the code it is calling.  It is an asynchronous message that binds Activities (even from different applications) together at runtime.  

An Intent can be defined to activate either a specific Activity, or a type of Activity (like open a web browser).  The Intent can further be set up so that it asks the new Activity to return some result. 

Coding  

For my purposes, I just want a dialog Activity to pop up with a message and a button.  So my first step is to create a new Activity in my project that will represent the dialog.  Like before, right click on the package and select new.. Other… Android… Android Activity.  Once going through the wizard, you will get a new java and xml file.  Add a button to the activity.  I then used the properties in the editor to rename my button (“btnOK”), change the text of the button, and change the text of the label.  I ended with this: 

 Android11.png

 Android12.png

In order for this Activity to be registered as a dialog, the app manifest XML needs to be updated to reflect that: 

       <activity 
           android:name=".WarningDialog" 
           android:label="@string/title_activity_warning_dialog"  
           android:theme="@android:style/Theme.Dialog"
        </activity> 

Eclipse will have already created the <activity> node and added the name and label attributes.  The “theme” attribute (in yellow) needs to be manually added. 

At this point, all that needs done is to wire everything together.  First, the main Activity needs to create the Intent to render the new Activity.  This is done in the click event, on the condition of the edit box being empty. 

private OnClickListener buttonListener = new OnClickListener() { 
@Override 
public void onClick(View view) { 
EditText editText = (EditText)findViewById(R.id.editText); 
TextView textView = (TextView)findViewById(R.id.textView1); 
 
if (editText.getText().length() == 0) { 
Intent intent=new Intent(getApplicationContext(),  
 WarningDialog.class); 
startActivity(intent); 
 
} else
textView.setText(editText.getText().toString()); 
}; 

And, in the new Dialog activity, the new button needs to be set to have a click event that will close the Activity: 

private OnClickListener buttonListener = new OnClickListener() { 
@Override 
public void onClick(View view) { 
finish(); 
}; 

And, the onCreate for the new dialog needs to have the listener bound to the button, and to have some other initialization properties set. 

@Override 
protected void onCreate(Bundle savedInstanceState) { 
super.onCreate(savedInstanceState); 
requestWindowFeature(Window.FEATURE_NO_TITLE); 
setContentView(R.layout.activity_warning_dialog); 
 
Button button = (Button)findViewById(R.id.btnOK); 
button.setOnClickListener(buttonListener);  

Here, the Activity is set with the feature of no title.  This gives it the look more of a dialog box than a new window.  And, the button (View) is found by the ID defined on the Graphical Layout window earlier. 

So, if we run it,  

 Android13.png

 

By setting the theme as a dialog, Android has automatically grayed out the background Activity.  And when OK is clicked, this dialog goes away and the previous Activity is brought back to the forefront. 

Conclusion 

There you have it.  In relatively little time we have set up our environment and created a simple application that showcases Activities, Views, and Intents.  Google provides a great, robust library for development, and the integration into Eclipse gives us a mature environment that makes creating applications relatively easy.