<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-277123759957171194</id><updated>2012-01-05T06:16:02.789+08:00</updated><category term='SQLiteOpenHelper'/><category term='sdcard'/><category term='hello world'/><category term='android'/><category term='j2me'/><category term='blogger'/><category term='threads'/><category term='css'/><category term='picture'/><category term='mapviewer'/><category term='java'/><category term='ListActivity'/><category term='camera'/><category term='sqlite'/><category term='intent'/><category term='stylesheet'/><category term='beer radar'/><category term='progress bar'/><category term='app engine'/><category term='networking'/><category term='json'/><category term='database'/><title type='text'>Java Padawan on J2ME and Android</title><subtitle type='html'>Google Android Programming Blog.
Development of Java Mobile Edition Applications and Porting them into Google Android codes. 
The Android tools that will be used are the Eclipse IDE and the Android SDK. 
The J2ME tools that will be used are Netbeans IDE complete and Nokia SDKs.
Tutorial does not cover tutorials on how to get started on developing Android, but rather focus on the similarities and differences of Android and J2ME.
Android.</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://www.androidph.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://www.androidph.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>15</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-5329468579752387723</id><published>2012-01-05T05:46:00.004+08:00</published><updated>2012-01-05T06:13:47.664+08:00</updated><title type='text'>Android Custom Database ListAdapters</title><content type='html'>On the ListActivity class : &lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;ListPatientCursorAdapter listAdapter = new ListPatientCursorAdapter(this, R.layout.patient_list, cursor);&lt;br /&gt;setListAdapter(listAdapter);&lt;br /&gt;startManagingCursor(cursor);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Custom List Adapter :&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt; class ListPatientCursorAdapter extends ResourceCursorAdapter {&lt;br /&gt;  &lt;br /&gt;  public ListPatientCursorAdapter(Context context, int layout, Cursor c) {&lt;br /&gt;   super(context, layout, c);&lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;  @Override&lt;br /&gt;  public View newView(Context context, Cursor cur, ViewGroup parent) {&lt;br /&gt;   LayoutInflater li = (LayoutInflater) getSystemService(Context.LAYOUT_INFLATER_SERVICE);&lt;br /&gt;   return li.inflate(R.layout.patient_list_row, parent, false);&lt;br /&gt;  }&lt;br /&gt;  &lt;br /&gt;  &lt;br /&gt;  @Override&lt;br /&gt;  public void bindView(View v, Context context, final Cursor _c) {&lt;br /&gt;   TextView tvId = (TextView)v.findViewById(R.id.tvId);&lt;br /&gt;   final Integer id = _c.getInt(_c.getColumnIndex(Patient.PatientField.ID));&lt;br /&gt;   TextView tvFirstName = (TextView) v.findViewById(R.id.tvFirstName);&lt;br /&gt;   tvFirstName.setText(_c.getString(_c&lt;br /&gt;     .getColumnIndex(Patient.PatientField.FIRSTNAME)));&lt;br /&gt;&lt;br /&gt;   TextView tvMiddleName = (TextView) v&lt;br /&gt;     .findViewById(R.id.tvMiddleName);&lt;br /&gt;   tvMiddleName.setText(_c.getString(_c&lt;br /&gt;     .getColumnIndex(Patient.PatientField.MIDDLENAME)));&lt;br /&gt;&lt;br /&gt;   TextView tvLastName = (TextView) v.findViewById(R.id.tvLastName);&lt;br /&gt;   tvLastName.setText(_c.getString(_c&lt;br /&gt;     .getColumnIndex(Patient.PatientField.LASTNAME)));&lt;br /&gt;&lt;br /&gt;   TextView tvLastUpdate = (TextView) v&lt;br /&gt;     .findViewById(R.id.tvLastUpdate);&lt;br /&gt;   &lt;br /&gt;   CheckBox cbFollowUp = (CheckBox) v.findViewById(R.id.cbFollowUp);&lt;br /&gt;   cbFollowUp&lt;br /&gt;     .setChecked(_c.getInt(_c&lt;br /&gt;       .getColumnIndex(Patient.PatientField.FOR_FOLLOWUP)) == 0 ? false&lt;br /&gt;       : true);&lt;br /&gt;   &lt;br /&gt;   Calendar cal = Calendar.getInstance();&lt;br /&gt;   cal.setTimeInMillis(_c.getLong(_c&lt;br /&gt;     .getColumnIndex(Patient.PatientField.UPDATE_DATE)));&lt;br /&gt;   &lt;br /&gt;   tvLastUpdate.setText(sdf.format(cal.getTime()));&lt;br /&gt;  &lt;br /&gt;   v.setOnClickListener(new OnClickListener() {&lt;br /&gt;    public void onClick(View v) {&lt;br /&gt;     processSelectedId(id);&lt;br /&gt;    }&lt;br /&gt;   });&lt;br /&gt;  }&lt;br /&gt; }&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;List View : &lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;    &lt;LinearLayout&lt;br /&gt;        android:layout_width="fill_parent"&lt;br /&gt;        android:layout_height="wrap_content"&lt;br /&gt;        android:orientation="vertical" &gt;&lt;br /&gt;        &lt;ListView&lt;br /&gt;            android:id="@android:id/list"&lt;br /&gt;            android:layout_width="fill_parent"&lt;br /&gt;            android:layout_height="fill_parent"&lt;br /&gt;            android:divider="#FFFFFF"&lt;br /&gt;            android:dividerHeight="0sp"&lt;br /&gt;            android:scrollbars="none" /&gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:id="@id/android:empty"&lt;br /&gt;            android:layout_width="fill_parent"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:layout_margin="5px"&lt;br /&gt;            android:gravity="center"&lt;br /&gt;            android:text="No Patient Record." &gt;&lt;br /&gt;        &lt;/TextView&gt;&lt;br /&gt;    &lt;/LinearLayout&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;List Row : &lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;&lt;?xml version="1.0" encoding="utf-8"?&gt;&lt;br /&gt;&lt;LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"&lt;br /&gt;    android:layout_width="match_parent"&lt;br /&gt;    android:layout_height="match_parent"&lt;br /&gt;    android:orientation="vertical" &gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:id="@+id/tvId"&lt;br /&gt;            android:layout_width="wrap_content"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:text=""&lt;br /&gt;            android:visibility="gone"/&gt;&lt;br /&gt;    &lt;LinearLayout&lt;br /&gt;        android:id="@+id/llPatient"&lt;br /&gt;        android:layout_width="fill_parent"&lt;br /&gt;        android:layout_height="wrap_content"&lt;br /&gt;        android:orientation="horizontal" &gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:id="@+id/tvLastName"&lt;br /&gt;            android:layout_width="wrap_content"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:text="Puti"&lt;br /&gt;            android:textAppearance="?android:attr/textAppearanceLarge" /&gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:layout_width="wrap_content"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:text=" "&lt;br /&gt;            android:textAppearance="?android:attr/textAppearanceMedium" /&gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:id="@+id/tvFirstName"&lt;br /&gt;            android:layout_width="wrap_content"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:text="Kyle"&lt;br /&gt;            android:textAppearance="?android:attr/textAppearanceMedium" /&gt;&lt;br /&gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:layout_width="wrap_content"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:text=" "&lt;br /&gt;            android:textAppearance="?android:attr/textAppearanceMedium" /&gt;&lt;br /&gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:id="@+id/tvMiddleName"&lt;br /&gt;            android:layout_width="wrap_content"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:text="Amousy"&lt;br /&gt;            android:textAppearance="?android:attr/textAppearanceMedium" /&gt;&lt;br /&gt;    &lt;/LinearLayout&gt;&lt;br /&gt;    &lt;LinearLayout&lt;br /&gt;        android:layout_width="fill_parent"&lt;br /&gt;        android:layout_height="wrap_content"&lt;br /&gt;        android:orientation="horizontal" &gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:layout_width="wrap_content"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:text="Last Update"&lt;br /&gt;            android:textAppearance="?android:attr/textAppearanceMedium" /&gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:layout_width="wrap_content"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:text=" "&lt;br /&gt;            android:textAppearance="?android:attr/textAppearanceMedium" /&gt;&lt;br /&gt;        &lt;TextView&lt;br /&gt;            android:id="@+id/tvLastUpdate"&lt;br /&gt;            android:layout_width="wrap_content"&lt;br /&gt;            android:layout_height="wrap_content"&lt;br /&gt;            android:text="Last Update" /&gt;&lt;br /&gt;    &lt;/LinearLayout&gt;&lt;br /&gt;    &lt;CheckBox&lt;br /&gt;        android:id="@+id/cbFollowUp"&lt;br /&gt;        android:layout_width="wrap_content"&lt;br /&gt;        android:layout_height="wrap_content"&lt;br /&gt;        android:checked="true"&lt;br /&gt;        android:enabled="false"&lt;br /&gt;        android:text="For Follow Up" /&gt;&lt;br /&gt;&lt;/LinearLayout&gt;&lt;br /&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-5329468579752387723?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/5329468579752387723/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=5329468579752387723' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/5329468579752387723'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/5329468579752387723'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2012/01/android-custom-database-listadapters.html' title='Android Custom Database ListAdapters'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-7553680433528746788</id><published>2012-01-05T04:38:00.008+08:00</published><updated>2012-01-05T04:50:52.049+08:00</updated><title type='text'>Android SQLite Primary Key Auto Increment</title><content type='html'>WRONG :&lt;br /&gt;&lt;pre name="code" class="sql"&gt;CREATE TABLE PERSON (ID INTEGER PRIMARY KEY AUTOINCREMENT,&lt;br /&gt;FIRSTNAME TEXT,&lt;br /&gt;LASTNAME TEXT)&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;WRONG :&lt;br /&gt;&lt;pre name="code" class="sql"&gt;CREATE TABLE PERSON (ID INT PRIMARY KEY AUTOINCREMENT,&lt;br /&gt;FIRSTNAME TEXT,&lt;br /&gt;LASTNAME TEXT)&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;b&gt;CORRECT :&lt;/b&gt;&lt;br /&gt;&lt;pre name="code" class="sql"&gt;CREATE TABLE PERSON (ID INTEGER PRIMARY KEY,&lt;br /&gt;FIRSTNAME TEXT,&lt;br /&gt;LASTNAME TEXT)&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Java Code To Insert (Do Not Set ID field):&lt;br /&gt;&lt;pre name="code" class="java"&gt;ContentValues values = new ContentValues();&lt;br /&gt;values.put("FIRSTNAME", "Java");&lt;br /&gt;values.put("LASTNAME", "Padawan");&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Then on your SQLiteDatabase instance do :&lt;br /&gt;&lt;pre name="code" class="java"&gt;sqlDatabase.insert("PERSON" null, values);&lt;br /&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-7553680433528746788?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/7553680433528746788/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=7553680433528746788' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/7553680433528746788'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/7553680433528746788'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2012/01/android-sqlite-primary-key-auto.html' title='Android SQLite Primary Key Auto Increment'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-8159921413882484922</id><published>2009-08-10T15:56:00.007+08:00</published><updated>2009-08-10T16:07:23.568+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='json'/><title type='text'>Android Parsing JSON</title><content type='html'>1. Parse the live JSON response from http://beer.androidph.com/beerws. See &lt;a href="http://www.androidph.com/2009/08/generating-json-with-java-app-engine.html"&gt;App Engine Generating JSON&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;2. Use the code from &lt;a href="http://www.androidph.com/2008/10/android-networking-user-experience-and.html"&gt;Android Networking Tutorial&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;3. JSON Parser Code&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;&lt;br /&gt;JSONArray parseArray = new JSONArray(message);&lt;br /&gt;for (int i = 0; i &lt; jo =" parseArray.getJSONObject(i);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;4. Modify nextscreen.xml of the source code from #2.&lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;&lt;br /&gt;&lt;linearlayout android="http://schemas.android.com/apk/res/android" orientation="vertical" layout_width="fill_parent" layout_height="fill_parent"&gt;&lt;br /&gt;&lt;scrollview id="@+id/scrollView" layout_width="fill_parent" layout_height="wrap_content" scrollbars="vertical"&gt;&lt;br /&gt; &lt;linearlayout id="@+id/linearLayout" orientation="vertical" layout_width="fill_parent" layout_height="wrap_content"&gt;&lt;br /&gt;  &lt;linearlayout orientation="horizontal" layout_width="fill_parent" layout_height="wrap_content"&gt;&lt;br /&gt;   &lt;textview id="@+id/tvName" layout_width="wrap_content" layout_alignparentright="false" layout_height="wrap_content" text="Name | "&gt;&lt;br /&gt;   &lt;textview id="@+id/tvAddress" layout_width="wrap_content" layout_height="wrap_content" text="Address | "&gt;&lt;br /&gt;   &lt;textview id="@+id/tvPrice" layout_width="wrap_content" layout_height="wrap_content" text="Price | "&gt;&lt;br /&gt;   &lt;textview id="@+id/tvLastCallTime" layout_width="wrap_content" layout_height="wrap_content" text="Time | "&gt;&lt;br /&gt;   &lt;textview id="@+id/tvLocation" layout_width="wrap_content" layout_height="wrap_content" text="Location"&gt;&lt;br /&gt;  &lt;/textview&gt;&lt;br /&gt; &lt;/textview&gt;&lt;br /&gt;&lt;/textview&gt;&lt;br /&gt;&lt;/textview&gt;&lt;br /&gt;&lt;/textview&gt;&lt;/linearlayout&gt;&lt;/linearlayout&gt;&lt;/scrollview&gt;&lt;/linearlayout&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;5. Modify NextScreen.java from source code in #2 or &lt;a href="http://www.androidph.com/2008/10/android-networking-user-experience-and.html"&gt;Android Networking Tutorial &lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class NextScreen extends Activity implements OnClickListener {&lt;br /&gt; private Button btnBack;&lt;br /&gt;&lt;br /&gt; private ViewGroup.LayoutParams layoutName;&lt;br /&gt; private ViewGroup.LayoutParams layoutAddress;&lt;br /&gt; private ViewGroup.LayoutParams layoutPrice;&lt;br /&gt; private ViewGroup.LayoutParams layoutLastCallTime;&lt;br /&gt; private ViewGroup.LayoutParams layoutLocation;&lt;br /&gt;&lt;br /&gt; private String message;&lt;br /&gt; private LinearLayout linearLayout;&lt;br /&gt; private LinearLayout linearInnerLayout;&lt;br /&gt;&lt;br /&gt; @Override&lt;br /&gt; public void onCreate(Bundle savedInstanceState) {&lt;br /&gt;  super.onCreate(savedInstanceState);&lt;br /&gt;  setContentView(R.layout.nextscreen);&lt;br /&gt;  initComponents();&lt;br /&gt; }&lt;br /&gt;&lt;br /&gt; public void initComponents() {&lt;br /&gt;&lt;br /&gt;  linearLayout = (LinearLayout) findViewById(R.id.linearLayout);&lt;br /&gt;  linearInnerLayout = (LinearLayout) linearLayout.getChildAt(0);&lt;br /&gt;&lt;br /&gt;  layoutName = ((TextView) linearInnerLayout.getChildAt(0))&lt;br /&gt;    .getLayoutParams();&lt;br /&gt;  layoutAddress = ((TextView) linearInnerLayout.getChildAt(1))&lt;br /&gt;    .getLayoutParams();&lt;br /&gt;  layoutPrice = ((TextView) linearInnerLayout.getChildAt(2))&lt;br /&gt;    .getLayoutParams();&lt;br /&gt;  layoutLastCallTime = ((TextView) linearInnerLayout.getChildAt(3))&lt;br /&gt;    .getLayoutParams();&lt;br /&gt;  layoutLocation = ((TextView) linearInnerLayout.getChildAt(4))&lt;br /&gt;    .getLayoutParams();&lt;br /&gt;&lt;br /&gt;  message = getIntent().getStringExtra(NetworkConnection.NC_RESPONSE);&lt;br /&gt;  &lt;br /&gt;  LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(&lt;br /&gt;    LinearLayout.LayoutParams.FILL_PARENT,&lt;br /&gt;    LinearLayout.LayoutParams.WRAP_CONTENT);&lt;br /&gt;  &lt;br /&gt;  try {&lt;br /&gt;   JSONArray parseArray = new JSONArray(message);&lt;br /&gt;   for (int i = 0; i &lt; parseArray.length(); i++) {&lt;br /&gt;    JSONObject jo = parseArray.getJSONObject(i);&lt;br /&gt;    &lt;br /&gt;    LinearLayout newRow = new LinearLayout(this);&lt;br /&gt;    newRow.setLayoutParams(linearInnerLayout.getLayoutParams());&lt;br /&gt;    &lt;br /&gt;    String name = jo.getString("name") + " | ";&lt;br /&gt;    TextView curTvName = new TextView(this);&lt;br /&gt;    curTvName.setText(name);&lt;br /&gt;    curTvName.setLayoutParams(layoutName);&lt;br /&gt;    &lt;br /&gt;    String address = jo.getString("address") + " | ";&lt;br /&gt;    TextView curTvAddress = new TextView(this);&lt;br /&gt;    curTvAddress.setText(address);&lt;br /&gt;    curTvAddress.setLayoutParams(layoutAddress);&lt;br /&gt;    &lt;br /&gt;    String price = jo.getString("price") + " | ";&lt;br /&gt;    TextView curTvPrice = new TextView(this);&lt;br /&gt;    curTvPrice.setText(price);&lt;br /&gt;    curTvPrice.setLayoutParams(layoutPrice);&lt;br /&gt;    &lt;br /&gt;    String lastCallTime = jo.getString("lastCallTimeString") + " | ";&lt;br /&gt;    TextView curTvLastCallTime = new TextView(this);&lt;br /&gt;    curTvLastCallTime.setText(lastCallTime);&lt;br /&gt;    curTvLastCallTime.setLayoutParams(layoutLastCallTime);&lt;br /&gt;    &lt;br /&gt;    String location = jo.getString("latitude") + "," + jo.getString("longitude");&lt;br /&gt;    TextView curTvLocation = new TextView(this);&lt;br /&gt;    curTvLocation.setText(location);&lt;br /&gt;    curTvLocation.setLayoutParams(layoutLocation);&lt;br /&gt;    &lt;br /&gt;    newRow.addView(curTvName);&lt;br /&gt;    newRow.addView(curTvAddress);&lt;br /&gt;    newRow.addView(curTvPrice);&lt;br /&gt;    newRow.addView(curTvLastCallTime);&lt;br /&gt;    newRow.addView(curTvLocation);&lt;br /&gt;    &lt;br /&gt;    linearLayout.addView(newRow, new LinearLayout.LayoutParams(&lt;br /&gt;      LinearLayout.LayoutParams.FILL_PARENT,&lt;br /&gt;      LinearLayout.LayoutParams.WRAP_CONTENT));&lt;br /&gt;   }&lt;br /&gt;  } catch (JSONException e) {&lt;br /&gt;   // TODO Auto-generated catch block&lt;br /&gt;   e.printStackTrace();&lt;br /&gt;  }&lt;br /&gt; }&lt;br /&gt;&lt;br /&gt; @Override&lt;br /&gt; public void onClick(View v) {&lt;br /&gt;  if (v == btnBack) {&lt;br /&gt;   finish();&lt;br /&gt;  }&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;6. Screenshot of the android JSON parser.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/Sn_S2Vy2GUI/AAAAAAAAAcc/GE8lpwX6uw4/s1600-h/JSON_Android.PNG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 324px; height: 378px;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/Sn_S2Vy2GUI/AAAAAAAAAcc/GE8lpwX6uw4/s400/JSON_Android.PNG" alt="" id="BLOGGER_PHOTO_ID_5368241111854094658" border="0" /&gt;&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-8159921413882484922?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/8159921413882484922/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=8159921413882484922' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/8159921413882484922'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/8159921413882484922'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2009/08/android-parsing-json.html' title='Android Parsing JSON'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://1.bp.blogspot.com/_WAOO_koVttQ/Sn_S2Vy2GUI/AAAAAAAAAcc/GE8lpwX6uw4/s72-c/JSON_Android.PNG' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-472294163693967674</id><published>2009-08-07T15:44:00.004+08:00</published><updated>2009-08-07T15:50:11.346+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='app engine'/><category scheme='http://www.blogger.com/atom/ns#' term='json'/><title type='text'>Generating JSON with Java App Engine</title><content type='html'>1. Requirements App Engine 1.2.2. (The older version of App Engine has a problem compiling the org.json package)&lt;br /&gt;&lt;br /&gt;2. Download Java &lt;a href="http://www.json.org/java/json.zip"&gt;JSON.zip&lt;/a&gt; from http://www.json.org&lt;br /&gt;&lt;br /&gt;3. Read my first &lt;a href="http://www.androidph.com/2009/04/app-engine-tutorial-creating-beer-radar.html"&gt;app engine tutorial&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;4. Generate a JSON string from any java.util.List of Objects. For this instance I used the objects from #3.&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class BeerWS extends HttpServlet {&lt;br /&gt;&lt;br /&gt; public void process(HttpServletRequest req, HttpServletResponse resp)&lt;br /&gt;   throws IOException, ServletException {&lt;br /&gt;  resp.setContentType("text/plain");&lt;br /&gt;     PersistenceManager persistenceManager = PMF.get()&lt;br /&gt;  .getPersistenceManager();&lt;br /&gt;  String query = "select from " + Beer.class.getName()&lt;br /&gt;  + " order by name asc";&lt;br /&gt;  List&lt;Beer&gt; beerLocations = (List&lt;Beer&gt;)persistenceManager.newQuery(query).execute();&lt;br /&gt;  List list = new ArrayList();&lt;br /&gt;  for(Beer beer : beerLocations) {&lt;br /&gt;   //Add the pojo as a JSONObject&lt;br /&gt;   list.add(new JSONObject(beer));&lt;br /&gt;  }&lt;br /&gt;  //Create a JSONArray based from the list of JSONObejcts&lt;br /&gt;  JSONArray jsonArray = new JSONArray(list);&lt;br /&gt;  //Then output the JSON string to the servlet response&lt;br /&gt;  resp.getWriter().println(jsonArray.toString());&lt;br /&gt; }&lt;br /&gt;&lt;br /&gt; public void doPost(HttpServletRequest req, HttpServletResponse resp)&lt;br /&gt;   throws IOException, ServletException {&lt;br /&gt;  process(req, resp);&lt;br /&gt; }&lt;br /&gt;&lt;br /&gt; public void doGet(HttpServletRequest req, HttpServletResponse resp)&lt;br /&gt;   throws IOException, ServletException {&lt;br /&gt;  process(req, resp);&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;5. Here's the link of the live demo. &lt;a href="http://beer.androidph.com/beerws"&gt;http://beer.androidph.com/beerws&lt;/a&gt;. Below is the object used if you have not already check my previous app engine tutorial.&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;@PersistenceCapable(identityType = IdentityType.APPLICATION)&lt;br /&gt;public class Beer {&lt;br /&gt;    @PrimaryKey&lt;br /&gt;    @Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)&lt;br /&gt; private Long id;&lt;br /&gt;    @Persistent&lt;br /&gt; private String name;&lt;br /&gt;    @Persistent&lt;br /&gt; private Double price;&lt;br /&gt;    @Persistent&lt;br /&gt; private Date lastCallTime;&lt;br /&gt;    @Persistent&lt;br /&gt; private String promotions;&lt;br /&gt;    @Persistent&lt;br /&gt; private String address;&lt;br /&gt;    @Persistent&lt;br /&gt; private Double longitude;&lt;br /&gt;    @Persistent&lt;br /&gt; private Double latitude;&lt;br /&gt;&lt;br /&gt;    public Beer() {}&lt;br /&gt;    &lt;br /&gt;    public Beer(String name, Double price, &lt;br /&gt;      Date lastCallTime, String promotions, &lt;br /&gt;  String address, Double longitude, Double latitude) {&lt;br /&gt;     this.name = name;&lt;br /&gt;     this.price = price;&lt;br /&gt;     this.lastCallTime = lastCallTime;&lt;br /&gt;     this.promotions = promotions;&lt;br /&gt;     this.address = address;&lt;br /&gt;     this.longitude = longitude;&lt;br /&gt;     this.latitude = latitude;&lt;br /&gt;    }&lt;br /&gt;    &lt;br /&gt;    public Beer(Long id, String name, Double price, &lt;br /&gt;      Date lastCallTime, String promotions, String address, &lt;br /&gt;     Double longitude, Double latitude) {&lt;br /&gt;     this.id = id;&lt;br /&gt;     this.name = name;&lt;br /&gt;     this.price = price;&lt;br /&gt;     this.lastCallTime = lastCallTime;&lt;br /&gt;     this.promotions = promotions;&lt;br /&gt;     this.address = address;&lt;br /&gt;     this.longitude = longitude;&lt;br /&gt;     this.latitude = latitude;&lt;br /&gt;    }&lt;br /&gt; public Long getId() {&lt;br /&gt;  return id;&lt;br /&gt; }&lt;br /&gt; public void setId(Long id) {&lt;br /&gt;  this.id = id;&lt;br /&gt; }&lt;br /&gt; public String getName() {&lt;br /&gt;  return name;&lt;br /&gt; }&lt;br /&gt; public void setName(String name) {&lt;br /&gt;  this.name = name;&lt;br /&gt; }&lt;br /&gt; public Double getPrice() {&lt;br /&gt;  return price;&lt;br /&gt; }&lt;br /&gt; public void setPrice(Double price) {&lt;br /&gt;  this.price = price;&lt;br /&gt; }&lt;br /&gt; public Date getLastCallTime() {&lt;br /&gt;  return lastCallTime;&lt;br /&gt; }&lt;br /&gt; public void setLastCallTime(Date lastCallTime) {&lt;br /&gt;  this.lastCallTime = lastCallTime;&lt;br /&gt; }&lt;br /&gt; private SimpleDateFormat sdf = new SimpleDateFormat("HH:mm");&lt;br /&gt; public String getLastCallTimeString() {&lt;br /&gt;  if(lastCallTime != null) {&lt;br /&gt;   return sdf.format(lastCallTime);&lt;br /&gt;  } else {&lt;br /&gt;   return "-";&lt;br /&gt;  }&lt;br /&gt; }&lt;br /&gt; public String getPromotions() {&lt;br /&gt;  return promotions;&lt;br /&gt; }&lt;br /&gt; public void setPromotions(String promotions) {&lt;br /&gt;  this.promotions = promotions;&lt;br /&gt; }&lt;br /&gt; public String getAddress() {&lt;br /&gt;  return address;&lt;br /&gt; }&lt;br /&gt; public void setAddress(String address) {&lt;br /&gt;  this.address = address;&lt;br /&gt; }&lt;br /&gt; public Double getLongitude() {&lt;br /&gt;  return longitude;&lt;br /&gt; }&lt;br /&gt; public void setLongitude(Double longitude) {&lt;br /&gt;  this.longitude = longitude;&lt;br /&gt; }&lt;br /&gt; public Double getLatitude() {&lt;br /&gt;  return latitude;&lt;br /&gt; }&lt;br /&gt; public void setLatitude(Double latitude) {&lt;br /&gt;  this.latitude = latitude;&lt;br /&gt; }&lt;br /&gt;} &lt;br /&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-472294163693967674?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/472294163693967674/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=472294163693967674' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/472294163693967674'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/472294163693967674'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2009/08/generating-json-with-java-app-engine.html' title='Generating JSON with Java App Engine'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-3834992813474383262</id><published>2009-07-21T17:54:00.008+08:00</published><updated>2009-07-24T18:26:26.590+08:00</updated><title type='text'>Google App Engine - Spring Integration Issues</title><content type='html'>I'm currently building the server component of &lt;span style="font-size:130%;"&gt;&lt;a href="http://www.androidph.com/2009/02/app-10-beer-radar.html"&gt;Beer Radar&lt;/a&gt;&lt;/span&gt; using &lt;span style="font-size:130%;"&gt;&lt;a href="http://www.androidph.com/2009/04/app-engine-tutorial-creating-beer-radar.html"&gt;Google App Engine&lt;/a&gt;&lt;/span&gt; and &lt;span style="font-size:130%;"&gt;&lt;a href="http://www.androidph.com/2009/07/google-app-engine-spring-integration.html"&gt;Spring Framework&lt;/a&gt;&lt;/span&gt; 3.0.&lt;br /&gt;&lt;br /&gt;I've encountered these problems below and posting their corresponding solutions.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:130%;"&gt;&lt;span style="font-weight: bold;"&gt;Problem:&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;Google App Engine cannot read JSTL and Spring Expression on JSPs&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:130%;"&gt;&lt;span style="font-weight: bold;"&gt;Solution:&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;Google App Engine has &lt;span style="font-style: italic;"&gt;isELIgnored="true"&lt;/span&gt; by default.&lt;br /&gt;Just add the&lt;span style="font-style: italic;"&gt; isELIgnored="false"&lt;/span&gt; on the &lt;span style="font-style: italic;"&gt;&amp;lt;%@page&lt;/span&gt; section in the JSP.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:130%;"&gt;&lt;span style="font-weight: bold;"&gt;Problem:&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;org.springframework.web.servlet.tags.RequestContextAwareTag doStartTag: access denied (java.lang.RuntimePermission getClassLoader)&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:130%;"&gt;&lt;span style="font-weight: bold;"&gt;Solution:&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;Add the following on your Controller&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;For Annotated controllers use&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;@InitBinder&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;public void initLogin(WebDataBinder binder) {&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;System.out.println("initLogin");&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;binder.registerCustomEditor(String.class, new StringTrimmerEditor&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;(false));&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;}&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;For sub-classed controllers&lt;/span&gt;&lt;br /&gt;Override the InitBinder method and register string trimmed editor in the binder&lt;br /&gt;&lt;span style="font-style: italic;"&gt;binder.registerCustomEditor(String.class, new StringTrimmerEditor&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;(false));&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:130%;"&gt;&lt;span style="font-weight: bold;"&gt;Problem:&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;org.springframework.web.HttpSessionRequiredException: Session attribute '' required - not found in session&lt;br /&gt;&lt;br /&gt;and/or&lt;br /&gt;&lt;br /&gt;Uncaught exception from servlet&lt;br /&gt;java.lang.RuntimeException: java.io.NotSerializableException:&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:130%;"&gt;&lt;span style="font-weight: bold;"&gt;Solution :&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;implements Serializable {&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;private static final long serialVersionUID = &amp;lt;generated value&amp;gt;L&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;The unserialized Session object will work on development but, it will throw a java.io.NotSerializableException on the appspot server.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:130%;"&gt;&lt;span style="font-weight: bold;"&gt;Problem :&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;Attempt was made to manually set the id component of a Key primary key.  If you want to control the value of the primary key, set the name component instead.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:130%;"&gt;&lt;span style="font-weight: bold;"&gt;Solution :&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;This happens when I update a child object. The solution for this, is to re-attach the parent object first, by&lt;br /&gt;&lt;span style="font-style: italic;"&gt;Parent attached = pm.getObjectById(Parent.class, detachedParent.getId());&lt;/span&gt;&lt;br /&gt;then&lt;br /&gt;Modify the child&lt;br /&gt;&lt;span style="font-style: italic;"&gt;attached.getChild().setName("new value");&lt;/span&gt;&lt;br /&gt;then&lt;br /&gt;&lt;span style="font-style: italic;"&gt;pm.makePersistent(attachedDrunkard);&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;This solved the problem for me. Here's a &lt;a href="http://groups.google.com/group/google-appengine-java/browse_thread/thread/d83846d489517b4f/2335b60705e495c1?#2335b60705e495c1"&gt;link&lt;/a&gt; of a couple of alternative solutions.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-3834992813474383262?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/3834992813474383262/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=3834992813474383262' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/3834992813474383262'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/3834992813474383262'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2009/07/google-app-engine-spring-integration.html' title='Google App Engine - Spring Integration Issues'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-7469306275767122743</id><published>2009-04-14T17:58:00.013+08:00</published><updated>2009-08-20T18:42:49.894+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='beer radar'/><category scheme='http://www.blogger.com/atom/ns#' term='app engine'/><title type='text'>App Engine Tutorial : Creating the Beer Radar Server component</title><content type='html'>&lt;span style="font-weight: bold;"&gt;App Engine App #1.0 - Server Component for &lt;a href="http://www.androidph.com/2009/02/app-10-beer-radar.html"&gt;Android Application&lt;/a&gt; &lt;a href="http://www.androidph.com/2009/02/app-10-beer-radar.html"&gt;Beer Radar&lt;/a&gt;.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;I created the &lt;span style="font-size:130%;"&gt;&lt;a style="font-weight: bold;" href="http://www.androidph.com/2009/02/app-10-beer-radar.html"&gt;Beer Radar&lt;/a&gt;&lt;span style="font-weight: bold;"&gt; &lt;/span&gt;&lt;a style="font-weight: bold;" href="http://www.androidph.com/2009/02/app-10-beer-radar.html"&gt;Android Application&lt;/a&gt;&lt;/span&gt; last February 2009, and I was looking for a suitable Java server application. I don't know when it was announced, but I just heard about the Google App Engine support for Java last week (April 10, 2009).&lt;br /&gt;&lt;br /&gt;Here's the basic &lt;a style="font-weight: bold;" href="http://beerradar.appspot.com/"&gt;App Engine&lt;/a&gt;&lt;span style="font-weight: bold;"&gt; &lt;/span&gt;&lt;a style="font-weight: bold;" href="http://beerradar.appspot.com/"&gt;Application&lt;/a&gt; which I'll connect the Beer Radar app soon. :) &lt;a style="font-weight: bold;" href="http://beer.androidph.com/"&gt;http://beer.androidph.com/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://www.androidph.com/2009/02/app-10-beer-radar.html"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 281px; height: 400px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SeRkcNG_AWI/AAAAAAAAAWw/lIrFm4VxGXU/s400/000.PNG" alt="" id="BLOGGER_PHOTO_ID_5324491095176839522" border="0" /&gt;&lt;/a&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/So0oWXYM4FI/AAAAAAAAAck/DJ5OOpkf6WI/s1600-h/beer_radar.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 314px;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/So0oWXYM4FI/AAAAAAAAAck/DJ5OOpkf6WI/s400/beer_radar.JPG" alt="" id="BLOGGER_PHOTO_ID_5371994295220625490" border="0" /&gt;&lt;/a&gt;I quickly signed up to see what is it all about. So, here's what I learned so far.&lt;br /&gt;&lt;br /&gt;Here are the steps to create a web app using Google App Engine with Java Lanuage Support.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;1. Sign-up for an App Engine Account http://appengine.google.com/ you should click link for Java then click the sign-up button (I waited for 2 days for the confirmation). I don't have a screenshot for it, but its easy to spot.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;2. Download the Google App Engine SDK http://code.google.com/appengine/downloads.html&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;3. Install the App Engine Eclipse Plugin&lt;/span&gt;&lt;br /&gt;From the Eclipse Menu, go to HELP &gt; Software Update...&lt;br /&gt;Click the Available Software Tab&lt;br /&gt;Click Add Site, type http://dl.google.com/eclipse/plugin/3.4&lt;br /&gt;Then Install&lt;br /&gt;See  http://code.google.com/appengine/docs/java/tools/eclipse.html for more details.&lt;br /&gt;Restart Eclipse&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;4. Click the New Web Application Icon as shown below&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SeRfCdc23pI/AAAAAAAAAWo/h599ltUrgUM/s1600-h/AppEngine_01.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 308px; height: 141px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SeRfCdc23pI/AAAAAAAAAWo/h599ltUrgUM/s400/AppEngine_01.JPG" alt="" id="BLOGGER_PHOTO_ID_5324485155328810642" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;5. Type in the Project name and package. I unchecked the GWT option since I'm not going to use it.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SeRfCAX8b-I/AAAAAAAAAWg/2IKW9TUzAzk/s1600-h/AppEngine_02.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 313px; height: 400px;" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SeRfCAX8b-I/AAAAAAAAAWg/2IKW9TUzAzk/s400/AppEngine_02.JPG" alt="" id="BLOGGER_PHOTO_ID_5324485147523575778" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;6. Then click Finish. Everything is created for you, even the libraries that you need for your application.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SeRfCNZPVlI/AAAAAAAAAWY/IT3naAz6LTw/s1600-h/AppEngine_03.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 327px; height: 389px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SeRfCNZPVlI/AAAAAAAAAWY/IT3naAz6LTw/s400/AppEngine_03.JPG" alt="" id="BLOGGER_PHOTO_ID_5324485151018669650" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;7. Run the server by right-clicking on the project, select Debug As &gt; Web Application&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SeRfB2ULiKI/AAAAAAAAAWQ/utPP5S_tIOM/s1600-h/AppEngine_04.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 338px;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SeRfB2ULiKI/AAAAAAAAAWQ/utPP5S_tIOM/s400/AppEngine_04.JPG" alt="" id="BLOGGER_PHOTO_ID_5324485144823433378" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;8. If you have tomcat running by default, you'd probably get this error message&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;WARNING: failed SelectChannelConnector@127.0.0.1:8080&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;java.net.BindException: Address already in use: bind&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SeRfB-qQj4I/AAAAAAAAAWI/RjX_CJuUPeQ/s1600-h/AppEngine_05.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 171px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SeRfB-qQj4I/AAAAAAAAAWI/RjX_CJuUPeQ/s400/AppEngine_05.JPG" alt="" id="BLOGGER_PHOTO_ID_5324485147063521154" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;9. Fix this by going to the Debug Configurations, then on the Main Tab, set a new port or click "Automatically select an unused port".&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SeRex0ERzbI/AAAAAAAAAWA/yZ1WkO0dTkc/s1600-h/AppEngine_06.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 70px;" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SeRex0ERzbI/AAAAAAAAAWA/yZ1WkO0dTkc/s400/AppEngine_06.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484869341957554" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SeRex_WS6sI/AAAAAAAAAV4/hpnSMSiRAyc/s1600-h/AppEngine_07.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 141px;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SeRex_WS6sI/AAAAAAAAAV4/hpnSMSiRAyc/s400/AppEngine_07.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484872370318018" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;10. Click Debug.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;11. Now open your browser to http://localhost:8989.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;12. Now you can test your application.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SeRexi0z15I/AAAAAAAAAVw/1s0tnoUV2Fk/s1600-h/AppEngine_08.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 344px; height: 160px;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SeRexi0z15I/AAAAAAAAAVw/1s0tnoUV2Fk/s400/AppEngine_08.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484864713676690" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;13. Once you're done with you application and you already got the Google confirmation message, you can now create an application.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SeRexv_CNDI/AAAAAAAAAVg/K54NNQMUYU8/s1600-h/AppEngine_09_email.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 181px;" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SeRexv_CNDI/AAAAAAAAAVg/K54NNQMUYU8/s400/AppEngine_09_email.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484868246221874" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SeRexmJcBVI/AAAAAAAAAVo/43lCHsP9xhE/s1600-h/AppEngine_09.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 172px;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SeRexmJcBVI/AAAAAAAAAVo/43lCHsP9xhE/s400/AppEngine_09.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484865605502290" border="0" /&gt;&lt;/a&gt;&lt;span style="font-weight: bold;"&gt;14. Type in a unique Application Identifier and the Application Title. This will be used in deploying your application.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SeReenNZv5I/AAAAAAAAAVY/dSXZXrRsmSg/s1600-h/AppEngine_10.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 249px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SeReenNZv5I/AAAAAAAAAVY/dSXZXrRsmSg/s400/AppEngine_10.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484539473051538" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;15. Once everything is done, you can now deploy by clicking the Deploy App Engine Project icon.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SeReepI3SJI/AAAAAAAAAVQ/QIeC5EHSkPs/s1600-h/AppEngine_11.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 314px; height: 106px;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SeReepI3SJI/AAAAAAAAAVQ/QIeC5EHSkPs/s400/AppEngine_11.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484539990886546" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;16. You will need to click the App Engine project settings to enter your Application Identifier.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SeReebVBVvI/AAAAAAAAAVI/H-ZqZZYCANw/s1600-h/AppEngine_12.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 245px;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SeReebVBVvI/AAAAAAAAAVI/H-ZqZZYCANw/s400/AppEngine_12.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484536283780850" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;17. Enter you Application ID then type in a version then click OK.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SeReebm-CsI/AAAAAAAAAVA/DdsSjX4FqTk/s1600-h/AppEngine_13.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 339px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SeReebm-CsI/AAAAAAAAAVA/DdsSjX4FqTk/s400/AppEngine_13.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484536359062210" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;18. Enter your Google App Engine Account Email and Password and that is done.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SeReeFqJm_I/AAAAAAAAAU4/yyWAVg0FUW4/s1600-h/AppEngine_14.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 296px;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SeReeFqJm_I/AAAAAAAAAU4/yyWAVg0FUW4/s400/AppEngine_14.JPG" alt="" id="BLOGGER_PHOTO_ID_5324484530466823154" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;20. Here's the app  &lt;/span&gt;&lt;span style="font-weight: bold;font-size:130%;" &gt;&lt;a href="http://beerradar.appspot.com/"&gt;http://beerradar.appspot.com&lt;/a&gt;/&lt;/span&gt;&lt;span style="font-weight: bold;"&gt;  I deployed, to be used as the server component of the &lt;/span&gt;&lt;span style="font-weight: bold;font-size:130%;" &gt;&lt;a href="http://www.androidph.com/2009/02/app-10-beer-radar.html"&gt;Beer Radar project. &lt;/a&gt;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;21. AND YES, I had to put in the ads. ;)&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;&lt;br /&gt;&lt;/span&gt;What I really like about the app engine is the JDO support.&lt;br /&gt;&lt;br /&gt;Here's the code for my Persistent Object&lt;br /&gt;Beer.java&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;package com.androidph.beerserver;&lt;br /&gt;&lt;br /&gt;import java.text.SimpleDateFormat;&lt;br /&gt;import java.util.Date;&lt;br /&gt;&lt;br /&gt;import javax.jdo.annotations.IdGeneratorStrategy;&lt;br /&gt;import javax.jdo.annotations.IdentityType;&lt;br /&gt;import javax.jdo.annotations.PersistenceCapable;&lt;br /&gt;import javax.jdo.annotations.Persistent;&lt;br /&gt;import javax.jdo.annotations.PrimaryKey;&lt;br /&gt;&lt;br /&gt;@PersistenceCapable(identityType = IdentityType.APPLICATION)&lt;br /&gt;public class Beer {&lt;br /&gt;@PrimaryKey&lt;br /&gt;@Persistent(valueStrategy = IdGeneratorStrategy.IDENTITY)&lt;br /&gt;private Long id;&lt;br /&gt;&lt;br /&gt;@Persistent&lt;br /&gt;private String name;&lt;br /&gt;&lt;br /&gt;@Persistent&lt;br /&gt;private Double price;&lt;br /&gt;&lt;br /&gt;@Persistent&lt;br /&gt;private Date lastCallTime;&lt;br /&gt;&lt;br /&gt;@Persistent&lt;br /&gt;private String promotions;&lt;br /&gt;&lt;br /&gt;@Persistent&lt;br /&gt;private String address;&lt;br /&gt;&lt;br /&gt;@Persistent&lt;br /&gt;private Double longitude;&lt;br /&gt;&lt;br /&gt;@Persistent&lt;br /&gt;private Double latitude;&lt;br /&gt;&lt;br /&gt;public Long getId() {&lt;br /&gt;return id;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setId(Long id) {&lt;br /&gt;this.id = id;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getName() {&lt;br /&gt;return name;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setName(String name) {&lt;br /&gt;this.name = name;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public Double getPrice() {&lt;br /&gt;return price;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setPrice(Double price) {&lt;br /&gt;this.price = price;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public Date getLastCallTime() {&lt;br /&gt;return lastCallTime;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setLastCallTime(Date lastCallTime) {&lt;br /&gt;this.lastCallTime = lastCallTime;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;private SimpleDateFormat sdf = new SimpleDateFormat("HH:mm");&lt;br /&gt;&lt;br /&gt;public String getLastCallTimeString() {&lt;br /&gt;if(lastCallTime != null) {&lt;br /&gt;return sdf.format(lastCallTime);&lt;br /&gt;} else {&lt;br /&gt;return "-";&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getPromotions() {&lt;br /&gt;return promotions;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setPromotions(String promotions) {&lt;br /&gt;this.promotions = promotions;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getAddress() {&lt;br /&gt;return address;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setAddress(String address) {&lt;br /&gt;this.address = address;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public Double getLongitude() {&lt;br /&gt;return longitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setLongitude(Double longitude) {&lt;br /&gt;this.longitude = longitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public Double getLatitude() {&lt;br /&gt;return latitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setLatitude(Double latitude) {&lt;br /&gt;this.latitude = latitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String toString() {&lt;br /&gt;return id + " | " + name + " | " + price + " | " + lastCallTime + " | " + promotions + " | " + address + " | " + longitude + " | " + latitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public byte[] convertToStream() {&lt;br /&gt;return null;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void fromStream(byte[] data) {&lt;br /&gt;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Here's the code to get a Persistence Manager. I got this from the GuestBook demo included in the AppEngine SDK&lt;br /&gt;&lt;br /&gt;PMF.java&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;package com.androidph.beerserver;&lt;br /&gt;&lt;br /&gt;import javax.jdo.JDOHelper;&lt;br /&gt;import javax.jdo.PersistenceManagerFactory;&lt;br /&gt;&lt;br /&gt;public final class PMF {&lt;br /&gt;private static final PersistenceManagerFactory pmfInstance =&lt;br /&gt;JDOHelper.getPersistenceManagerFactory("transactions-optional");&lt;br /&gt;&lt;br /&gt;private PMF() {}&lt;br /&gt;&lt;br /&gt;public static PersistenceManagerFactory get() {&lt;br /&gt;return pmfInstance;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Here are code snippets on how to use the Persistence Manager.&lt;br /&gt;&lt;br /&gt;Persisting an Object&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;PersistenceManager persistenceManager = PMF.get()&lt;br /&gt;.getPersistenceManager();&lt;br /&gt;Beer beer = beerValidator.getBeer(name, address, price,&lt;br /&gt;lastCallTime, promotions, longitude, latitude);&lt;br /&gt;persistenceManager.makePersistent(beer);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Retrieving Data&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;String query = "select from " + Beer.class.getName()&lt;br /&gt;+ " order by name asc";&lt;br /&gt;List&lt;beer&gt; beerLocations = (List&lt;beer&gt;) persistenceManager&lt;br /&gt;.newQuery(query).execute();&lt;br /&gt;for (Beer beer : beerLocations) {&lt;br /&gt;beerServletData.addLog("beer.toString() : " + beer.toString());&lt;br /&gt;}&lt;br /&gt;&lt;/beer&gt;&lt;/beer&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-7469306275767122743?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/7469306275767122743/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=7469306275767122743' title='16 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/7469306275767122743'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/7469306275767122743'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2009/04/app-engine-tutorial-creating-beer-radar.html' title='App Engine Tutorial : Creating the Beer Radar Server component'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_WAOO_koVttQ/SeRkcNG_AWI/AAAAAAAAAWw/lIrFm4VxGXU/s72-c/000.PNG' height='72' width='72'/><thr:total>16</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-5962064773020449449</id><published>2009-02-08T11:32:00.011+08:00</published><updated>2009-02-08T12:06:20.474+08:00</updated><title type='text'>App #1.0 - Beer Radar</title><content type='html'>&lt;span style="font-size:100%;"&gt;&lt;span style="font-family:arial;"&gt;I want to create an application, where it downloads bar location and some necessary details such as price of a beer, location and last call time. Also, I want it to be plotted with the user's current GPS location. Also, I want to have a server where user's can upload their recommended bars so that other user's may see it on their screens.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a style="font-family: arial;" onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SY5SuFgDnuI/AAAAAAAAANI/Km7bFlJZGE4/s1600-h/000.PNG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 281px; height: 400px;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SY5SuFgDnuI/AAAAAAAAANI/Km7bFlJZGE4/s400/000.PNG" alt="" id="BLOGGER_PHOTO_ID_5300264763165744866" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Download Source Code Below.&lt;br /&gt;&lt;br /&gt;Objectives:&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;1. Download Bar Details from Server&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;* 2. Plot Bar Details with respect to the user's current gps location&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;3. Upload Bar Details to Server&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;4. Be able adjust the coverage of the radar (1 km - 10 km)&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;But for this tutorial, I just want to implement #2, since I still can't find a nice free server to host my server app.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;The MODEL&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-family:arial;"&gt;STEP 1. Create BeerLocation.java&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - this is just a POJO for the Bar Details. It also stores the longitude and latitude values of the Bar.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;package com.androidph.beer.model;&lt;br /&gt;&lt;br /&gt;import java.text.DecimalFormat;&lt;br /&gt;&lt;br /&gt;public class BeerLocation {&lt;br /&gt;&lt;br /&gt;private int id;&lt;br /&gt;private String name;&lt;br /&gt;private String price;&lt;br /&gt;private String description;&lt;br /&gt;private String lastCallTime;&lt;br /&gt;private double latitude;&lt;br /&gt;private double longitude;&lt;br /&gt;private DecimalFormat df = new DecimalFormat("####.##");&lt;br /&gt;&lt;br /&gt;public BeerLocation(String name, String price, String description,&lt;br /&gt;String lastCallTime, double latitude, double longitude) {&lt;br /&gt;this.name = name;&lt;br /&gt;this.price = price;&lt;br /&gt;this.description = description;&lt;br /&gt;this.lastCallTime = lastCallTime;&lt;br /&gt;this.latitude = latitude;&lt;br /&gt;this.longitude = longitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String toString() {&lt;br /&gt;return name + ", " + price + " ( " + df.format(longitude) + ", " + df.format(latitude) + " ) ";&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public BeerLocation() {&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public int getId() {&lt;br /&gt;return id;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setId(int id) {&lt;br /&gt;this.id = id;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getName() {&lt;br /&gt;return name;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setName(String name) {&lt;br /&gt;this.name = name;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getPrice() {&lt;br /&gt;return price;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setPrice(String price) {&lt;br /&gt;this.price = price;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getDescription() {&lt;br /&gt;return description;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setDescription(String description) {&lt;br /&gt;this.description = description;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getLastCallTime() {&lt;br /&gt;return lastCallTime;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setLastCallTime(String lastCallTime) {&lt;br /&gt;this.lastCallTime = lastCallTime;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public double getLatitude() {&lt;br /&gt;return latitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setLatitude(double latitude) {&lt;br /&gt;this.latitude = latitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public double getLongitude() {&lt;br /&gt;return longitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setLongitude(double longitude) {&lt;br /&gt;this.longitude = longitude;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;STEP 2. Create interface BarLocationService.java&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - contains the method to retrieve a List of Bar Details. Currently, the implementation is just hard-coded and will be replaced on the next iterations&lt;/span&gt;&lt;span style="font-family:arial;"&gt;of this application.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;package com.androidph.beer.model;&lt;br /&gt;&lt;br /&gt;import java.util.List;&lt;br /&gt;&lt;br /&gt;public interface BeerLocationService {&lt;br /&gt;public List retrieveAllBeerLocations();&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;STEP 3. Create BeerLocationServiceMemory.java&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - Just create a java.util.List and add BeerLocation to the list.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;package com.androidph.beer.model.impl;&lt;br /&gt;&lt;br /&gt;import java.util.ArrayList;&lt;br /&gt;import java.util.List;&lt;br /&gt;&lt;br /&gt;import com.androidph.beer.model.BeerLocation;&lt;br /&gt;import com.androidph.beer.model.BeerLocationService;&lt;br /&gt;&lt;br /&gt;public class BeerLocationServiceMemory implements BeerLocationService {&lt;br /&gt;&lt;br /&gt;private List beerLocations = new ArrayList();&lt;br /&gt;@Override&lt;br /&gt;public List retrieveAllBeerLocations() {&lt;br /&gt;beerLocations.add( new BeerLocation("Chili Pepper's", "Php45.0", "", "9:00AM", 50, 50));&lt;br /&gt;beerLocations.add( new BeerLocation("OTB", "Php45.0", "", "3:00AM", 0, 0));&lt;br /&gt;beerLocations.add( new BeerLocation("Gerry's Grill", "Php38.0", "", "00:00AM", 235, 100));&lt;br /&gt;beerLocations.add( new BeerLocation("Giligan's", "Php40.0", "", "03:00AM", 180, 150));&lt;br /&gt;return beerLocations;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;The VIEW&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-family:arial;"&gt;STEP 1. Create BeerRadarView&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - Extend the android.view.View class. The View class contains the onDraw(Canvas) method which is where the painting is done. The onDraw(Canvas)&lt;/span&gt; &lt;span style="font-family:arial;"&gt;method is similar to the paint(Graphics g) of AWT and/or Swing components. Even the draw methods are almost the same. (example. g.drawArc(...), &lt;/span&gt;&lt;span style="font-family:arial;"&gt;canvas.drawArc(...), g.drawLine(...), canvas.drawLine(...) and so forth. The only difference is that the canvas stores most of its paint/draw properties in a &lt;/span&gt;&lt;span style="font-family:arial;"&gt;Paint object.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - The Paint class stores common drawing properties such as color, font size, stoke etc.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - The coordinates are also the same for both canvas and graphics. 0,0 is the upperleft-most and MAX_WIDTH, MAX_HEIGHT is on the lower right-most.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;@Override&lt;br /&gt;protected void onDraw(Canvas canvas) {&lt;br /&gt;if(!hasInitialized) {&lt;br /&gt;initializeConstants();&lt;br /&gt;}&lt;br /&gt;drawRadarGrid(canvas);&lt;br /&gt;drawRadar(canvas);&lt;br /&gt;drawBeer(canvas, beerLocations);&lt;br /&gt;String currentLocation = "( " + df.format(currentLongitude) + ", " + df.format(currentLatitude) + " )";&lt;br /&gt;canvas.drawText(currentLocation, midpointX-30, midpointY-5, paintScreenText);&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;STEP 2. Drawing the Radar Grid&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - Just plot two lines that looks like a corsair.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;STEP 3. Drawing the Radar Circles&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - This uses the canvas.drawCircle(...) which actually is not on the graphics class. The canvas.drawArc(...), is different from the drawCircle, since&lt;/span&gt; &lt;span style="font-family:arial;"&gt;it uses a RectF to get the size of the arc/ellipse to be drawn.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;private void drawRadarGrid(Canvas canvas) {&lt;br /&gt;canvas.drawLine(0, midpointY, screenWidth, midpointY, paintRadarGrid);&lt;br /&gt;canvas.drawLine(midpointX, 0, midpointX, screenHeight, paintRadarGrid);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;STEP 4. Animated the Radar&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - Use the circle path formula&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;      &lt;span style="font-style: italic;"&gt;x = A cos(radian);&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;font-family:arial;" &gt;      y = A Sine(radian);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;      Where A is the amplitude.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - Since I am using 0-360 degrees for the angles, it is necessary to convert degrees to radians.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - &lt;span style="font-style: italic;"&gt;Radian = Angle * (PI / 180)&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;private void drawRadar(Canvas canvas) {&lt;br /&gt;if (startAngle &gt; 360) {&lt;br /&gt;startAngle = 0;&lt;br /&gt;}&lt;br /&gt;float x = (float) (minimumScreenSize / 2 * Math.cos(startAngle&lt;br /&gt;* (Math.PI / 180)));&lt;br /&gt;float y = (float) (minimumScreenSize / 2 * Math.sin(startAngle&lt;br /&gt;* (Math.PI / 180)));&lt;br /&gt;canvas.drawLine(getWidth() / 2, getHeight() / 2, x + getWidth() / 2, y&lt;br /&gt;+ getHeight() / 2, paintRadar);&lt;br /&gt;startAngle += 3;&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;STEP 5. Plotting the BeerLocation data.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - Plot the longitude and latitude of the BeerLocation with respect to the user's current GPS location&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - x =  (beerLoc.getLongitude() + midpointX - currentLongitude - BEER_ICON_SIZE);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;    Since the screens midpoint is not 0, the longitude must the adjusted. The + (positive) value of X should be in the WEST part of the screen. So the &lt;/span&gt;&lt;span style="font-family:arial;"&gt;midpoint of the X-axis must be added to the location's longitude. Also, to adjust it to the user's current location, the currentLongitude is subtracted. The &lt;/span&gt;&lt;span style="font-family:arial;"&gt;BEER_ICON_SIZE is subtracted just so it becomes centered.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - y = (midpointY - beerLoc.getLatitude() + currentLatitude - BEER_ICON_SIZE);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;    There's a slight difference between the computation of Y, since the + (positive) value of y should be on the NORTH part of the screen, thus, the &lt;/span&gt;&lt;span style="font-family:arial;"&gt;point is adjusted. So, midpoint of Y is subtracted with the beer location's latitude. Also, the currentLatitude is added to the equation.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - The maximum coverage is not yet adjustable yet. In the future, I'll modify so that the user can select a minimum radius of 1KM and a maximum radius &lt;/span&gt;&lt;span style="font-family:arial;"&gt;of 10KM. I currently do not know how each degrees of the longitude and latitude translates into KM. I'll research on it first.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;private void drawBeer(Canvas canvas, List beerLocations) {&lt;br /&gt;if(beerIcon == null) {&lt;br /&gt;beerIcon = BitmapFactory.decodeResource(this.getResources(), R.drawable.beer);&lt;br /&gt;}&lt;br /&gt;for(BeerLocation beerLoc : beerLocations) {&lt;br /&gt;float x =  (float)(beerLoc.getLongitude() + midpointX - currentLongitude - BEER_ICON_SIZE);&lt;br /&gt;float y = (float)(midpointY - beerLoc.getLatitude() + currentLatitude - BEER_ICON_SIZE);&lt;br /&gt;canvas.drawBitmap(beerIcon, x, y,  paintScreenText);&lt;br /&gt;canvas.drawText(beerLoc.toString(), x, y,  paintScreenText);&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;The ACTIVITY&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;STEP 1. Set the BeerRadarView as the Activity's contentView&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onCreate(Bundle savedInstanceState) {&lt;br /&gt;super.onCreate(savedInstanceState);&lt;br /&gt;beerRadarView = new BeerRadarView(this);&lt;br /&gt;setContentView(beerRadarView);&lt;br /&gt;setCurrentGpsLocation(null);&lt;br /&gt;thread = new Thread(new MyThreadRunner());&lt;br /&gt;thread.start();&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;STEP 2. Create a android.os.Handler that invalidate's the view when called. Invalidate is similar to calling awt/swing component's repaint() method.&lt;/span&gt;&lt;span style="font-family:arial;"&gt; &lt;span style="font-style: italic;font-size:85%;" &gt;&lt;span style="font-weight: bold;"&gt;&lt;br /&gt;&lt;br /&gt;"When a process is created for your application, its main thread is dedicated to running a message queue that takes care of managing &lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-style: italic;font-size:85%;" &gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;the top-level application objects (activities, intent receivers, etc) and any windows they create. You can create your own threads, and communicate back with&lt;/span&gt;&lt;span style="font-weight: bold;"&gt; &lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;the main application thread through a Handler. This is done by calling the same post or sendMessage methods as before, but from your new thread. The given Runnable or Message will than be scheduled in the Handler's message queue and processed when appropriate."&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;Handler updateHandler = new Handler() {&lt;br /&gt;/** Gets called on every message that is received */&lt;br /&gt;// @Override&lt;br /&gt;public void handleMessage(Message msg) {&lt;br /&gt;switch (msg.what) {&lt;br /&gt;case UPDATE_LOCATION: {&lt;br /&gt;beerRadarView.setCurrentLatitude(latitude);&lt;br /&gt;beerRadarView.setCurrentLongitude(longitude);&lt;br /&gt;break;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;beerRadarView.invalidate();&lt;br /&gt;super.handleMessage(msg);&lt;br /&gt;}&lt;br /&gt;};&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;STEP 3. implement android.location.LocationListener on the Activity&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class BeerRadar extends Activity implements LocationListener {&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - Implement the necessary methods.&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onLocationChanged(Location location) {&lt;br /&gt;setCurrentGpsLocation(location);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onProviderDisabled(String provider) {&lt;br /&gt;setCurrentGpsLocation(null);&lt;br /&gt;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onProviderEnabled(String provider) {&lt;br /&gt;setCurrentGpsLocation(null);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onStatusChanged(String provider, int status, Bundle extras) {&lt;br /&gt;setCurrentGpsLocation(null);&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;  - Use onLocationChanged(Location location) to update the user's current location&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;private void setCurrentGpsLocation(Location location) {&lt;br /&gt;if (location == null) {&lt;br /&gt;locationManager = (LocationManager) getSystemService(LOCATION_SERVICE);&lt;br /&gt;locationManager.requestLocationUpdates(&lt;br /&gt; LocationManager.GPS_PROVIDER, 0, 0, this);&lt;br /&gt;location = locationManager&lt;br /&gt; .getLastKnownLocation(LocationManager.GPS_PROVIDER);&lt;br /&gt;}&lt;br /&gt;longitude = location.getLongitude();&lt;br /&gt;latitude = location.getLatitude();&lt;br /&gt;Message msg = new Message();&lt;br /&gt;msg.what = UPDATE_LOCATION;&lt;br /&gt;BeerRadar.this.updateHandler.sendMessage(msg);&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;code style="font-family: arial; font-weight: bold;" location=""&gt;Testing&lt;/code&gt;&lt;/span&gt;  &lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;div style="text-align: center;"&gt;&lt;span style="font-size:100%;"&gt;&lt;code style="font-family: arial;" location=""&gt;Since it just an emulator, you can use the DDMS perspective to update the longitude and latitude.&lt;/code&gt;&lt;a style="font-family: arial;" onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SY5SuZU03II/AAAAAAAAANQ/vs1aq770Hcw/s1600-h/001.png"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 338px; height: 400px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SY5SuZU03II/AAAAAAAAANQ/vs1aq770Hcw/s400/001.png" alt="" id="BLOGGER_PHOTO_ID_5300264768487349378" border="0" /&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;span style="font-family:arial;"&gt;Longitude =50, Latitude = 50&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;/div&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;div style="text-align: center;"&gt;&lt;span style="font-size:100%;"&gt;&lt;a style="font-family: arial;" onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SY5SuYXAxMI/AAAAAAAAANY/avsa4XQKZWA/s1600-h/002.PNG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 393px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SY5SuYXAxMI/AAAAAAAAANY/avsa4XQKZWA/s400/002.PNG" alt="" id="BLOGGER_PHOTO_ID_5300264768228082882" border="0" /&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;span style="font-family:arial;"&gt;Longitude =120, Latitude = 100&lt;/span&gt;&lt;code style="font-family: arial;" location=""&gt;&lt;/code&gt;&lt;/span&gt;&lt;br /&gt;&lt;/div&gt;&lt;div style="text-align: center;"&gt;&lt;span style="font-size:100%;"&gt;&lt;code style="font-family: arial;" location=""&gt;&lt;/code&gt;&lt;/span&gt;&lt;/div&gt;&lt;span style="font-size:100%;"&gt;&lt;code style="font-family: arial;" location=""&gt;&lt;br /&gt;&lt;a href="http://mobileserver.byethost2.com/?p=95"&gt;Source Code&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.androidph.com/2008/11/camera-capture.html"&gt;Android Camera Capture Tutorial&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Reference: http://www.anddev.org/the_pizza_timer_-_threading-drawing_on_canvas-t126.html&lt;br /&gt;&lt;br /&gt;&lt;/code&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-5962064773020449449?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/5962064773020449449/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=5962064773020449449' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/5962064773020449449'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/5962064773020449449'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2009/02/app-10-beer-radar.html' title='App #1.0 - Beer Radar'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_WAOO_koVttQ/SY5SuFgDnuI/AAAAAAAAANI/Km7bFlJZGE4/s72-c/000.PNG' height='72' width='72'/><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-2388062612317671009</id><published>2008-11-24T00:52:00.016+08:00</published><updated>2009-01-30T14:23:32.509+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='sdcard'/><category scheme='http://www.blogger.com/atom/ns#' term='camera'/><category scheme='http://www.blogger.com/atom/ns#' term='picture'/><title type='text'>Camera Capture</title><content type='html'>&lt;span style="font-style: italic;font-family:arial;font-size:100%;"  &gt;Source code can be downloaded below.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Before creating the Image Capture application, the SDCard must be configured first in order to be able to save in the Picture Gallery of the emulator.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Creating the SDCARD&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;1. See the emulator -help-sdcard to see where the default sdcard.img is located. Create if necessary.&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SSmTE8vU7TI/AAAAAAAAAH4/KMRE02bOqyI/s1600-h/sd-card-help.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 202px;" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SSmTE8vU7TI/AAAAAAAAAH4/KMRE02bOqyI/s400/sd-card-help.JPG" alt="" id="BLOGGER_PHOTO_ID_5271906552047267122" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;2. Type mksdcard in the command line to know the required switches in the command-line.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SSmTXbsRJAI/AAAAAAAAAIA/D9FUilS57e8/s1600-h/mksdcard-help.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 202px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SSmTXbsRJAI/AAAAAAAAAIA/D9FUilS57e8/s400/mksdcard-help.JPG" alt="" id="BLOGGER_PHOTO_ID_5271906869593580546" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;3. Make SD Card.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SSmTmwMSYqI/AAAAAAAAAII/Pu3-50L0FOk/s1600-h/create-sd-card.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 205px;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SSmTmwMSYqI/AAAAAAAAAII/Pu3-50L0FOk/s400/create-sd-card.JPG" alt="" id="BLOGGER_PHOTO_ID_5271907132794626722" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;4. For my SD Card, I just went to the default folder on step#1 and created the default SD-Card. &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;-cd to the default sd directory&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;-mksdcard 16M sdcard.img&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;font-family:arial;" &gt;*Note: the minumum SD required by the emulator is 8Megabytes, I just used 16M to make sure. Also, the higher the size of the SD, the longer it takes to create. So, when you create a 4GB SD, the command line might seem unresponsive.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;I've been trying to figure out how to capture images in android and storing it in the picture gallery for 2 weeks now.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;I just discovered, that there is nothing wrong with the code, but there's something wrong with the emulator.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;For one thing, I keep on getting this image, even when using the built in Camera Application on the main menu. But, I think it is normal. Is it?&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SSmK7c4Hf4I/AAAAAAAAAHg/0e9TXFV-IAw/s1600-h/1227459143121.jpg"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 213px; height: 350px;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SSmK7c4Hf4I/AAAAAAAAAHg/0e9TXFV-IAw/s400/1227459143121.jpg" alt="" id="BLOGGER_PHOTO_ID_5271897592782356354" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;The problem I am having is that when I capture an image in the application, the File Explorer (sdcard/dcim/Camera) does save the image file. But when I check the gallery, it does not seem to exist. I then try to push an image to the emulator's file system (sdcard/dcim/Camera), but still the Picture Gallery does not reflect. Below, is a screenshot of what (sdcard/dcim/Camera) contains and what shows in the emulator's picture gallery.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SSmMHmw6BUI/AAAAAAAAAHo/HJYJwDpV8zI/s1600-h/sdcard-gallery-not-updated.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 238px;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SSmMHmw6BUI/AAAAAAAAAHo/HJYJwDpV8zI/s400/sdcard-gallery-not-updated.JPG" alt="" id="BLOGGER_PHOTO_ID_5271898901106525506" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;When I restarted the emulator, the Picture Gallery reflected the content's of the file system. Is this a bug or did I just missed a step?&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SSmMibDz6UI/AAAAAAAAAHw/MzZTU4aI63I/s1600-h/sdcard-gallery-updated-after-restart.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 143px;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SSmMibDz6UI/AAAAAAAAAHw/MzZTU4aI63I/s400/sdcard-gallery-updated-after-restart.JPG" alt="" id="BLOGGER_PHOTO_ID_5271899361821059394" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Anyways, here's the code I compiled from various sources using Google Android SDK 1R1.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;http://www.anddev.org/viewtopic.php?p=704#704&lt;br /&gt;http://www.anddev.org/viewtopic.php?p=645#645&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold; font-style: italic;font-family:arial;font-size:85%;"  &gt;I also used another site but I forgot the link. So if you see your code here, just drop me a message and I'll link you up as reference. I think the file I downloaded was CameraTestApi.zip but was based on an older SDK. I apologize for the author of the code that I based my revised Image Capture application.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Here the code for the Image Capture Application.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;1. Create two classes.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold; font-style: italic;font-family:arial;" &gt;ImageCapture.java&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;&lt;br /&gt;public class ImageCapture extends Activity implements SurfaceHolder.Callback&lt;br /&gt;{&lt;br /&gt;private Camera camera;&lt;br /&gt;private boolean isPreviewRunning = false;&lt;br /&gt;private SimpleDateFormat timeStampFormat = new SimpleDateFormat("yyyyMMddHHmmssSS");&lt;br /&gt;&lt;br /&gt;private SurfaceView surfaceView;&lt;br /&gt;private SurfaceHolder surfaceHolder;&lt;br /&gt;private Uri target = Media.EXTERNAL_CONTENT_URI;&lt;br /&gt;&lt;br /&gt;public void onCreate(Bundle icicle)&lt;br /&gt;{&lt;br /&gt;super.onCreate(icicle);&lt;br /&gt;Log.e(getClass().getSimpleName(), "onCreate");&lt;br /&gt;getWindow().setFormat(PixelFormat.TRANSLUCENT);&lt;br /&gt;setContentView(R.layout.main);&lt;br /&gt;surfaceView = (SurfaceView)findViewById(R.id.surface);&lt;br /&gt;surfaceHolder = surfaceView.getHolder();&lt;br /&gt;surfaceHolder.addCallback(this);&lt;br /&gt;surfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public boolean onCreateOptionsMenu(android.view.Menu menu) {&lt;br /&gt;MenuItem item = menu.add(0, 0, 0, "goto gallery");&lt;br /&gt;item.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() {&lt;br /&gt; public boolean onMenuItemClick(MenuItem item) {&lt;br /&gt;     Intent intent = new Intent(Intent.ACTION_VIEW, target);&lt;br /&gt;     startActivity(intent);&lt;br /&gt;     return true;&lt;br /&gt; }&lt;br /&gt;});&lt;br /&gt;return true;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;protected void onRestoreInstanceState(Bundle savedInstanceState)&lt;br /&gt;{&lt;br /&gt;super.onRestoreInstanceState(savedInstanceState);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;Camera.PictureCallback mPictureCallbackRaw = new Camera.PictureCallback() {&lt;br /&gt;public void onPictureTaken(byte[] data, Camera c) {&lt;br /&gt; Log.e(getClass().getSimpleName(), "PICTURE CALLBACK RAW: " + data);&lt;br /&gt; camera.startPreview();&lt;br /&gt;}&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;Camera.PictureCallback mPictureCallbackJpeg= new Camera.PictureCallback() {&lt;br /&gt;public void onPictureTaken(byte[] data, Camera c) {&lt;br /&gt; Log.e(getClass().getSimpleName(), "PICTURE CALLBACK JPEG: data.length = " + data);&lt;br /&gt;}&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;Camera.ShutterCallback mShutterCallback = new Camera.ShutterCallback() {&lt;br /&gt;public void onShutter() {&lt;br /&gt;Log.e(getClass().getSimpleName(), "SHUTTER CALLBACK");&lt;br /&gt;}&lt;br /&gt;};&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;public boolean onKeyDown(int keyCode, KeyEvent event)&lt;br /&gt;{&lt;br /&gt;ImageCaptureCallback iccb = null;&lt;br /&gt;if(keyCode == KeyEvent.KEYCODE_DPAD_CENTER) {&lt;br /&gt;try {&lt;br /&gt;String filename = timeStampFormat.format(new Date());&lt;br /&gt;ContentValues values = new ContentValues();&lt;br /&gt;values.put(Media.TITLE, filename);&lt;br /&gt;values.put(Media.DESCRIPTION, "Image capture by camera");&lt;br /&gt;Uri uri = getContentResolver().insert(Media.EXTERNAL_CONTENT_URI, values);&lt;br /&gt;//String filename = timeStampFormat.format(new Date());&lt;br /&gt;iccb = new ImageCaptureCallback( getContentResolver().openOutputStream(uri));&lt;br /&gt;} catch(Exception ex ){&lt;br /&gt;ex.printStackTrace();&lt;br /&gt;Log.e(getClass().getSimpleName(), ex.getMessage(), ex);&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;if (keyCode == KeyEvent.KEYCODE_BACK) {&lt;br /&gt; return super.onKeyDown(keyCode, event);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;if (keyCode == KeyEvent.KEYCODE_DPAD_CENTER) {&lt;br /&gt; camera.takePicture(mShutterCallback, mPictureCallbackRaw, iccb);&lt;br /&gt; return true;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;return false;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;protected void onResume()&lt;br /&gt;{&lt;br /&gt;Log.e(getClass().getSimpleName(), "onResume");&lt;br /&gt;super.onResume();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;protected void onSaveInstanceState(Bundle outState)&lt;br /&gt;{&lt;br /&gt;super.onSaveInstanceState(outState);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;protected void onStop()&lt;br /&gt;{&lt;br /&gt;Log.e(getClass().getSimpleName(), "onStop");&lt;br /&gt;super.onStop();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void surfaceCreated(SurfaceHolder holder)&lt;br /&gt;{&lt;br /&gt;Log.e(getClass().getSimpleName(), "surfaceCreated");&lt;br /&gt;camera = Camera.open();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void surfaceChanged(SurfaceHolder holder, int format, int w, int h)&lt;br /&gt;{&lt;br /&gt;Log.e(getClass().getSimpleName(), "surfaceChanged");&lt;br /&gt;if (isPreviewRunning) {&lt;br /&gt; camera.stopPreview();&lt;br /&gt;}&lt;br /&gt;Camera.Parameters p = camera.getParameters();&lt;br /&gt;p.setPreviewSize(w, h);&lt;br /&gt;camera.setParameters(p);&lt;br /&gt;camera.setPreviewDisplay(holder);&lt;br /&gt;camera.startPreview();&lt;br /&gt;isPreviewRunning = true;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void surfaceDestroyed(SurfaceHolder holder)&lt;br /&gt;{&lt;br /&gt;Log.e(getClass().getSimpleName(), "surfaceDestroyed");&lt;br /&gt;camera.stopPreview();&lt;br /&gt;isPreviewRunning = false;&lt;br /&gt;camera.release();&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic; font-weight: bold;font-family:arial;" &gt;ImageCaptureCallback.java&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class ImageCaptureCallback implements PictureCallback  {&lt;br /&gt;&lt;br /&gt;private OutputStream filoutputStream;&lt;br /&gt;public ImageCaptureCallback(OutputStream filoutputStream) {&lt;br /&gt;this.filoutputStream = filoutputStream;&lt;br /&gt;}&lt;br /&gt;@Override&lt;br /&gt;public void onPictureTaken(byte[] data, Camera camera) {&lt;br /&gt;try {&lt;br /&gt;Log.v(getClass().getSimpleName(), "onPictureTaken=" + data + " length = " + data.length);&lt;br /&gt;filoutputStream.write(data);&lt;br /&gt;filoutputStream.flush();&lt;br /&gt;filoutputStream.close();&lt;br /&gt;} catch(Exception ex) {&lt;br /&gt;ex.printStackTrace();&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;2. Create the main.xml as shown below&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;&lt;br /&gt;&lt;linearlayout android="http://schemas.android.com/apk/res/android" layout_width="fill_parent" layout_height="fill_parent" orientation="vertical"&gt;&lt;br /&gt;&lt;surfaceview id="@+id/surface" layout_width="fill_parent" layout_height="10dip" layout_weight="1"&gt;&lt;br /&gt;&lt;/surfaceview&gt;&lt;br /&gt;&lt;/linearlayout&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;3.  Add a camera permission to the ApplicationManifest&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;&lt;uses-permission name="android.permission.CAMERA"&gt;&lt;br /&gt;&lt;/uses-permission&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://mobileserver.byethost2.com/?p=45"&gt;Source Code&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-2388062612317671009?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/2388062612317671009/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=2388062612317671009' title='20 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/2388062612317671009'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/2388062612317671009'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2008/11/camera-capture.html' title='Camera Capture'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://3.bp.blogspot.com/_WAOO_koVttQ/SSmTE8vU7TI/AAAAAAAAAH4/KMRE02bOqyI/s72-c/sd-card-help.JPG' height='72' width='72'/><thr:total>20</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-2504023312611481406</id><published>2008-10-27T01:27:00.015+08:00</published><updated>2009-04-10T15:01:33.080+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='mapviewer'/><title type='text'>Android Map Viewer</title><content type='html'>&lt;span style="font-weight: bold;font-family:arial;" &gt;1.   Create MapViewer Project&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;      - Create MapViewer class that extends MapActivity&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;package javapadawan.android;&lt;br /&gt;&lt;br /&gt;import android.os.Bundle;&lt;br /&gt;import android.view.KeyEvent;&lt;br /&gt;import com.google.android.maps.MapActivity;&lt;br /&gt;import com.google.android.maps.MapController;&lt;br /&gt;import com.google.android.maps.MapView;&lt;br /&gt;&lt;br /&gt;public class MapViewer extends MapActivity {&lt;br /&gt;private MapView map;&lt;br /&gt;private MapController mc;&lt;br /&gt;private static int zoomValue = 1;&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onCreate(Bundle savedInstanceState) {&lt;br /&gt;  super.onCreate(savedInstanceState);&lt;br /&gt;  setContentView(R.layout.main);&lt;br /&gt;  map = (MapView) findViewById(R.id.map);&lt;br /&gt;  mc = map.getController();&lt;br /&gt;  mc.setZoom(zoomValue);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public boolean dispatchKeyEvent(KeyEvent event) {&lt;br /&gt;if(event.getKeyCode() == KeyEvent.KEYCODE_DPAD_UP) {&lt;br /&gt;zoomValue = zoomValue + 1;&lt;br /&gt;mc.setZoom(zoomValue);&lt;br /&gt;} else if(event.getKeyCode() == KeyEvent.KEYCODE_DPAD_DOWN) {&lt;br /&gt;zoomValue = zoomValue - 1;&lt;br /&gt;mc.setZoom(zoomValue);&lt;br /&gt;} else if(event.getKeyCode() == KeyEvent.KEYCODE_DPAD_LEFT) {&lt;br /&gt;map.setSatellite(false);&lt;br /&gt;} else if(event.getKeyCode() == KeyEvent.KEYCODE_DPAD_RIGHT) {&lt;br /&gt;map.setSatellite(true);&lt;br /&gt;}&lt;br /&gt;return super.dispatchKeyEvent(event);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;protected boolean isRouteDisplayed() {&lt;br /&gt;return false;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;2. Modify main.xml &lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;&lt;br /&gt;&lt;linearlayout android="http://schemas.android.com/apk/res/android" id="@+id/main" layout_width="fill_parent" layout_height="fill_parent"&gt;&lt;br /&gt;&lt;com.google.android.maps.mapview id="@+id/map" layout_width="fill_parent" layout_height="fill_parent" enabled="true" clickable="true" apikey="replaceOwnKey"&gt;&lt;/com.google.android.maps.mapview&gt;&lt;br /&gt;&lt;/linearlayout&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;3. Set the required permissions in the AndroidManifest.xml&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;&lt;manifest android="http://schemas.android.com/apk/res/android" package="javapadawan.android" versioncode="1" versionname="1.0.0"&gt;&lt;br /&gt;&lt;application icon="@drawable/icon" label="@string/app_name"&gt;&lt;br /&gt;&lt;uses-library name="com.google.android.maps"&gt;&lt;/uses-library&gt;&lt;br /&gt;  &lt;activity name=".MapViewer" label="@string/app_name"&gt;&lt;br /&gt;      &lt;intent-filter&gt;&lt;br /&gt;          &lt;action name="android.intent.action.MAIN"&gt;&lt;/action&gt;&lt;br /&gt;          &lt;category name="android.intent.category.LAUNCHER"&gt;&lt;/category&gt;&lt;br /&gt;      &lt;/intent-filter&gt;&lt;br /&gt;  &lt;/activity&gt;&lt;br /&gt;&lt;/application&gt;&lt;br /&gt;&lt;uses-permission name="android.permission.ACCESS_COARSE_LOCATION"&gt;&lt;/uses-permission&gt;&lt;br /&gt;&lt;uses-permission name="android.permission.ACCESS_FINE_LOCATION"&gt;&lt;/uses-permission&gt;&lt;br /&gt;&lt;uses-permission name="android.permission.INTERNET"&gt;&lt;/uses-permission&gt;&lt;br /&gt;&lt;/manifest&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;4. Clean, Build and Run the Project. You will see an Empty Map Grid instead of a google map.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SQSoqN7bi1I/AAAAAAAAAHY/Ok1mZC7FIRw/s1600-h/01.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 204px; height: 400px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SQSoqN7bi1I/AAAAAAAAAHY/Ok1mZC7FIRw/s400/01.JPG" alt="" id="BLOGGER_PHOTO_ID_5261515707922484050" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;4. The reason why the code does not work is that the apiKey needs to be a valid key from google. Below are the steps to obtain a valid key. &lt;/span&gt;&lt;br /&gt;&lt;br /&gt;- &lt;a href="http://developer.android.com/guide/topics/location/geo/mapkey.html"&gt;Obtaining a Maps API Key&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;- Edit the main.xml and replace apiKey with the value from google. See below on how to generate an MD5 Certificate fingerprint.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SQSop1X5dqI/AAAAAAAAAHQ/VhTUF3k5vVo/s1600-h/02.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 400px; height: 91px;" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SQSop1X5dqI/AAAAAAAAAHQ/VhTUF3k5vVo/s400/02.JPG" alt="" id="BLOGGER_PHOTO_ID_5261515701330998946" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;5. Now clean, build and compile again. Click the UP/Down to ZOOM, and LEFT/RIGHT to switch Map View and Satellite View. &lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SQSophPd5FI/AAAAAAAAAHI/R3QvEx-aNns/s1600-h/03.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 229px; height: 400px;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SQSophPd5FI/AAAAAAAAAHI/R3QvEx-aNns/s400/03.JPG" alt="" id="BLOGGER_PHOTO_ID_5261515695926928466" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SQSopfVgtbI/AAAAAAAAAHA/5n3HUlXaGqc/s1600-h/04.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer; width: 227px; height: 400px;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SQSopfVgtbI/AAAAAAAAAHA/5n3HUlXaGqc/s400/04.JPG" alt="" id="BLOGGER_PHOTO_ID_5261515695415408050" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;6. Now that I got Map View to work, maybe I'll create something useful next time.&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;a href="http://mobileserver.byethost2.com/?p=41"&gt;&lt;span style="font-family:arial;"&gt;Source Code&lt;/span&gt;&lt;/a&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-2504023312611481406?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/2504023312611481406/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=2504023312611481406' title='6 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/2504023312611481406'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/2504023312611481406'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2008/10/android-map-viewer.html' title='Android Map Viewer'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_WAOO_koVttQ/SQSoqN7bi1I/AAAAAAAAAHY/Ok1mZC7FIRw/s72-c/01.JPG' height='72' width='72'/><thr:total>6</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-5280906251766706113</id><published>2008-10-19T23:35:00.004+08:00</published><updated>2009-06-13T18:10:45.097+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='ListActivity'/><category scheme='http://www.blogger.com/atom/ns#' term='sqlite'/><category scheme='http://www.blogger.com/atom/ns#' term='database'/><category scheme='http://www.blogger.com/atom/ns#' term='SQLiteOpenHelper'/><title type='text'>Android Simple SQLiteDatabase</title><content type='html'>&lt;div style="text-align: center;"&gt;Account List&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SPtTPpD1mwI/AAAAAAAAAGI/DuA-HTXM-4I/s1600-h/01.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SPtTPpD1mwI/AAAAAAAAAGI/DuA-HTXM-4I/s400/01.JPG" alt="" id="BLOGGER_PHOTO_ID_5258888518070278914" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;/div&gt;&lt;div style="text-align: center;"&gt;&lt;span style="font-family:arial;"&gt;New Account&lt;/span&gt;&lt;br /&gt;&lt;/div&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SPtTPxdrHMI/AAAAAAAAAGQ/pC9ljGJ0NZk/s1600-h/02.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SPtTPxdrHMI/AAAAAAAAAGQ/pC9ljGJ0NZk/s400/02.JPG" alt="" id="BLOGGER_PHOTO_ID_5258888520326126786" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;div style="text-align: center; font-family: arial;"&gt;Modify Account&lt;br /&gt;&lt;/div&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SPtTP2KDUpI/AAAAAAAAAGY/bLePd5Qmap8/s1600-h/03.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SPtTP2KDUpI/AAAAAAAAAGY/bLePd5Qmap8/s400/03.JPG" alt="" id="BLOGGER_PHOTO_ID_5258888521586004626" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;font-family:arial;" &gt;Source Code can be downloaded below.&lt;/span&gt; Also, the syntaxhighlighter for the XML code, has some problems. For some reason, the JS and CSS I used modifies the XML I place. Just check with the code downloadable below for the correct xml files.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;New Classes Used:&lt;/span&gt;&lt;br /&gt;&lt;a style="font-family: arial;" href="http://code.google.com/android/reference/android/app/ListActivity.html"&gt;ListActivity&lt;/a&gt;&lt;br /&gt;&lt;a style="font-family: arial;" href="http://code.google.com/android/reference/android/database/sqlite/SQLiteOpenHelper.html"&gt;SQLiteOpenHelper&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;1. Create new Android Project.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;     -Activity Name: AccountList&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;2. Create View Classes and XML&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;     &lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;2.1 Create &lt;/span&gt;&lt;span style="font-style: italic; font-weight: bold;font-family:arial;" &gt;account_list.xml&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;&lt;br /&gt;&lt;linearlayout android="http://schemas.android.com/apk/res/android" orientation="vertical" layout_width="wrap_content" layout_height="wrap_content"&gt;&lt;br /&gt;&lt;listview id="@+id/android:list" layout_width="wrap_content" layout_height="wrap_content"&gt;&lt;br /&gt;&lt;textview id="@+id/android:empty" layout_width="wrap_content" layout_height="wrap_content" text="@string/listEmpty"&gt;&lt;br /&gt;&lt;/textview&gt;&lt;br /&gt;&lt;br /&gt;&lt;/listview&gt;&lt;/linearlayout&gt;&lt;/pre&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;account_row.xml&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;&lt;br /&gt;&lt;textview id="@+id/tfServerName" android="http://schemas.android.com/apk/res/android" layout_width="wrap_content" layout_height="wrap_content"&gt;&lt;br /&gt;&lt;/textview&gt;&lt;/pre&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;     2.2. Create &lt;/span&gt;&lt;span style="font-style: italic; font-weight: bold;font-family:arial;" &gt;ListActivity&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt; class &lt;/span&gt;&lt;span style="font-style: italic; font-weight: bold;font-family:arial;" &gt;AccountList&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class AccountList extends ListActivity {&lt;br /&gt;/** Called when the activity is first created. */&lt;br /&gt;@Override&lt;br /&gt;public void onCreate(Bundle savedInstanceState) {&lt;br /&gt;super.onCreate(savedInstanceState);&lt;br /&gt;setContentView(R.layout.account_list);&lt;br /&gt;initComponents();&lt;br /&gt;}&lt;br /&gt;private void initComponents() {&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;2.3 Create &lt;/span&gt;&lt;span style="font-style: italic; font-weight: bold;font-family:arial;" &gt;account_detail.xml&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Below is an example of combining two or more layouts.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;&lt;br /&gt;&lt;linearlayout android="http://schemas.android.com/apk/res/android" orientation="vertical" layout_width="fill_parent" layout_height="fill_parent"&gt;&lt;br /&gt;&lt;textview layout_width="wrap_content" layout_height="wrap_content" text="@string/tvId"&gt;&lt;br /&gt;&lt;textview id="@+id/tvId" layout_width="wrap_content" layout_height="wrap_content" text=""&gt;&lt;br /&gt;&lt;textview layout_width="wrap_content" layout_height="wrap_content" text="@string/tvServerName"&gt;&lt;br /&gt;&lt;edittext id="@+id/etServerName" layout_width="fill_parent" layout_height="wrap_content"&gt;&lt;br /&gt;&lt;br /&gt;&lt;textview layout_width="wrap_content" layout_height="wrap_content" text="@string/tvUsername"&gt;&lt;br /&gt;&lt;edittext id="@+id/etUsername" layout_width="fill_parent" layout_height="wrap_content"&gt;&lt;br /&gt;&lt;br /&gt;&lt;textview layout_width="wrap_content" layout_height="wrap_content" text="@string/tvPassword"&gt;&lt;br /&gt;&lt;edittext id="@+id/etPassword" layout_width="fill_parent" layout_height="wrap_content"&gt;&lt;br /&gt;&lt;br /&gt;&lt;relativelayout android="http://schemas.android.com/apk/res/android" layout_width="fill_parent" layout_height="wrap_content"&gt;&lt;br /&gt;&lt;button id="@+id/btnSave" layout_width="wrap_content" layout_height="wrap_content" text="@string/btnSave"&gt;&lt;br /&gt;&lt;br /&gt;&lt;/button&gt;&lt;/relativelayout&gt;&lt;br /&gt;&lt;/edittext&gt;&lt;br /&gt;&lt;/textview&gt;&lt;/edittext&gt;&lt;/textview&gt;&lt;/edittext&gt;&lt;/textview&gt;&lt;/textview&gt;&lt;/textview&gt;&lt;/linearlayout&gt;&lt;/pre&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt; &lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;2.4. Create &lt;/span&gt;&lt;span style="font-style: italic; font-weight: bold;font-family:arial;" &gt;Activity&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt; class &lt;/span&gt;&lt;span style="font-style: italic; font-weight: bold;font-family:arial;" &gt;AccountDetail&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class AccountDetail extends Activity {&lt;br /&gt;public void onCreate(Bundle savedInstanceState) {&lt;br /&gt;super.onCreate(savedInstanceState);&lt;br /&gt;setContentView(R.layout.account_detail);&lt;br /&gt;initComponents();&lt;br /&gt;}&lt;br /&gt;private void initComponents() {&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;3. Create Model Classes&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;     &lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;3.1 Create Account class&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class Account {&lt;br /&gt;public static final String COL_ROW_ID = "_id";&lt;br /&gt;public static final String COL_SERVER_NAME = "server_name";&lt;br /&gt;public static final String COL_USERNAME = "username";&lt;br /&gt;public static final String COL_PASSWORD = "password";&lt;br /&gt;public static final String SQL_TABLE_NAME = "account_db";&lt;br /&gt;public static final String SQL_CREATE_TABLE = "CREATE TABLE "&lt;br /&gt;+ SQL_TABLE_NAME + " "&lt;br /&gt;+ " (_id integer primary key autoincrement, "&lt;br /&gt;+ "server_name text not null, username text not null, "&lt;br /&gt;+ "password text not null); ";&lt;br /&gt;&lt;br /&gt;public int getId() {&lt;br /&gt;return id;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setId(int id) {&lt;br /&gt;this.id = id;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getUsername() {&lt;br /&gt;return username;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setUsername(String username) {&lt;br /&gt;this.username = username;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getPassword() {&lt;br /&gt;return password;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setPassword(String password) {&lt;br /&gt;this.password = password;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getServerName() {&lt;br /&gt;return serverName;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setServerName(String serverName) {&lt;br /&gt;this.serverName = serverName;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;private String username;&lt;br /&gt;&lt;br /&gt;private String password;&lt;br /&gt;&lt;br /&gt;private String serverName;&lt;br /&gt;&lt;br /&gt;private int id;&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt; &lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;3.2 Create ActiveRecord interface&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;This is the interface that will be extend by POJO to make it a sort-of Active Domain. I'm not really experienced with the Active Domain pattern but this is my understanding of it. So just correct me if I am wrong and I'll change the code.&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public interface ActiveRecord {&lt;br /&gt;public long save();&lt;br /&gt;public boolean delete();&lt;br /&gt;public void load(Activity activity);&lt;br /&gt;public Cursor retrieveAll();&lt;br /&gt;public void setSQLiteDatabase(SQLiteDatabase sqliteDb);&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;3.3 Extend SQLiteOpenHelper &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;I derived  MyDatabaseAdapter class from &lt;/span&gt;&lt;br /&gt;&lt;a style="font-family: arial;" href="http://code.google.com/android/intro/tutorial.html"&gt;Tutorial: A Notepad Application&lt;/a&gt;&lt;span style="font-family:arial;"&gt;, However I made the MyDatabaseAdapter as a utility class instead of placing CRUD functions inside it. I made the Controller a sort-of Active Domain pattern so that the MyDatabaseAdapter can be re-used for future applications.&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class MyDatabaseAdapter extends SQLiteOpenHelper {&lt;br /&gt;private static SQLiteDatabase sqliteDb;&lt;br /&gt;private static MyDatabaseAdapter instance;&lt;br /&gt;&lt;br /&gt;private static final String DATABASE_NAME = "simple_sqlite_db";&lt;br /&gt;private static final int DATABASE_VERSION = 1;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;private MyDatabaseAdapter(Context context, String name, CursorFactory factory, int version) {&lt;br /&gt;super(context, name, factory, version);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onCreate(SQLiteDatabase db) {&lt;br /&gt;db.execSQL(Account.SQL_CREATE_TABLE);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {&lt;br /&gt;Log.w(getClass().getSimpleName(), "Upgrading database from version " + oldVersion + " to "&lt;br /&gt;       + newVersion + ", which will destroy all old data");&lt;br /&gt;db.execSQL("DROP TABLE IF EXISTS " + Account.SQL_TABLE_NAME );&lt;br /&gt;onCreate(db);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;private static void initialize(Context context) {&lt;br /&gt;if(instance == null) {&lt;br /&gt;instance = new MyDatabaseAdapter(context, DATABASE_NAME, null, DATABASE_VERSION);&lt;br /&gt;sqliteDb = instance.getWritableDatabase();&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public static final MyDatabaseAdapter getInstance(Context context) {&lt;br /&gt;initialize(context);&lt;br /&gt;return instance;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public SQLiteDatabase getDatabase() {&lt;br /&gt;return sqliteDb;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void close() {&lt;br /&gt;if(instance != null ) {&lt;br /&gt;instance.close();&lt;br /&gt;instance = null;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt; &lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;3.4 Create implementation of &lt;span style="font-style: italic;"&gt;ActiveRecord&lt;/span&gt; on &lt;span style="font-style: italic;"&gt;Account &lt;/span&gt;class&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Here's the code that implements the CRUD methods of the ActiveRecord interface. I also learned that from the Notepad Tutorial, since the Android Docs, does not really explain how to use SQLiteDB, or maybe I just do not know where to look.&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class Account implements ActiveRecord {&lt;br /&gt;&lt;br /&gt;public static final String COL_ROW_ID = "_id";&lt;br /&gt;public static final String COL_SERVER_NAME = "server_name";&lt;br /&gt;public static final String COL_USERNAME = "username";&lt;br /&gt;public static final String COL_PASSWORD = "password";&lt;br /&gt;&lt;br /&gt;public static final String SQL_TABLE_NAME = "account_db";&lt;br /&gt;public static final String SQL_CREATE_TABLE = "CREATE TABLE "&lt;br /&gt;+ SQL_TABLE_NAME + " "&lt;br /&gt;+ " (_id integer primary key autoincrement, "&lt;br /&gt;+ "server_name text not null, username text not null, "&lt;br /&gt;+ "password text not null); ";&lt;br /&gt;&lt;br /&gt;private SQLiteDatabase sqliteDatabase;&lt;br /&gt;&lt;br /&gt;public int getId() {&lt;br /&gt;return id;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setId(int id) {&lt;br /&gt;this.id = id;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getUsername() {&lt;br /&gt;return username;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setUsername(String username) {&lt;br /&gt;this.username = username;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getPassword() {&lt;br /&gt;return password;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setPassword(String password) {&lt;br /&gt;this.password = password;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public String getServerName() {&lt;br /&gt;return serverName;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void setServerName(String serverName) {&lt;br /&gt;this.serverName = serverName;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;private String username;&lt;br /&gt;&lt;br /&gt;private String password;&lt;br /&gt;&lt;br /&gt;private String serverName;&lt;br /&gt;&lt;br /&gt;private int id;&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void load(Activity activity) {&lt;br /&gt;Cursor cursor = sqliteDatabase.query(true, SQL_TABLE_NAME,&lt;br /&gt;new String[] { COL_ROW_ID, COL_SERVER_NAME, COL_USERNAME,&lt;br /&gt;COL_PASSWORD }, COL_ROW_ID + "=" + id, null, null,&lt;br /&gt;null, null, null);&lt;br /&gt;if (cursor != null) {&lt;br /&gt;cursor.moveToFirst();&lt;br /&gt;activity.startManagingCursor(cursor);&lt;br /&gt;setId(cursor.getInt(cursor&lt;br /&gt;.getColumnIndex(COL_ROW_ID)));&lt;br /&gt;setPassword(cursor.getString(cursor&lt;br /&gt;.getColumnIndex(COL_PASSWORD)));&lt;br /&gt;setUsername(cursor.getString(cursor&lt;br /&gt;.getColumnIndex(COL_USERNAME)));&lt;br /&gt;setServerName(cursor.getString(cursor&lt;br /&gt;.getColumnIndex(COL_SERVER_NAME)));&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public Cursor retrieveAll() {&lt;br /&gt;return sqliteDatabase.query(SQL_TABLE_NAME, new String[] { COL_ROW_ID,&lt;br /&gt;COL_SERVER_NAME, COL_USERNAME, COL_PASSWORD }, null, null,&lt;br /&gt;null, null, null);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public long save() {&lt;br /&gt;ContentValues values = new ContentValues();&lt;br /&gt;if (id &lt;= 0) {    values.put(COL_SERVER_NAME, serverName);    values.put(COL_USERNAME, username);    values.put(COL_PASSWORD, password);    return sqliteDatabase.insert(SQL_TABLE_NAME, null, values);   } else {    values.put(COL_SERVER_NAME, serverName);    values.put(COL_USERNAME, username);    values.put(COL_PASSWORD, password);    return sqliteDatabase.update(SQL_TABLE_NAME, values, COL_ROW_ID      + "=" + id, null);   }  }   public boolean delete() {   return sqliteDatabase.delete(SQL_TABLE_NAME, COL_ROW_ID + "=" + id,     null) &gt; 0;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void setSQLiteDatabase(SQLiteDatabase sqliteDatabase) {&lt;br /&gt;this.sqliteDatabase = sqliteDatabase;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;4. Create Controllers&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;     4.1 &lt;span style="font-style: italic;"&gt;AccountList &lt;/span&gt;Controllers&lt;/span&gt;&lt;br /&gt;For the AccountList I used the OptionsMenu.&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class AccountList extends ListActivity {&lt;br /&gt;/** Called when the activity is first created. */&lt;br /&gt;private MyDatabaseAdapter myDatabaseAdapter;&lt;br /&gt;&lt;br /&gt;private static final int INTENT_NEXT_SCREEN = 0;&lt;br /&gt;public static final String INTENT_EXTRA_SELECTED_ROW = "SELECTED_ROW";&lt;br /&gt;&lt;br /&gt;private static final int INSERT_ID = Menu.FIRST;&lt;br /&gt;private static final int DELETE_ID = Menu.FIRST + 1;&lt;br /&gt;private static final int EXIT_ID = DELETE_ID + 1;&lt;br /&gt;private Account account = new Account();&lt;br /&gt;private Intent intent;&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onCreate(Bundle savedInstanceState) {&lt;br /&gt;super.onCreate(savedInstanceState);&lt;br /&gt;setContentView(R.layout.account_list);&lt;br /&gt;myDatabaseAdapter = MyDatabaseAdapter.getInstance(this);&lt;br /&gt;intent = new Intent(this, AccountDetail.class);&lt;br /&gt;initComponents();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;private void initComponents() {&lt;br /&gt;account.setSQLiteDatabase(myDatabaseAdapter.getDatabase());&lt;br /&gt;Cursor recordsCursor = account.retrieveAll();&lt;br /&gt;startManagingCursor(recordsCursor);&lt;br /&gt;String[] from = new String[] { Account.COL_SERVER_NAME };&lt;br /&gt;int[] to = new int[] { R.id.tfServerName };&lt;br /&gt;SimpleCursorAdapter records = new SimpleCursorAdapter(this,&lt;br /&gt;R.layout.account_row, recordsCursor, from, to);&lt;br /&gt;setListAdapter(records);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public boolean onMenuItemSelected(int featureId, MenuItem item) {&lt;br /&gt;switch (item.getItemId()) {&lt;br /&gt;case INSERT_ID:&lt;br /&gt;createRecord();&lt;br /&gt;return true;&lt;br /&gt;case DELETE_ID:&lt;br /&gt;account.setId((int) getListView().getSelectedItemId());&lt;br /&gt;account.delete();&lt;br /&gt;initComponents();&lt;br /&gt;return true;&lt;br /&gt;case EXIT_ID:&lt;br /&gt;finish();&lt;br /&gt;}&lt;br /&gt;return super.onMenuItemSelected(featureId, item);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;private void createRecord() {&lt;br /&gt;intent.putExtra(INTENT_EXTRA_SELECTED_ROW, 0);&lt;br /&gt;startActivityForResult(intent, INTENT_NEXT_SCREEN);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;protected void onListItemClick(ListView l, View v, int position, long id) {&lt;br /&gt;super.onListItemClick(l, v, position, id);&lt;br /&gt;Log.v(getClass().getSimpleName(), "id=" + id);&lt;br /&gt;intent.putExtra(INTENT_EXTRA_SELECTED_ROW, id);&lt;br /&gt;startActivityForResult(intent, INTENT_NEXT_SCREEN);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public boolean onCreateOptionsMenu(Menu menu) {&lt;br /&gt;super.onCreateOptionsMenu(menu);&lt;br /&gt;menu.add(0, INSERT_ID, 0, R.string.btnAdd);&lt;br /&gt;menu.add(0, DELETE_ID, 0, R.string.btnDelete);&lt;br /&gt;menu.add(0, EXIT_ID, 0, R.string.btnExit);&lt;br /&gt;return true;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;protected void onActivityResult(int requestCode, int resultCode, Intent data) {&lt;br /&gt;initComponents();&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;span style="font-weight: bold;"&gt;   &lt;span style="font-family:arial;"&gt;  4.2 AccountDetail Controllers&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class AccountDetail extends Activity implements OnClickListener {&lt;br /&gt;&lt;br /&gt;private MyDatabaseAdapter myDatabaseAdapter;&lt;br /&gt;private long selectedRow;&lt;br /&gt;private TextView tvId;&lt;br /&gt;private EditText etServerName, etUserName, etPassword;&lt;br /&gt;private Button btnSave, btnCancel;&lt;br /&gt;private Account account;&lt;br /&gt;&lt;br /&gt;public void onCreate(Bundle savedInstanceState) {&lt;br /&gt;super.onCreate(savedInstanceState);&lt;br /&gt;setContentView(R.layout.account_detail);&lt;br /&gt;myDatabaseAdapter = MyDatabaseAdapter.getInstance(this);&lt;br /&gt;initComponents();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;private void initComponents() {&lt;br /&gt;selectedRow = getIntent().getLongExtra(&lt;br /&gt;AccountList.INTENT_EXTRA_SELECTED_ROW, 0);&lt;br /&gt;tvId = (TextView) findViewById(R.id.tvId);&lt;br /&gt;etServerName = (EditText) findViewById(R.id.etServerName);&lt;br /&gt;etUserName = (EditText) findViewById(R.id.etUsername);&lt;br /&gt;etPassword = (EditText) findViewById(R.id.etPassword);&lt;br /&gt;&lt;br /&gt;account = new Account();&lt;br /&gt;account.setSQLiteDatabase(myDatabaseAdapter.getDatabase());&lt;br /&gt;Log.v(getClass().getSimpleName(), "selectedRow=" + selectedRow);&lt;br /&gt;account.setId((int) selectedRow);&lt;br /&gt;if (selectedRow &gt; 0) {&lt;br /&gt;account.load(this);&lt;br /&gt;}&lt;br /&gt;Log.v(getClass().getSimpleName(), "account.getId()=" + account.getId());&lt;br /&gt;if (account.getId() &gt; 0) {&lt;br /&gt;tvId.setText(account.getId() + "");&lt;br /&gt;etServerName.setText(account.getServerName());&lt;br /&gt;etUserName.setText(account.getUsername());&lt;br /&gt;etPassword.setText(account.getPassword());&lt;br /&gt;} else {&lt;br /&gt;tvId.setText("new");&lt;br /&gt;}&lt;br /&gt;btnSave = (Button) findViewById(R.id.btnSave);&lt;br /&gt;btnSave.setOnClickListener(this);&lt;br /&gt;btnCancel = (Button) findViewById(R.id.btnCancel);&lt;br /&gt;btnCancel.setOnClickListener(this);&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;a style="font-family: arial;" href="http://mobileserver.byethost2.com/?p=30"&gt;Source Code&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;If you find something confusing from this tutorial, just post a comment, and I'll fix it for you.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;In order to display multiple items on the list, just edit account_row.xml as shown below.&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="xml"&gt;&lt;br /&gt;&lt;RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"&lt;br /&gt; android:layout_width="fill_parent" android:layout_height="wrap_content"&gt;&lt;br /&gt; &lt;TextView android:id="@+id/tfServerName" android:layout_marginLeft="10px"&lt;br /&gt;     android:layout_width="wrap_content" android:layout_alignParentRight="false"&lt;br /&gt;     android:layout_height="wrap_content" android:text="Server Name" /&gt;&lt;br /&gt; &lt;TextView android:id="@+id/tfUsername" &lt;br /&gt;     android:layout_width="wrap_content"&lt;br /&gt;     android:layout_height="wrap_content" android:layout_toRightOf="@id/tfServerName" &lt;br /&gt;     android:text="Username"/&gt; &lt;br /&gt;&lt;/RelativeLayout&gt;&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;Also modify AccountList.java to display the fields you want.&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;String[] from = new String[] { Account.COL_SERVER_NAME, Account.COL_USERNAME};&lt;br /&gt;int[] to = new int[] { R.id.tfServerName, R.id.tfUsername };&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-5280906251766706113?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/5280906251766706113/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=5280906251766706113' title='14 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/5280906251766706113'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/5280906251766706113'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2008/10/android-simple-sqlitedatabase.html' title='Android Simple SQLiteDatabase'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://1.bp.blogspot.com/_WAOO_koVttQ/SPtTPpD1mwI/AAAAAAAAAGI/DuA-HTXM-4I/s72-c/01.JPG' height='72' width='72'/><thr:total>14</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-3828981530624713315</id><published>2008-10-12T21:27:00.021+08:00</published><updated>2009-01-30T14:21:55.311+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='progress bar'/><category scheme='http://www.blogger.com/atom/ns#' term='threads'/><category scheme='http://www.blogger.com/atom/ns#' term='intent'/><category scheme='http://www.blogger.com/atom/ns#' term='networking'/><title type='text'>Android Networking, User Experience and Threads</title><content type='html'>&lt;span style=";font-family:arial;font-size:100%;"  &gt;This tutorial is an android version of good old J2ME tutorial about &lt;a href="http://developers.sun.com/mobility/midp/articles/threading/"&gt;Networking, User Experience and Threads&lt;/a&gt;; thus, I won't make my own J2ME tutorial for that.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;Source code can be downloaded below.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;For this Simple Http Connection application, it uses the following classes:&lt;br /&gt;&lt;br /&gt;&lt;a href="http://code.google.com/android/reference/android/os/Handler.html"&gt;Handler&lt;/a&gt;&lt;br /&gt;&lt;a href="http://code.google.com/android/reference/android/content/Intent.html"&gt;Intent&lt;/a&gt;&lt;br /&gt;&lt;a href="http://code.google.com/android/reference/android/widget/ProgressBar.html"&gt;ProgressBar&lt;/a&gt;&lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;&lt;br /&gt;&lt;br /&gt;Unlike, the hello world tutorial, where only an alert screen shows, this tutorial will have two screens or two activities. &lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;So, I'll get started.&lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;&lt;br /&gt;&lt;br /&gt;First, create two activity classes for the first screen and the next screen.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;SimpleHttpConnection.java&lt;/span&gt; is the MAIN activity,&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;NextScreen.java&lt;/span&gt; will display the network response.&lt;br /&gt;&lt;br /&gt;Here's what the SimpleHttpConnection (main.xml) looks like.&lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SPIByb6P-9I/AAAAAAAAAFk/uhhDLbcuxh0/s1600-h/01.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SPIByb6P-9I/AAAAAAAAAFk/uhhDLbcuxh0/s400/01.JPG" alt="" id="BLOGGER_PHOTO_ID_5256265681091951570" border="0" /&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;The white space on top of the buttons is supposed to be the progress bar, for some reason the android eclipse plug-in does not render it properly.&lt;/span&gt;&lt;p style="font-family: arial;"&gt;&lt;/p&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;&lt;pre name="code" class="java"&gt; @Override&lt;br /&gt;public void onCreate(Bundle savedInstanceState) {&lt;br /&gt;super.onCreate(savedInstanceState);&lt;br /&gt;setContentView(R.layout.main);&lt;br /&gt;initComponents();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;private void initComponents() {&lt;br /&gt;connectIntent = new Intent(this, NextScreen.class);&lt;br /&gt;progressBar = (ProgressBar) findViewById(R.id.pbProgressBar);&lt;br /&gt;progressBar.setVisibility(ProgressBar.INVISIBLE);&lt;br /&gt;btnConnect = (Button) findViewById(R.id.btnConnect);&lt;br /&gt;btnConnect.setOnClickListener(this);&lt;br /&gt;btnCancel = (Button) findViewById(R.id.btnCancel);&lt;br /&gt;btnCancel.setOnClickListener(this);&lt;br /&gt;btnCancel.setVisibility(Button.INVISIBLE);&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;Above is the code, for the user interface. Notice that the btnCancel and the progressBar is set to invisible. It will be visible to the user once btnConnect is clicked. Here's what the user-interface will look like.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SPIC9Zl36XI/AAAAAAAAAFs/dxFi6k4myH8/s1600-h/02.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SPIC9Zl36XI/AAAAAAAAAFs/dxFi6k4myH8/s400/02.JPG" alt="" id="BLOGGER_PHOTO_ID_5256266968959805810" border="0" /&gt;&lt;/a&gt;&lt;/span&gt;&lt;pre name="code" class="java"&gt;@Override&lt;br /&gt;public void onClick(View v) {&lt;br /&gt;if (v == btnConnect) {&lt;br /&gt;try {&lt;br /&gt;networkConnection = new NetworkConnection(progressBar,&lt;br /&gt;getString(R.string.simplehttpurl), this,&lt;br /&gt;connectIntent, INTENT_NEXT_SCREEN);&lt;br /&gt;networkConnection.start();&lt;br /&gt;btnConnect.setVisibility(Button.INVISIBLE);&lt;br /&gt;btnCancel.setVisibility(Button.VISIBLE);&lt;br /&gt;} catch (Exception ex) {&lt;br /&gt;Log.e(getClass().getName(), "Error on onClick btnConnect ", ex);&lt;br /&gt;}&lt;br /&gt;} else if(v == btnCancel) {&lt;br /&gt;if(networkConnection != null) {&lt;br /&gt;try {&lt;br /&gt;networkConnection.close();&lt;br /&gt;} catch(Exception ex) {&lt;br /&gt;Log.e(getClass().getName(), "Error on onClick btnCancel ", ex);&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;reset();&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;When btnConnect is clicked, it initializes the NetworkConnection class and sends the request to the server. The btnConnect button is then set to invisible then the cancel button is set to visible. When the btnCancel is clicked, it will then interrupt the connection, and enables the btnConnect again, disabling the btnCancel and resets the progress bar.&lt;br /&gt;&lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SPIHnPQo-xI/AAAAAAAAAF0/j84QDnemG6I/s1600-h/03.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SPIHnPQo-xI/AAAAAAAAAF0/j84QDnemG6I/s400/03.JPG" alt="" id="BLOGGER_PHOTO_ID_5256272085787409170" border="0" /&gt;&lt;/a&gt;&lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;&lt;br /&gt;The &lt;span style="font-weight: bold;"&gt;NetworkConnection&lt;/span&gt; class implements Runnable since it will run as another thread.&lt;br /&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public class NetworkConnection implements Runnable&lt;br /&gt;&lt;/pre&gt;Network Connection uses the following parameters:&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;progressBar&lt;/span&gt; - passes the screen's progress bar to be update the progress.&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;serverUrl&lt;/span&gt; - the server's url.&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;activity&lt;/span&gt; - the previous activity, this will be used to call startActivityForResult(intent, intentId);&lt;br /&gt;&lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;&lt;span style="font-weight: bold;"&gt;nextIntent&lt;/span&gt; - the next activity to be run after the network connection is done.&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;intentId&lt;/span&gt; - the requestCode used by the Main Activity's onActivityResult method show below.&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;protected void onActivityResult(int requestCode, int resultCode, Intent data) {&lt;br /&gt;Log.v(getClass().getName(), requestCode + " - " + resultCode);&lt;br /&gt;if (requestCode == INTENT_NEXT_SCREEN) {&lt;br /&gt;reset();&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;When the NetworkConnection is started, a thread is created and the HTTP connection starts.&lt;/span&gt;&lt;br /&gt;&lt;pre name="code" class="java"&gt;public void start() throws IOException {&lt;br /&gt;runner = new Thread(this);&lt;br /&gt;runner.start();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void run() {&lt;br /&gt;try {&lt;br /&gt;&lt;br /&gt;transfer(serverUrl);&lt;br /&gt;} catch (Exception e) {&lt;br /&gt;Log.e(getClass().getName(), "Error on startStreaming ", e);&lt;br /&gt;return;&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void transfer(String urlStr) throws IOException {&lt;br /&gt;url = new URL(urlStr);&lt;br /&gt;urlConnection = url.openConnection();&lt;br /&gt;inputStream = urlConnection.getInputStream();&lt;br /&gt;if (inputStream == null) {&lt;br /&gt;Log.e(getClass().getName(), "Error on transfer " + url);&lt;br /&gt;}&lt;br /&gt;int contentLength = (int) urlConnection.getContentLength();&lt;br /&gt;if (contentLength == -1)&lt;br /&gt;contentLength = 255;&lt;br /&gt;int ch = 0;&lt;br /&gt;total = contentLength;&lt;br /&gt;Log.v(getClass().getName(), contentLength + "");&lt;br /&gt;StringBuffer buffer = new StringBuffer();&lt;br /&gt;while ((ch = inputStream.read()) != -1) {&lt;br /&gt;buffer.append((char) ch);&lt;br /&gt;fireDataLoadUpdate();&lt;br /&gt;current++;&lt;br /&gt;}&lt;br /&gt;inputStream.close();&lt;br /&gt;response = buffer.toString();&lt;br /&gt;Log.v(getClass().getName(), response);&lt;br /&gt;intent.putExtra(NC_RESPONSE, response);&lt;br /&gt;parent.startActivityForResult(intent, intentId);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;private void fireDataLoadUpdate() {&lt;br /&gt;Runnable updater = new Runnable() {&lt;br /&gt;public void run() {&lt;br /&gt;double loadProgress = ((double) current / (double) total);&lt;br /&gt;Log.v(getClass().getName(), "loadProgress=" + loadProgress);&lt;br /&gt;progressBar.setProgress((int) (loadProgress * 100));&lt;br /&gt;progressBar.setSecondaryProgress((int) (loadProgress * 100));&lt;br /&gt;Log.v(getClass().getName(), "" + progressBar.getProgress());&lt;br /&gt;}&lt;br /&gt;};&lt;br /&gt;handler.post(updater);&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;&lt;br /&gt;The &lt;/span&gt;&lt;span style="font-style: italic;font-family:arial;font-size:100%;"  &gt;transfer&lt;/span&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt; method, is just a basic HTTP connection, its just opens a connections from the url then opens an input stream. The important part of this method is&lt;br /&gt;&lt;/span&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;intent.putExtra(NC_RESPONSE, response);&lt;br /&gt;parent.startActivityForResult(intent, intentId);&lt;br /&gt;&lt;/pre&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;&lt;br /&gt;This code, puts the server response in the intent.putExra, then starts the next activity, which was defined on the first screen.&lt;br /&gt;&lt;br /&gt;Also, the NetworkConnection has close method, that when the user clicks, it cancels the operation. The method I created is a crude one without any graceful handling. But for this app, it does not need to. If you're app parses data and saves them somewhere, be careful in using this since it will corrupt your data.&lt;br /&gt;&lt;pre name="code" class="java"&gt;&lt;br /&gt;public void close() {&lt;br /&gt;if (runner != null) {&lt;br /&gt;&lt;br /&gt;if(inputStream != null) {&lt;br /&gt;try {&lt;br /&gt;inputStream.close();&lt;br /&gt;} catch (IOException e) {&lt;br /&gt;}&lt;br /&gt;inputStream = null;&lt;br /&gt;}&lt;br /&gt;if(urlConnection != null) {&lt;br /&gt;try {&lt;br /&gt;urlConnection = null;&lt;br /&gt;} catch(Exception ex) {&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;try {&lt;br /&gt;runner.interrupt();&lt;br /&gt;runner.join();&lt;br /&gt;runner = null;&lt;br /&gt;} catch (InterruptedException e) {&lt;br /&gt;//Thread.currentThread().interrupt();&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;span style="font-weight: bold;"&gt;NextScreen.java&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;pre name="code" class="java"&gt;public class NextScreen extends Activity implements OnClickListener {&lt;br /&gt;private Button btnBack;&lt;br /&gt;private TextView tvMessage;&lt;br /&gt;private String message;&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onCreate(Bundle savedInstanceState) {&lt;br /&gt;&lt;br /&gt;super.onCreate(savedInstanceState);&lt;br /&gt;setContentView(R.layout.nextscreen);&lt;br /&gt;initComponents();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void initComponents() {&lt;br /&gt;message = getIntent().getStringExtra(NetworkConnection.NC_RESPONSE);&lt;br /&gt;tvMessage = (TextView) findViewById(R.id.tvMessage);&lt;br /&gt;if (message != null) {&lt;br /&gt;tvMessage.setText(message);&lt;br /&gt;} else {&lt;br /&gt;tvMessage.setText("Message is null");&lt;br /&gt;}&lt;br /&gt;btnBack = (Button) findViewById(R.id.btnBack);&lt;br /&gt;btnBack.setOnClickListener(this);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;@Override&lt;br /&gt;public void onClick(View v) {&lt;br /&gt;if (v == btnBack) {&lt;br /&gt;finish();&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;&lt;/pre&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;On the initComponent method, the Intent Extra is that was set in the NetworkConnection class was retrieved then set on the TextView.&lt;br /&gt;&lt;br /&gt;Here's what it looks like.&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SPIMt9xeP_I/AAAAAAAAAF8/_a9J9y0EdfQ/s1600-h/04.JPG"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SPIMt9xeP_I/AAAAAAAAAF8/_a9J9y0EdfQ/s400/04.JPG" alt="" id="BLOGGER_PHOTO_ID_5256277698910502898" border="0" /&gt;&lt;/a&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style=";font-family:arial;font-size:100%;"  &gt;When the Back button is clicked, the finish() method is called, signifying that the Activity is done. Thus, it goes back to the main screen, and calling the onActivityResult method. For this, application, I just reset the progress bar, and the buttons.&lt;br /&gt;&lt;br /&gt;Also, do not forget to add permission, or you might get a Socket Exception.&lt;br /&gt;&lt;br /&gt;Modify the Android Manifest and add&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;uses-permission name="android.permission.INTERNET"&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;See the AndroidManifest.xml in the source code for more details.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://mobileserver.byethost2.com/?p=26"&gt;Source Code&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-3828981530624713315?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/3828981530624713315/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=3828981530624713315' title='4 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/3828981530624713315'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/3828981530624713315'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2008/10/android-networking-user-experience-and.html' title='Android Networking, User Experience and Threads'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://1.bp.blogspot.com/_WAOO_koVttQ/SPIByb6P-9I/AAAAAAAAAFk/uhhDLbcuxh0/s72-c/01.JPG' height='72' width='72'/><thr:total>4</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-3616986634653015213</id><published>2008-10-12T14:05:00.008+08:00</published><updated>2008-10-12T21:29:28.764+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='stylesheet'/><category scheme='http://www.blogger.com/atom/ns#' term='blogger'/><category scheme='http://www.blogger.com/atom/ns#' term='css'/><title type='text'>Java Source Code Style</title><content type='html'>I just found out how to write Java and XML code with syntax highlights in blogger.&lt;br /&gt;You can find the project &lt;a href="http://code.google.com/p/syntaxhighlighter/"&gt;here&lt;/a&gt;. So on the next post, i'll use it instead of screen captures of the source code.&lt;br /&gt;&lt;pre name="code" class="java"&gt;public class HelloWorld {&lt;br /&gt;private String message = "Hello World";&lt;br /&gt;&lt;br /&gt;public static void main(String[] args) {&lt;br /&gt;System.out.println(message);&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-3616986634653015213?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/3616986634653015213/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=3616986634653015213' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/3616986634653015213'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/3616986634653015213'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2008/10/java-source-code-style.html' title='Java Source Code Style'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-2347532793882730675</id><published>2008-09-28T16:12:00.020+08:00</published><updated>2009-01-30T14:07:09.380+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='hello world'/><category scheme='http://www.blogger.com/atom/ns#' term='android'/><title type='text'>Hello World Android version</title><content type='html'>&lt;span style="font-size:100%;"&gt;&lt;span style="font-family:arial;"&gt;For J2ME developers, read the &lt;/span&gt;&lt;a style="font-family: arial;" href="http://javapadawan.blogspot.com/2008/09/hello-world-j2me-version.html"&gt;J2ME version&lt;/a&gt;&lt;span style="font-family:arial;"&gt; first.&lt;br /&gt;&lt;br /&gt;Link for the source code at the end of the tutorial.&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;Step 1. Create Android Project By File &gt; New then select Android Project.&lt;/span&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SN9Pe7JPfRI/AAAAAAAAAFI/zDVVAF7n7G0/s1600-h/01.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251003083228413202" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SN9Pe7JPfRI/AAAAAAAAAFI/zDVVAF7n7G0/s400/01.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;Step 2. Enter Project Name, to be consistent with the J2ME version, I chose HelloWorld.&lt;/span&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SN9Pe3wiyhI/AAAAAAAAAFQ/6xEwBjmoRQY/s1600-h/02.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251003082319514130" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SN9Pe3wiyhI/AAAAAAAAAFQ/6xEwBjmoRQY/s400/02.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Android enforces a two identifier package, thus javapadawan.android is used.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;The Activity name, entered in above will serve as the entry point of the application. This is similar to J2ME's MIDlet. One can create multiple MIDlets, but only once can be used as a program entry point.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;Step 3. Create HelloWorldActivity.java.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SN9PW0v4U_I/AAAAAAAAAEg/NOqB7LZO6E4/s1600-h/03.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002944072471538" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SN9PW0v4U_I/AAAAAAAAAEg/NOqB7LZO6E4/s400/03.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Note that R.java is generated by the Eclipse Android plug-in, so don't bother with that. Also, when encountering compile problems with R.java, just do a Clean on the Eclipse Menu Project&gt;Clean then Build the Project.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-family:arial;" &gt;Step 4. Creating the User Interface.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;When you created the HelloWorldActivity, the Eclipse Android plug-in already created the layout XML.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PWyZFw-I/AAAAAAAAAEo/GTAvV-1FovI/s1600-h/04.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002943440012258" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PWyZFw-I/AAAAAAAAAEo/GTAvV-1FovI/s400/04.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Above is generated XML. Although, one can program Android user-interfaces by hand, without using XML, but that's considered an advanced topic. Similar to coding UIs using MIDP's Canvas.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PXYMvFdI/AAAAAAAAAEw/GO30mzzJ68I/s1600-h/05.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002953588741586" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PXYMvFdI/AAAAAAAAAEw/GO30mzzJ68I/s400/05.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Below is the User Interface similar to the J2ME version of the HelloWorld. The one's encircled in red are going to be used in the HelloWorldActivity class, the @+id/&lt;/span&gt;&lt;name style="font-family: arial;"&gt; should be unique. The usage of such will be shown below. Further, detailed explaination for the xml layouts will come in the future tutorials.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PXZQfWDI/AAAAAAAAAE4/BnBgBqPVs9I/s1600-h/06.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002953872922674" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PXZQfWDI/AAAAAAAAAE4/BnBgBqPVs9I/s400/06.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Above is the result of the xml layout above. This uses the RelativeLayout.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Step 5. Coding the HelloWorldActivity.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;As much as possible, I want the Android version to be similar to the J2ME version of the HelloWorld so that a J2ME developer may see the differences.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SN9PXefo82I/AAAAAAAAAFA/BcfyVVlddiI/s1600-h/07.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002955278644066" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SN9PXefo82I/AAAAAAAAAFA/BcfyVVlddiI/s400/07.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Thus, I also included a initComponents() method. This is where the User Interface Components defined in the XML are retrieved.&lt;br /&gt;&lt;br /&gt;Notice the usage of the R.java. Whenever, there are thing modified in the XMLs such as the main.xml and string.xml, it gets reflected here.&lt;br /&gt;&lt;br /&gt;The android:id identified above will become R.id.&lt;name&gt;.&lt;br /&gt;&lt;br /&gt;So to be able to use the User Interface components, it need to be retrieved using the Activity method, findByViewId(...). The parameter needed by findByViewId is integer, but the R.java values should be used.&lt;br /&gt;&lt;br /&gt;So just set the values of the findById(...) to a private variable inside the class. For the buttons, (similar to MIDP), listeners must be assigned. Since I used the same class as the listener in J2ME, I will also use the same for Android.&lt;br /&gt;&lt;br /&gt;So just, add implements OnClickListener to the class and implement its method.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PJ4UF6NI/AAAAAAAAAEA/Sw21XRSjfH0/s1600-h/08.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002721691363538" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PJ4UF6NI/AAAAAAAAAEA/Sw21XRSjfH0/s400/08.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Similar to J2ME's commandAction(Command c, Displayable d), when a button is clicked, the View (Component) responsible to the event is also passed in the onClick(View v) method.&lt;br /&gt;&lt;br /&gt;So above is the implementation I did. Notice the similarities of the MIDP version.&lt;br /&gt;&lt;br /&gt;However, the Alert is quite different and more complex in android. Just see the &lt;a href="http://code.google.com/android/reference/android/app/AlertDialog.Builder.html"&gt;AlertBuilder API&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Step 6. Clean, Build and Run&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SN9PKCXzFsI/AAAAAAAAAEI/v_eVU_5gD_g/s1600-h/09.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002724391261890" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SN9PKCXzFsI/AAAAAAAAAEI/v_eVU_5gD_g/s400/09.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Clean and Buld the Project.&lt;br /&gt;&lt;br /&gt;Run by going to the Menu then Run &gt; Run (Ctrl + F11).&lt;br /&gt;Then Run As Android Applicaiton. On the first Run, this may take a couple of minutes depending on your Hardware.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PKNGElJI/AAAAAAAAAEQ/urXvm9kx6yI/s1600-h/10.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002727269700754" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9PKNGElJI/AAAAAAAAAEQ/urXvm9kx6yI/s400/10.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SN9PKHk-AMI/AAAAAAAAAEY/-cKc1O0d1RY/s1600-h/11.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002725788680386" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SN9PKHk-AMI/AAAAAAAAAEY/-cKc1O0d1RY/s400/11.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Step 7. Debugging and Cleaning the Emulator.&lt;/span&gt;&lt;br /&gt;Unlike in Netbeans IDE, Mobility where the System.out.print, and stacktraces displays on the IDE's consolde&lt;br /&gt;&lt;br /&gt;In Eclipse Android Plug-in, you need to go to the DDMS perspective to debug. Open a new Perspective Window &gt; Open Perspective &gt; Other&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SN9PCfglYdI/AAAAAAAAAD4/SkhDC4TrNJc/s1600-h/12.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002594773787090" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SN9PCfglYdI/AAAAAAAAAD4/SkhDC4TrNJc/s400/12.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;On the dialog, select DDMS.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9O8ZYjL8I/AAAAAAAAADw/WJZ0OhCnlV4/s1600-h/13.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002490050260930" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SN9O8ZYjL8I/AAAAAAAAADw/WJZ0OhCnlV4/s400/13.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Here's what the DDMS Perspective looks like. Also, you may delete the installed apps if you want. Highlight the .apk to be deleted and click the red (-) minus button shown.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SN9O56SQUMI/AAAAAAAAADo/mgBJ4-Cep_Y/s1600-h/14.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5251002447342620866" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SN9O56SQUMI/AAAAAAAAADo/mgBJ4-Cep_Y/s400/14.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.geocities.com/java.padawan/android/HelloWorld.zip"&gt;&lt;/a&gt;&lt;a href="http://mobileserver.byethost2.com/?p=16"&gt;Source Code&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;/name&gt;&lt;/name&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-2347532793882730675?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/2347532793882730675/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=2347532793882730675' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/2347532793882730675'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/2347532793882730675'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2008/09/hello-world-android-version.html' title='Hello World Android version'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_WAOO_koVttQ/SN9Pe7JPfRI/AAAAAAAAAFI/zDVVAF7n7G0/s72-c/01.JPG' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-4566723239031097721</id><published>2008-09-28T15:26:00.037+08:00</published><updated>2009-01-30T14:02:23.777+08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='hello world'/><category scheme='http://www.blogger.com/atom/ns#' term='j2me'/><title type='text'>Hello World J2ME version</title><content type='html'>&lt;span style="font-size:100%;"&gt;&lt;span style="font-family:arial;"&gt;Before reading this, you should have downloaded &lt;/span&gt;&lt;a style="font-family: arial;" href="http://download.netbeans.org/netbeans/6.1/final/"&gt;Netbeans IDE 6.1&lt;/a&gt;&lt;span style="font-family:arial;"&gt;, choose the Mobility version or the All version.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;When creating a J2ME application, I usually separate my MIDlet class, view-controller classes and model classes.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;I do not separate View and Controller since normally my views only have a couple of controls and I find it more organized that way.&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;span style="font-family:arial;"&gt;Link for the source code at the end of the tutorial.&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;font-size:100%;"  &gt;Step 1. Create a new Project By File&gt;New Project &lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;font-size:100%;"  &gt;Click Mobility from the Categories and MIDP Application from Projects.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SN8yn9vO-vI/AAAAAAAAABI/8YIyCIpDtLA/s1600-h/02.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5250971352706251506" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SN8yn9vO-vI/AAAAAAAAABI/8YIyCIpDtLA/s400/02.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;font-size:100%;"  &gt;Step 2. Write any Project Name and select a project location then click the Next Button.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SN8yWWH6WMI/AAAAAAAAABA/Kwqz-11TaHI/s1600-h/01.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5250971050014562498" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SN8yWWH6WMI/AAAAAAAAABA/Kwqz-11TaHI/s400/01.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;font-size:100%;"  &gt;Step 3. Select CLDC 2.0 and MIDP 2.0&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SN8y8_XPHRI/AAAAAAAAABQ/Ef2r3D5My7A/s1600-h/03.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5250971713919720722" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SN8y8_XPHRI/AAAAAAAAABQ/Ef2r3D5My7A/s400/03.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;font-size:100%;"  &gt;Step 4. Click Finish. Delete all generated .java files as we will not be using the WYSIWYG editor.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SN86OhsUHvI/AAAAAAAAACg/2Hpl5IsjhGc/s1600-h/04a.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5250979711774105330" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SN86OhsUHvI/AAAAAAAAACg/2Hpl5IsjhGc/s400/04a.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;Then create two classes, HelloWorldForm.java and HelloWorldMIDlet.java&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;You should have the following files on your Project Tab.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SN86Ze3oCBI/AAAAAAAAACo/04cAjZnVFmk/s1600-h/04b.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5250979899994802194" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SN86Ze3oCBI/AAAAAAAAACo/04cAjZnVFmk/s400/04b.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;font-size:100%;"  &gt;Step5. Writing the HelloWorldMIDlet.java code.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();}  catch(e) {}" style="font-family: arial;" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SN80RZJzR_I/AAAAAAAAABo/Bx6AUTbCCcQ/s1600-h/05.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5250973163951704050" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SN80RZJzR_I/AAAAAAAAABo/Bx6AUTbCCcQ/s400/05.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;PauseApp, destroyApp and startApp are the abstract classes of the MIDlet class that needs to be implemented. I added two methods to be used by the UI class, showScreen(Displayble d) and showScreenAndAlert(Alert a, Displayble d).&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;The code in startApp() will be discussed after the next step.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;font-size:100%;"  &gt;Step 6. Coding the HelloWorldForm.java.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SN80rpgQgsI/AAAAAAAAABw/egAlRTXhH8M/s1600-h/06.JPG"&gt;&lt;br /&gt;&lt;img id="BLOGGER_PHOTO_ID_5250973615017460418" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SN80rpgQgsI/AAAAAAAAABw/egAlRTXhH8M/s400/06.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;As you may have noticed, the MIDlet class is passed to the constructor, I find this useful in creating a apps with a lot of forms. Further, the MIDlet class may also be used to store Application sessions data, also handling unexpected application problems.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;The initComponents() method is where the UI Components are initialized and added to the Form.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;If you do not want the controller and the view to be on the same class, you may create, or pass in the constructor a class that implements the CommandListener interface.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;On the code, instead of setCommandListener(this), just replace this with a CommandListener instance.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();}  catch(e) {}" style="font-family: arial;" href="http://4.bp.blogspot.com/_WAOO_koVttQ/SN81S6IDpXI/AAAAAAAAAB4/Rc5KL5Lj6MU/s1600-h/07.JPG"&gt;&lt;br /&gt;&lt;img id="BLOGGER_PHOTO_ID_5250974289494254962" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://4.bp.blogspot.com/_WAOO_koVttQ/SN81S6IDpXI/AAAAAAAAAB4/Rc5KL5Lj6MU/s400/07.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-weight: bold;font-family:arial;font-size:100%;"  &gt;Step 7. Building and Running.&lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SN81kz3mKnI/AAAAAAAAACA/v79JAaUNSLU/s1600-h/08.JPG"&gt;&lt;br /&gt;&lt;img id="BLOGGER_PHOTO_ID_5250974597052246642" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SN81kz3mKnI/AAAAAAAAACA/v79JAaUNSLU/s400/08.JPG" border="0" /&gt;&lt;/a&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://3.bp.blogspot.com/_WAOO_koVttQ/SN81o4MOnlI/AAAAAAAAACI/zLx2wg5tDes/s1600-h/09.JPG"&gt;&lt;br /&gt;&lt;img id="BLOGGER_PHOTO_ID_5250974666932002386" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://3.bp.blogspot.com/_WAOO_koVttQ/SN81o4MOnlI/AAAAAAAAACI/zLx2wg5tDes/s400/09.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://2.bp.blogspot.com/_WAOO_koVttQ/SN81u7Zt7UI/AAAAAAAAACQ/AhVnupI8wZ4/s1600-h/10.JPG"&gt;&lt;br /&gt;&lt;img id="BLOGGER_PHOTO_ID_5250974770873101634" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://2.bp.blogspot.com/_WAOO_koVttQ/SN81u7Zt7UI/AAAAAAAAACQ/AhVnupI8wZ4/s400/10.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" style="font-family: arial;" href="http://1.bp.blogspot.com/_WAOO_koVttQ/SN81yCuvHeI/AAAAAAAAACY/BIsEfJi6sqU/s1600-h/11.JPG"&gt;&lt;img id="BLOGGER_PHOTO_ID_5250974824379915746" style="margin: 0px auto 10px; display: block; cursor: pointer; text-align: center;" alt="" src="http://1.bp.blogspot.com/_WAOO_koVttQ/SN81yCuvHeI/AAAAAAAAACY/BIsEfJi6sqU/s400/11.JPG" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;a href="http://mobileserver.byethost2.com/?p=3"&gt;&lt;span style="text-decoration: underline;"&gt;Source Code&lt;/span&gt;&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-4566723239031097721?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/4566723239031097721/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=4566723239031097721' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/4566723239031097721'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/4566723239031097721'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2008/09/hello-world-j2me-version.html' title='Hello World J2ME version'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://3.bp.blogspot.com/_WAOO_koVttQ/SN8yn9vO-vI/AAAAAAAAABI/8YIyCIpDtLA/s72-c/02.JPG' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-277123759957171194.post-4954417935522633217</id><published>2008-09-28T12:17:00.002+08:00</published><updated>2008-09-28T18:53:05.141+08:00</updated><title type='text'>About.</title><content type='html'>&lt;span style="font-size:100%;"&gt;&lt;span style="font-family:arial;"&gt;I am a Java Mobile Edition developer ever since MIDP 1.0, I've already experienced and done the workarounds of almost all of the limitation of the MIDP platform. The worst ever is not being able to get the Mobile Number of the Phones (This is for most Phones, some implementations offer a native utility for retrieving IMEI, Numbers, Contacts but not the standard MIDP API). &lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;When I first reviewed Google Android, I got excited with the fact that everything in the phones is programmable and is not limited to a J2ME like tiny little sandbox. I worry about the Device's security though.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:arial;"&gt;I'll be starting a Journal of how to program Android from a J2ME Developer's Perspective. I am planning to use my knowledge in MIDP, and try to figure out how to port it in android. In the future, I may start on some advanced Android apps and see what the android can really do.&lt;/span&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/277123759957171194-4954417935522633217?l=www.androidph.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://www.androidph.com/feeds/4954417935522633217/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=277123759957171194&amp;postID=4954417935522633217' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/4954417935522633217'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/277123759957171194/posts/default/4954417935522633217'/><link rel='alternate' type='text/html' href='http://www.androidph.com/2008/09/hello-world.html' title='About.'/><author><name>java.padawan</name><uri>http://www.blogger.com/profile/04565725757123152660</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry></feed>
