Tuesday 21 May 2013

Hello World : Android : Eclipse

Introduction

This page is about using Eclipse IDE to write your first Hello World app on Android.

Optional diversion: Android officially supports development using IntelliJ IDEA based IDE called Android Studio. It is less bloated but as a consequence incomplete in supporting several Android development aspects. For instance we'll eventually use Eclipse to code in C/C++ (Android NDK) which can't be done using Android Studio (in 2013). If you aren't going to be concerned about completeness, Android Studio even in its preview state is pretty good for Java based application development on Android. See this post ("Hello World Using Android Studio") about Hello World using Android Studio. 

Download, Install and Start

Make sure you have JDK6 installed on your system. (Use a google search like this to get it).

Follow instructions on http://developer.android.com/sdk/index.html to download and install the Android ADT bundle.

New Project


Lets create a new project using the inbuilt wizard.

Start Eclipse and point to some workspace.
 Wait for it to finish loading.
 Close the welcome screen using the X next to "Welcome".
 You'd probably end up with a blank perspective.
You can customize the view to your needs from menu Eclipse > Preferences. I like larger font and changing one setting makes it larger on most editors. (General > Apperance > Colors and Fonts > Basic > Text Font).
Consider changing Android > Logcat > Font as well.
Feel free to tune key mappings (General > Keys) etc to your liking.

Tip: At menu Eclipse > Preferences > Java > Compiler > Compliance level, ensure that Java 1.6 is chosen.

Now lets start the wizard using menu File > New > Project > Android > Android Application Project
Enter some name for the application and make sure your package name is unique. If you own some domain say mydomain.com, then your package could be com.mydomain.helloworld.
While uniqueness isn't of concern for our Hello World project, it will be important for an application that needs to be published. Google Play (Android Market) distinguishes apps by the package name only.

Next, I've  changed project location in the screen shot but isn't necessary.

Now click "Next" button to be taken to a screen to choose an icon. Default is good enough for Hello World.
Click "Next" button again and you'll be presented with a list of activity types. Here again, the default choice (Blank) is good enough for our Hello World project.
Applications in Android show screens or pages for the user to interact. Those belonging to a single sort of activity are called an Activity. Our Hello World project is just going to show a single screen with "Hello World" written on it. Call such an activity what ever. Default name for the first activity is MainActivity by this wizard, and is good enough for us.
 The project is coded and ready! Lets anyway get some housekeeping tasks done before executing it.


Android SDK Manager


Since this is the first time this IDE is being used, choose to download few more essential pieces using Android SDK Manager. There is a green Android (bugdroid) icon in the toolbar on top.

Tip: If you can't find that button, start it from command line using
android sdk


When Android SDK Manager settles down with a list of packages, choose (tick) the components of the latest API that aren't yet installed. Similarly scroll down and choose all the "Extra" components that aren't yet installed and then click the "Install ... packages".

That will throw a dialog with license information.

Read each if you must before accepting.



Accept using "Accept license" radio button on bottom left.

And then choose to Install.

Download may take a long time to finish. Don't close that window. But return to the IDE with Cmd+Tab or Alt+Tab or whatever but don't close that Android SDK Manager window.

















Project Structure

Lets explore the main content of our project





(If you aren't following this with your own IDE, click the image to see a larger image with readable text.)

Lets see what's in the 'HelloWorld'.
  • java: Java files. In our case just the MainActivity.java created using the wizard.
  • res: Resources. This holds all resources like drawables (icons, background images), strings, styles, etc. 
    • We are encouraged (but not required) to provide drawables for different screen densities. And hence ic_launcher.png is available as different sizes in those drawable-... folders. 
    • Similarly values (eg. style) can be per API type. Earlier APIs may not support Holo theme for instance. 
  • AndroidManifest.xml: This is the file that tells the Android system about the application. 

The source code (Java) is compiled into class file(s) and zipped along with these resources and the manifest to produce a final single file called the APK (Android Application Package). Of course there are a few more pieces than just these. But this level of understanding will do for now.

Execution

Now to run the application we'll need an android device or an emulator instance.

Or we can create an Android Emulator instance to run our app on. Skip the section about AVD and emulators if you are anyway using on an Android device (phone/tablet).

Execute on Device

If you have an Android device, plug it in to the development machine (running the IDE) with USB.
On the device go into

Settings > Security > Unknown sources

(On devices running Gingerbread or earlier firmware: Settings > Applications > Unknown sources)

And check that option to allow installation of apps from sources other than the primary app store on the device. In this case our Hello World over USB.

Now click the button in the toolbar that looks like a play button to run the application.




Choose to run as Android Application.

That would bring a dialog with all connected devices and emulator instances.


When running on a device (phone/tablet) make sure, "Choose a running device" radio button is selected and then choose one of your connected devices and then click the OK button.


That's it! Your device's screen should light up with your "Hello World"!!!

Continue reading the DDMS>LogCat section (below).






















Execute on an Emulator Instance


Android supports virtual devices running almost the same firmware as a regular device to be emulated on the development machine.

The AVD manager's button is right next to the Android SDK Manager button in the toolbar on top. Click that to launch the AVD (Android Virtual Device) Manager.


Tip: If you can't find that button, start it from command line using
android avd




Create a new AVD instance using the manager and provide some details.


This screen lets us choose some quick values.

Instead of writing every detail by hand, we can choose the type of device to emulate and the boxes are pre-filled with corresponding details.

In particular we wish to use Google API and enable Snapshot.

Google API instances are useful in running applications using Google Maps API etc on top of regular Android APIs.

Using the snapshot feature, we can reduce the startup time from several minutes to couple of seconds except for the first run.

We'd also like to "Use Host GPU" feature, which allows smoother graphics on the emulator by utilizing GPU on the development machine. However at the time of writing this, the two options were mutually-exclusive (and we can't forgo Snapshot feature).

