In this post I will explain the code I used for my UAT Tester App. The complete tutorial will be a combination of 4 posts. The UAT Tester app is an app I developed based on some small frustration I had during my role as Product Manager. The app can be used by User Acceptance Testers to raise defects, often a phase before the app is launched to the larger public. Often people who test your app have little or no experience with application development and raise issues (although briefed differently) in a lazy way. They send emails with a small text what they think is an issue or a defect. Unfortunately this information is often lacking important data to actually debug the issue. This results in additional emails requesting for more information like: device type, android version, priority, screenshots etc. This extra communication is for both parties the handler and the issue raiser a pain in the ass. Also this information is regarded as “hard” to find for the issue-raisers.
Well the UAT Tester app is an application you can distribute among your User Acceptance Testers and provide a simple tool and interface to raise defects to the product manager or test manager. The app retrieves essential information for debugging and the user of the app can send this information quickly via email to the test manager or product manager.
As said, this Tutorial exists out of 4 posts in total. I will discuss the following topics in each of the 4 posts.
Part 1: Design and Layout of the UAT Tester App;
Part 2: Create References of the layout in the Java class + use the Android Build API to retrieve device information;
Part 3: Create Image Picker for the Screenshots;
Part 4: Create Email Intent to send the information via a thirds part email client (e.g. Gmail /Exchange).
The following Android Framework classes are used: Build API, OnclickListeners, Email Intents, Relative Layout, ArrayAdapter, BitmapFactory.
TextViews:
Are used for the Static Headers like Device Information, Defect Description, Set Priority and Screenshot
TextViews:
Are used for the device parameters which we will retrieve from Android Device APIs
EditTexts:
Are used for the input fields Expected Results, Actual Results and Comments
Buttons:
Are used for sending the defect via email and adding a screenshot
Spinner:
Is used for setting the priority based on a drop-down list.
Please note that TextViews, EditText, Button and Spinner refer to the widgets in Android which are part of the layout-editor or XML definitions.
The first choice we had in designing the layout is to go for a Relative Layout or Linear Layout. In principle its your choice, but personally I like to work with the Relative Layout because of the more flexibility in building the Layout.
Also we need a ScrollView in our layout as the information and fields we want to display on our device extends the vertical height.
Use the following XML code in main.xml (project –> res –> layout –> main.xml)
So now we have defined our main layout, we need to add all the widgets we want to use for our UAT Tester App. Below you find the complete XML layout for the UAT Tester App. I will not go into every detail as it is pretty straightforward. But I highlighted some elements.
For positioning in the RelativeLayout you could use positioning in relation to the other widgets. For Example:
android:layout_below="@+id/tv_static_deviceinformation"
You can set easily the color of text or background via color codes:
android:textColor="#F78181"
or textsize:
android:textSize="8pt"
And here you see the complete layout for the UAT Tester App:
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="fill_parent" android:layout_height="fill_parent" android:fillViewport="true" > <RelativeLayout android:layout_width="match_parent" android:layout_height="800dp" android:paddingLeft="15dp" > <TextView android:id="@+id/tv_static_deviceinformation" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_alignParentTop="true" android:paddingLeft="10dp" android:paddingTop="5dp" android:text="Device Information:" android:textAppearance="?android:attr/textAppearanceLarge" android:textColor="#F78181" /> <TextView android:id="@+id/tv_softwarebrand" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/tv_static_deviceinformation" android:layout_marginTop="14dp" android:paddingLeft="10dp" android:text="tv_software brand" /> <TextView android:id="@+id/tv_devicebrand" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/tv_softwarebrand" android:paddingLeft="10dp" android:text="tv_devicebrand" /> <TextView android:id="@+id/tv_modeltype" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/tv_devicebrand" android:paddingLeft="10dp" android:text="tv_modeltype" /> <TextView android:id="@+id/tv_androidversion" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/tv_modeltype" android:paddingLeft="10dp" android:text="tv_androidversion" /> <TextView android:id="@+id/tv_screensize" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/tv_androidversion" android:paddingLeft="10dp" android:text="tv_screensize" /> <TextView android:id="@+id/tv_timestamp" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/tv_screensize" android:paddingLeft="10dp" android:text="tv_timestamp" /> <TextView android:id="@+id/tv_static_defectdes" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/tv_timestamp" android:layout_marginTop="14dp" android:paddingLeft="10dp" android:text="Defect Description:" android:textAppearance="?android:attr/textAppearanceLarge" android:textColor="#F78181" /> <EditText android:id="@+id/et_expected" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/tv_static_defectdes" android:layout_marginTop="10dp" android:ems="10" android:height="75dp" android:hint="Expected Results:" android:paddingLeft="10dp" > </EditText> <EditText android:id="@+id/et_actual" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/et_expected" android:layout_marginTop="29dp" android:ems="10" android:height="75dp" android:hint="Actual Result:" android:paddingLeft="10dp" > <requestFocus /> </EditText> <EditText android:id="@+id/et_comments" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="@+id/et_actual" android:layout_marginTop="34dp" android:ems="10" android:height="75dp" android:hint="Extra comments" android:paddingLeft="10dp" /> <TextView android:id="@+id/tv_static_prio" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_below="@+id/et_comments" android:layout_marginTop="27dp" android:paddingLeft="10dp" android:text="Set Priority:" android:textAppearance="?android:attr/textAppearanceLarge" android:textColor="#F78181" android:textSize="8pt" /> <Spinner android:id="@+id/sp_priority" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignLeft="@+id/tv_static_prio" android:layout_below="@+id/tv_static_prio" android:layout_marginTop="28dp" android:paddingLeft="10dp" android:textSize="10pt" /> <Button android:id="@+id/btn_screenshot" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentRight="true" android:layout_alignTop="@+id/sp_priority" android:layout_marginRight="18dp" android:text="Screenshot" /> <Button android:id="@+id/btn_email" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_below="@+id/btn_screenshot" android:layout_marginTop="60dp" android:paddingLeft="10dp" android:text="Email defect" /> <ImageView android:id="@+id/iv_thumbscr" android:layout_width="70dp" android:layout_height="70dp" android:layout_alignLeft="@+id/btn_screenshot" android:layout_alignTop="@+id/btn_email" android:background="#00000000" /> <TextView android:id="@+id/textView1" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_above="@+id/sp_priority" android:layout_alignRight="@+id/btn_screenshot" android:text="Add Screenshot" android:textAppearance="?android:attr/textAppearanceLarge" android:textColor="#F78181" android:textSize="8pt" /> </RelativeLayout> </ScrollView>
This was everything for Tutorial Part 1. In the next blog post we will start with our Java class.
2 Responses