Asynchrony Solutions Blog

How to Reuse UI Components Using XML Layouts and the Inflater Service

by on February 28th, 2011 at 3:46 pm

Creating UI components for Android apps programmatically is difficult.  So, the Android framework provides a way to create UI components via XML.  The Eclipse Android SDK actually provides a tool for creating these XML UIs via drag-and-drop/WYSIWYG.  Now developers must manage XML documents along with their Java code, which can also be difficult.  To help alleviate some of these difficulties, the Android framework allows for reusing the XML views via the Inflater Service.

First, let’s define some UI components in XML.

The first XML layout will be the main layout that will be the base of the UI shown to the user. This could also be reused for all the screens as it is just an empty LinearLayout.

res/layout/main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
          android:id="@+id/main_layout" android:orientation="vertical"
          android:layout_width="fill_parent" android:layout_height="fill_parent">
     <TextView android:text="@string/title" android:layout_width="fill_parent"
               android:layout_height="wrap_content" />
</LinearLayout>

The second XML layout will be used for some text fields for a simple form.

res/layout/personnel_form.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
          android:orientation="vertical" android:layout_width="fill_parent"
          android:layout_height="wrap_content">
     <LinearLayout android:orientation="horizontal"
               android:layout_width="fill_parent"
               android:layout_height="wrap_content">
          <TextView android:text="@string/firstname_label"
               android:layout_height="wrap_content"
               android:layout_width="wrap_content" />
          <EditText android:id="@+id/firstname"
               android:layout_height="wrap_content"
               android:layout_width="fill_parent" />
     </LinearLayout>
     <LinearLayout android:orientation="horizontal"
          android:layout_width="fill_parent"
          android:layout_height="wrap_content">
          <TextView android:text="@string/lastname_label"
               android:layout_height="wrap_content"
               android:layout_width="wrap_content" />
          <EditText android:id="@+id/lastname"
               android:layout_height="wrap_content"
               android:layout_width="fill_parent" />
     </LinearLayout>
</LinearLayout>

The final XML layout will be an OK and Cancel button that could be reused for a number of other screens.

res/layout/buttons.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
          android:layout_height="wrap_content" android:orientation="horizontal"
          android:layout_width="fill_parent">
     <Button android:id="@+id/ok_button" android:text="@string/ok"
               android:layout_height="wrap_content"
               android:layout_width="fill_parent" android:layout_weight="1" />
     <Button android:id="@+id/cancel_button" android:text="@string/cancel"
               android:layout_height="wrap_content"
               android:layout_width="fill_parent" android:layout_weight="1" />
</LinearLayout>

Now we get down to obtaining and using an instance of the Inflater Service in the Activity.  To do this, we simply use the getSystemService() method giving it the name of the Inflater Service.

LayoutInflater inflater = (LayoutInflater) context.
     getSystemService(Context.LAYOUT_INFLATER_SERVICE);

Once you have an instance of the Inflator Service, you can call the inflate method giving it the XML layout that you want to use and the root view that you want to append it to.

LinearLayout mainLayout = (LinearLayout) findViewById(R.id.main_layout);
inflater.inflate(R.layout.personnel_form, mainLayout)

And finally putting it all together, here’s the Activity…

public class MyTestActivity extends Activity {
     @Override
     public void onCreate(Bundle savedInstanceState) {
          super.onCreate(savedInstanceState);
          setContentView(R.layout.main);

          LayoutInflater inflater = (LayoutInflater)
               getSystemService(LAYOUT_INFLATER_SERVICE);

          LinearLayout mainLayout = (LinearLayout) findViewById(R.id.main_layout);
          inflater.inflate(R.layout.personnel_form, mainLayout);
          inflater.inflate(R.layout.buttons, mainLayout);

          Button okButton = (Button) findViewById(R.id.ok_button);
          okButton.setOnClickListener(new View.OnClickListener() {
               @Override
               public void onClick(View v) {
                    EditText firstNameText = (EditText) findViewById(R.id.firstname);
                    EditText lastNameText = (EditText) findViewById(R.id.lastname);

                    String message = "Hello, " + firstNameText.getText() + " " +
                         lastNameText.getText() + "!";
                    Toast.makeText(MyTestActivity.this, message, Toast.LENGTH_LONG).
                         show();
               }
          });

          Button cancelButton = (Button) findViewById(R.id.cancel_button);
          cancelButton.setOnClickListener(new View.OnClickListener() {
               @Override
               public void onClick(View v) {
                    MyTestActivity.this.finish();
               }
          });
     }
}

Using this technique, you will be able to reuse portions of UI components for various screens in your Android application.

Tags: , , , ,

Cumulative-flow diagram can double as timeline

by on February 22nd, 2011 at 10:35 am

If you’re using kanban in your environment, you probably use a cumulative-flow diagram. It’s a handy tool to track kanban metrics like cycle time and to quickly see bottlenecks. In addition to all the kanban goodness it gives you, it can also double as a timeline that you can use in your retrospectives.

Whether you use a physical version posted on your kanban board (like my current team does) or an electronic one, you can annotate dates with important events, such as when:

  • A team member joins or leaves
  • An unexpected technical problem surfaces, like a major refactoring or bug
  • The team decides to change something about its kanban, like increase a WIP limit

It’s pretty easy to do, especially if you have a physical chart that you update during your standup meeting.

Then, when you have a retrospective, bring the diagram along to help you remember what happened during the period over which you’re retrospecting. If you’re anything like me, you have a hard time remembering what happened beyond yesterday, so it’s handy to have a reference. Having this time-based information will help you make more objective decisions about how to improve, since you won’t be guessing so much as to why your cycle time lengthened over the last week, or why you decided to decrease a WIP limit a month ago.

Tags: ,

I’m Not a Superhero, But I’ll Be Playing One in a Comic

by on February 10th, 2011 at 12:23 pm

Bill Howard and I will be co-presenting “Facilitating Change at United States Transportation Command” at the 2011 Association of Change Management Professionals Global Conference in May. Bill is going to share some of what he’s been doing as the Organization Change Management program lead for the CIO and Director of C4 Systems at USTRANSCOM. I’m going to give the audience a taste of the executive-level ChangeViz workshops I’ve been facilitating to support Bill’s CM efforts.

I thought it would be fun to put together a 16 page comic on ChangeViz as a leave behind. This is my favorite cover concept at the moment. Stay tuned for more updates.

Older Posts