We may of course edit it further.

For instance the emulator by default doesn't seem to care about the camera.


We can choose to use the webcam on our development laptop for both the front and back camera.

Several such customizations are possible.

Now choose the AVD created and click on the "Start.." button.






If this is were not the first time, we'd have chosen to "Launch from snapshot" as shown.

DON'T DO THIS THE FIRST TIME.

Have shown this dialog before the dialog for first time launch to help those who won't read the text and would wish to run forward clicking buttons as shown in the screen shots. 

First time select "Save to Snapshot"
















IMPORTANT: In the dialog shown when running the AVD (emulator instance) for the first time, remember to save to snapshot. This will help us launch from the snapshot next time onwards.

Launching takes several minutes the first time, since there is no old snapshot to start with. Take a short break. Be patient.


When you get back you might find a dark screen as the device is emulating sleep mode using dim screen.



Patience!!!
Emulating Sleep Mode without lock screen



You didn't expect the emulator to turn your laptop's screen to a touch-screen, did you? The emulator can use what is available on your laptop and fake other things like 3G, GPS etc. Some of these can be fed fake values through command line interfaces.


Click (with mouse/touchpad on laptop) and follow the suggestions on screen in the first launch.



Suggestion: From settings, lets do one small thing before shutting it down to save a clean snapshot. Add a gmail (Google) account as it will come in handy for other application tests later.

Add a Gmail/Google account before saving clean emulator state in a snapshot

Now we may Exit the emulator. After going through all the pain and time to start the emulator? Nuts! Yes I am but this time I have a reason. Current state of our emulator is clean and ready to consume applications. Like a freshly booted phone from factory with just one account added. Such an instance is very useful in testing applications. So exiting will help us save a clean state snapshot which we'll use for several months (if we remember to avoid overwriting the snapshot on every fresh launch).

So yes, please close that return to the AVD Manager and choose the one already created by us and click the "Start ..." button again. Don't launch as yet.


From now on always use "Launch from snapshot" and don't wipe. 

This time, remember to Not check "Wipe user data" or "Save to snapshot". Just check "Launch from snapshot" and the emulator should be up and running within a few seconds unlike in our first run.


Now that the one time job of preparing a clean emulator snapshot is done and it is ready, we are happy to execute our Hello World project.

Click the button in the toolbar that looks like a play button to run the application.





Choose to run as Android Application.

That would bring a dialog with all connected devices and emulator instances.


When the emulator is already running, make sure, "Choose a running device" radio button is selected and then choose one of your connected devices and then click the OK button.

(Otherwise, we can create or launch existing AVD from here as well). This too basically just uses the same AVD Manager.








That's it! Your device's screen should light up with your "Hello World"!!!





















DDMS > LogCat


We won't be going into details of debugging etc. But it is worth a mention that anything logged in the application can be viewed through DDMS tool. Eclipse can show different perspectives.




From menu Windows > Open Perspective > Other choose to open DDMS




Choose the device of interest from the list on top left.

If that list is empty, killing and restarting adb from command line may help. Use this:
adb kill-server; adb devices

At the bottom of the screen there is a section for logcat and console output. Console output shows the details of build process etc.

LogCat shows the content logged by android applications running on a device.

The Code

Now lets look at the code behind wizard generated Hello World app we've already run.

MainActivity class in MainActivity.java file extends Android Activity. It overrides onCreate() method with a custom call. The custom call starts with a call to the parent class' (Activity's) onCreate(). Then it sets the layout to show on the screen whenever this activity is launched.




The layout is referenced using 'R', a resources class, that is generated by the build system. R has a reference field for every Android resource in use from this project's resource directory.


This layout is the graphical representation of the XML file under res/layout... folder of our project's main directory (we discussed of earlier). This is called the design view of the layout. Click on "Text" next to "Design" tab at the bottom of the layout to see the corresponding XML document.

Now that's where the string "Hello World" came from:
   string.xml > activity_main.xml > MainActivity.java
using these respectively:
   hello_world > @strings/hello_world > setContentView(R.layout.activity_main)

Quick Exercise 0:
Edit the value of hello_world in string.xml (while keeping the same name).
Run the app again and your change will be reflected. 

Quick Exercise 1:
Edit MainActivity.class to log something using Log.d(String, String).
Say
public static final String TAG = MainActivity.class.getName();  @Override
  protected void onCreate(Bundle savedInstanceState) {
      super.onCreate(savedInstanceState);
      setContentView(R.layout.activity_main);
      Log.d(TAG, "OnCreate() was called");  }

Run the app and observe LogCat. Do you see a debug log with your log message? 

One last piece that must be said about the simple project is about the AndroidManifest.xml file. Lets open it. Open project view (if hidden in vertical tab on the left gutter of the window) and scroll down to find AndroidManifest.xml file in main sub-section.

It is from this file that the Android system gathers that MainActivity needs to be run when this application is launched. Remember, there can be several activities in the same application. The ones that can be launched by the system are given a special category "android.intent.category.LAUNCHER".

Others are custom or "android.intent.category.DEFAULT". Such activities are typically invoked by one of the launched activities.

In our simple Hello World app, there isn't much else, well other than icon, name and most importantly the unique package name given in the wizard.

That would be it for now.

2 comments:

  1. nice tutorial... very useful thank you...

    ReplyDelete
  2. hi, i have an issue on creating myfirst app. The java ADT doesnt create MainActivity.java and activity_main.xml automatically....! so, without it, i couldnt do anything...! do you have any solution ? thanks

    ReplyDelete