Your First Android Application
This first chapter is full of new concepts and moving parts required to build an Android application.
The application you are going to create is called GeoQuiz. GeoQuiz tests the user’s knowledge of geography. The user presses TRUE or FALSE to answer the question on screen, and GeoQuiz provides instant feedback.

App Basics
Your GeoQuiz application will consist of an activity and a layout:
An activity is an instance of Activity, a class in the Android SDK. An activity is responsible for managing user interaction with a screen of information.
A layout defines a set of UI objects and their positions on the screen. A layout is made up of definitions written in XML.
The relationship between QuizActivity and activity_quiz.xml is diagrammed in the figure below

Creating an Android Project
The first step is to create an Android project. An Android project contains the files that make up an application. To create a new project, first open Android Studio.

Creating a new application

Specifying device support

Choosing a type of activity If your wizard looks very different, then the tools have changed more drastically. Do not panic.

Navigating in Android Studio
The lefthand view is the project tool window. From here, you can view and manage the files associated with your project.

Laying Out the UI
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="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=".MainActivity">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Hello World!"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintLeft_toLeftOf="parent"
app:layout_constraintRight_toRightOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
Widgets are the building blocks you use to compose a UI. A widget can show text or graphics, interact with the user, or arrange other widgets on the screen. Buttons, text input controls, and checkboxes are all types of widgets. The Android SDK includes many widgets that you can configure to get the appearance and behavior you want. Every widget is an instance of the View class or one of its subclasses (such as TextView or Button).
But these are not the widgets you are looking for. The interface for QuizActivity requires five widgets:
a vertical LinearLayout
a TextView
a horizontal LinearLayout
two Buttons

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:gravity="center"
android:orientation="vertical" >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="24dp"
android:text="@string/question_text" />
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal" >
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/true_button" />
<Button
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/false_button" />
</LinearLayout>
</LinearLayout>
The view hierarchy

Widget attributes
android:layout_width and android:layout_height
The android:layout_width and android:layout_height attributes are required for almost every type of widget. They are typically set to either match_parent or wrap_content:
Attribute
Description
match_parent
view will be as big as its parent
wrap_content
view will be as big as its contents require
android:orientation
The android:orientation attribute on the two LinearLayout widgets determines whether their children will appear vertically or horizontally. The root LinearLayout is vertical; its child LinearLayout is horizontal.
android:text
The TextView and Button widgets have android:text attributes. This attribute tells the widget what text to display.
Creating string resources
Open res/values/strings.xml. The template has already added one string resource for you. Add the three new strings that your layout requires.
<resources>
<string name="app_name">GeoQuiz</string>
<string name="question_text">Canberra is the capital of Australia.</string>
<string name="true_button">True</string>
<string name="false_button">False</string>
</resources>
Previewing the layout
Your layout is now complete, and you can preview the layout in the graphical layout tool.

From Layout XML to View Objects
When you created the GeoQuiz project, a subclass of Activity named QuizActivity was created for you. The class file for QuizActivity is in the app/java directory of your project. The java directory is where the Java code for your project lives.
package com.bignerdranch.android.geoquiz;
import android.support.v7.app.AppCompatActivity;
import android.os.Bundle;
public class QuizActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_quiz);
}
}
Wondering what AppCompatActivity is? It is a subclass of Android’s Activity class that provides compatibility support for older versions of Android. You will learn much more about AppCompatActivity in Chapter 13
The onCreate(Bundle) method is called when an instance of the activity subclass is created. When an activity is created, it needs a UI to manage. To get the activity its UI, you call the following Activity method:
public void setContentView(int layoutResID)
This method inflates a layout and puts it on screen.
Resources and resource IDs
A layout is a resource. A resource is a piece of your application that is not code – things like image files, audio files, and XML files.
To access a resource in code, you use its resource ID. The resource ID for your layout is R.layout.activity_quiz.
To generate a resource ID for a widget, you include an android:id attribute in the widget’s definition. In activity_quiz.xml, add an android:id attribute to each button.
<LinearLayout ... >
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="24dp"
android:text="@string/question_text" />
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:orientation="horizontal">
<Button
android:id="@+id/true_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/true_button" />
<Button
android:id="@+id/false_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/false_button" />
</LinearLayout>
</LinearLayout>
Wiring Up Widgets
Now that the buttons have resource IDs, you can access them in QuizActivity. The first step is to add two member variables.
public class QuizActivity extends AppCompatActivity {
private Button mTrueButton;
private Button mFalseButton;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_quiz);
}
}
Getting references to widgets
In an activity, you can get a reference to an inflated widget by calling the following Activity method:
public View findViewById(int id)
This method accepts a resource ID of a widget and returns a View object.
public class QuizActivity extends AppCompatActivity {
private Button mTrueButton;
private Button mFalseButton;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_quiz);
mTrueButton = (Button) findViewById(R.id.true_button);
mFalseButton = (Button) findViewById(R.id.false_button);
}
}
Setting listeners
Android applications are typically event driven. Unlike command-line programs or scripts, event driven applications start and then wait for an event, such as the user pressing a button.
Start with the TRUE button. In QuizActivity.java, add the following code to onCreate(Bundle) just after the variable assignment.
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_quiz);
mTrueButton = (Button) findViewById(R.id.true_button);
mTrueButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
// Does nothing yet, but soon!
}
});
mFalseButton = (Button) findViewById(R.id.false_button);
}
}
Set a similar listener for the FALSE button.
mTrueButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
// Does nothing yet, but soon!
}
});
mFalseButton = (Button) findViewById(R.id.false_button);
mFalseButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
// Does nothing yet, but soon!
}
});
}
Making Toasts
Now to make the buttons fully armed and operational. You are going to have a press of each button trigger a pop-up message called a toast. A toast is a short message that informs the user of something but does not require any input or action.

First, return to strings.xml and add the string resources that your toasts will display.
<resources>
<string name="app_name">GeoQuiz</string>
<string name="question_text">Canberra is the capital of Australia.</string>
<string name="true_button">True</string>
<string name="false_button">False</string>
<string name="correct_toast">Correct!</string>
<string name="incorrect_toast">Incorrect!</string>
</resources>
mTrueButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Toast.makeText(QuizActivity.this,
R.string.correct_toast,
Toast.LENGTH_SHORT).show();
}
});
mFalseButton = (Button) findViewById(R.id.false_button);
mFalseButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Toast.makeText(QuizActivity.this,
R.string.incorrect_toast,
Toast.LENGTH_SHORT).show();
}
});
Challenge: Customizing the Toast
In this challenge, you will customize the toast to show at the top instead of the bottom of the screen. To change how the toast is displayed, use the Toast class’s setGravity method.
Last updated
Was this helpful?