Sunday, February 23, 2014

ToDo List example

Since repetition is the mother of all learning and the following example is one of the most distinct examples of how to start android development I wrote it down as well to try to explain it as best as I can.

What we are going to do is a ToDo List app.

Bearing the design in mind will help us better understand what components will be needed ( plus I prefer a more visualized approach to such kind of problems ).

android todo app

As we can see from the mockup sketch two fragments are needed. One will just display an EditText widget and when the user clicks 'Send' on the software keyboard we will pass the text to the list bellow. That gets us to the second fragment which is a ListFragment.


Both of them are in the MainActivity.
Since we are using a ListFragment we have to use an Adapter to bind the data to the list.

Also we will need a data model for our todo items. Lets name it DataItem class.
Last but not least we will create a custom view from each list item.

Let me summarize things a little bit : We have one MainActivity class with its layout, composed of two fragments ( one is a ListFragment ). The ListFragment also needs an Adapter class. Our data model will only need a String variable and a Custom View for each ListFragment's item for the time.


So let's start from our model. We only need one getter and one setter method since our only variable will be a String. You can check the code here .

Now its time to create the TopFragment. As you can see 
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".TopFragment" > <EditText android:id="@+id/myEditText1" android:inputType="textCapSentences|textAutoCorrect" android:imeOptions="actionSend" android:layout_width="match_parent" android:layout_height="wrap_content" android:ems="10" /> </LinearLayout>
 the layout is just an EditText. We inflate that layout in onCreateView method ( like we do with every fragment ). The “tricky” part here is adding an OnEditorActionListener  so we can listen for the 'SEND' action, get the user input and clear the text in EditText. An Interface is also necessary so we can implement it on the MainActivity and get the user's text input. All of these data will be stored on an ArrayList in the MainActivity and passed to the Adapter to bind them to the view.  


The TaskListAdapter gets each item from the ArrayList as we said above, creates a new list item and sets the data.

ListFragment just inflates the layout which consists of a ListView with the android:divider atrribute set to null so we don't have to deal with the default divider line from the ListView widget.


Since each item is just a TextView our custom view needs to extend a TextView. We saw on a previous post  how to create a custom view so I will not go into details.

The XML layout file for the custom view, used by the TaskListAdapter is:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:custom="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" tools:context=".TaskListFragment" > <org.codeteo.todolist.CustomItemView android:id="@+id/row" android:layout_width="match_parent" android:layout_height="match_parent" android:padding="10dp" android:textColor="#FF0000" android:textSize="20sp" /> </LinearLayout>


Now we have to check the MainActivity code. The MainActivity implements the OnItemAddedListener Interface we declared on the TopFragment and create the method onNewItemAdded() so it can get the data user's input and store it on an ArrayList.
That input along with the id resource of the XML file that represents the list
item are passed to the Adapter.
The code is below :

 public class MainActivity extends Activity  implements TopFragment.OnItemAddedListener {
 
   private ArrayList todoItems;
   private TaskListAdapter aa; 

 @Override
 protected void onCreate(Bundle savedInstanceState) {
  super.onCreate(savedInstanceState);
  setContentView(R.layout.main);
       
     // Get references to the Fragments
     FragmentManager fm = getFragmentManager();
     TaskListFragment todoListFragment = 
       (TaskListFragment)fm.findFragmentById(R.id.TaskListFragment);
      
     // Create the array list of to do items
     todoItems = new ArrayList();
      
     // Create the array adapter to bind the array to the ListView
     int resID = R.layout.tasklist_fragment;   
     aa = new TaskListAdapter(this, resID, todoItems);
      
     // Bind the array adapter to the ListView.
     todoListFragment.setListAdapter(aa);
   }
   
   public void onNewItemAdded(String newItem) {
     DataItem newTodoItem = new DataItem(newItem);
     todoItems.add(0, newTodoItem);
     aa.notifyDataSetChanged();
   }
}


The method onNewItemAdded() adds the DataItem before every other ArrayList item and also notify the data set has changed.
You can find the code of the project in the github repo here and you can import it and run it on your eclipse.
This example is based on Reto Meier's example on chapter four of his book "Professional Android 4 Application Development" you can find in this link

No comments:

Post a Comment