intents - appspot.combranko-cirovic.appspot.com/cp3490/listviews.pdf · intents activity_main.xml...

181
Intents

Upload: hadieu

Post on 18-Sep-2018

217 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Intents

Page 2: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

So far our apps had a single view.

Next example demonstrates how to create a navigation path through series of views.

Create new project Button Intent.

Intents

Page 3: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

We’ll need some graphics (http://flaticons.net, Next-128.png saved as next.png)

Create folder drawable-xxhdpi relative to folder res, copy and paste downloaded image into newly created folder.

Intents

Page 4: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally centered with top margin of 64dp.

Intents

<LinearLayout android:id="@+id/next" android:orientation="vertical" android:layout_width="72dp" android:layout_height="96dp" android:layout_centerHorizontal="true" android:layout_marginTop="64dp">

Page 5: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Intents

<ImageButton android:layout_width="match_parent" android:layout_height="72dp" android:id="@+id/nextButton" android:gravity="center" android:background="@drawable/next" android:clickable="true"/>

Page 6: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Intents

<TextView android:layout_width="match_parent" android:layout_height="24dp" android:gravity="center_horizontal" android:layout_marginTop="6dp" android:text="Next"/> </LinearLayout>

Page 7: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

We need another activity to transition to. Create layout next_activity.xml. Inside a relative layout we have a single Textview:

Intents

Page 8: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Intents<TextView android:id="@+id/nextTextView" android:layout_width="match_parent" android:layout_height="wrap_content" android:text="Next Activity" android:fontFamily="sans-serif-light" android:textSize="24dp" android:layout_marginLeft="12dp" android:layout_marginRight="12dp" android:gravity="center_horizontal" android:layout_centerVertical=“true"/>

Page 9: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

NextActivity.java simply sets the content view to next_activity.xml

Intents

import android.support.v7.app.AppCompatActivity; import android.os.Bundle;

public class NextActivity extends AppCompatActivity {

@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.next_activity); } }

Page 10: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

In order to transition from MainActivity to NextActivity, we need to set onClickListener associated with the button:

Intents

ImageButton nextButton = (ImageButton)findViewById(R.id.nextButton); nextButton.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View view) { Intent nextScreen = new Intent(getApplicationContext(), NextActivity.class); startActivity(nextScreen); } });

Page 11: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

NextActivity must be registered in AndroidManifest.xml:

Intents

<activity android:name=".NextActivity"> </activity>

Page 12: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Sometimes we need to pass data between activities. Say, we wanted to pass a message from MainActivity to the NextActivity. In MainActivity, just before we start intent:

Intents

nextScreen.putExtra("message", "Hello from MainActivity");

Page 13: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

In NextActivity we have:

Intents

Bundle extras = getIntent().getExtras(); String message = extras.getString("message");

TextView nextText = (TextView) findViewById(R.id.nextTextView); nextText.setText(message);

Page 14: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

An intent is an abstract description of an operation to be performed. It can be used with one Activity to launch another.

The primary pieces of information in an intent are:

Intents

1. action -- The general action to be performed, such as ACTION_VIEW.

2. data -- The data to operate on.

Page 15: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ListView is a view group that displays a list of scrollable items.

The list items are automatically inserted to the list using an Adapter.

ListView.1.zip

ListView

Page 16: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Adapters

An adapter manages the data model and adapts it to the individual rows in the list view. An adapter extends the BaseAdapter class.

Every line in the list view consists of a layout which can be as complex as you want.

In its simplest form it consists of a single TextView

Page 17: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

activity_main.xml<?xml version="1.0" encoding="utf-8"?> <TextView xmlns:android="http:// schemas.android.com/apk/ res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:padding="10dp" android:textSize="20sp"> </TextView>

Page 18: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Adapters

The adapter would inflate the layout for each row in its getView() method and assign the data to the individual views in the row.

The adapter is assigned to the ListView via the setAdapter method on the ListView object.

Page 19: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.javapackage com.example.admin.listview1;

import android.app.ListActivity; import android.os.Bundle; import android.view.View; import android.widget.AdapterView; import android.widget.ArrayAdapter; import android.widget.ListView; import android.widget.TextView; import android.widget.Toast; import android.widget.AdapterView.OnItemClickListener;

public class MainActivity extends ListActivity {

Page 20: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.javastatic final String[] PROGRAMS = new String[] { "Architectural", "Civil", "Geomatics", "Computing Systems", "Electronics (Biomedical)", "Electronics (Instrumentation)", "Electrical (Power)", "Telecommunications", "Chemical Processing", "Industrial", “Mechanical", "Mechanical (Manufacturing)", "Petroleum"};

@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setListAdapter(new ArrayAdapter<String>(this, R.layout.activity_main,PROGRAMS));

ListView listView = getListView(); listView.setTextFilterEnabled(true);

Page 21: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.java

listView.setOnItemClickListener( new OnItemClickListener() { public void onItemClick(AdapterView<?> parent, View view, int position, long id) {

Toast.makeText(getApplicationContext(), ((TextView) view).getText(), Toast.LENGTH_SHORT).show(); } });

Page 22: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

In many cases, single title inside list view’s cell is not sufficient ( e.g. Play Store )

Android allows us to define layout of cells in any way imaginable.

ListView.2.zip

CustomAdapters

Page 23: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Custom Adapters

Computing SystemsEngineering Technology

TextView

RelativeLayout

TextView

ImageView

In our case, cell might look like:

Page 24: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Custom Adapters

Create drawable-xxhdpi folder as before and paste into it right_arrow.png

Cell layout will be defined in rowlist.xml file: right-click on layout subdirectory and select New, XML, Layout XML file.

Page 25: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

rowlist.xml<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/ res/android" android:orientation="horizontal" android:layout_width="match_parent" android:layout_height="match_parent" android:padding="10dp">

<TextView android:id="@+id/textid" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="text" android:textColor="#666" android:textSize="20sp"/>

Page 26: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

rowlist.xml <TextView android:id="@+id/subtextid" android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_below="@id/textid" android:textColor="#aaa" android:textSize="12sp" android:text="subtext" android:layout_marginTop=“0dp"/>

<ImageView android:layout_width="wrap_content" android:layout_height="wrap_content" android:src="@drawable/right_arrow" android:layout_alignParentRight="true" android:layout_centerVertical="true"/> </RelativeLayout>

Page 27: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

activity_main.xml

<LinearLayout android:orientation="vertical" android:layout_width="match_parent" android:layout_height=“match_parent" android:background="#ffffff"> <ListView android:layout_width="wrap_content" android:layout_height="wrap_content" android:id="@+id/programListView" android:layout_gravity="center" android:layout_marginLeft="16dp" android:layout_marginRight="16dp" android:clickable="true"/> </LinearLayout>

Contains a single ListView inside LinearLayout :

Page 28: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Custom Adapters

In order to create custom adapter, we have to create new class ProgramAdapter.java which extends ArrayAdapter.

Right-click on first subfolder relative to java folder, New, Java Class, ProgramAdapter.

Page 29: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ProgramAdapter.javapackage com.example.admin.listview2;

import android.widget.ArrayAdapter; import android.content.Context; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.TextView;

public class ProgramAdapter extends ArrayAdapter <String> { private Context context; private String[] items;

Page 30: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ProgramAdapter.javapublic ProgramAdapter(Context context, String[] items) {

super(context, R.layout.rowlist, R.id.textid, items); this.context = context; this.items = items; }

@Override public View getView(int position, View convertView, ViewGroup parent) { LayoutInflater inflater = (LayoutInflater) context .getSystemService( Context.LAYOUT_INFLATER_SERVICE);

Page 31: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ProgramAdapter.java View rowView = inflater.inflate(R.layout.rowlist, parent, false); TextView textView = (TextView) rowView.findViewById(R.id.textid); TextView subTextView = (TextView) rowView.findViewById(R.id.subtextid); textView.setText(items[position]); subTextView.setText("Engineering Technology"); return rowView; } }

Page 32: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.javapackage com.example.admin.listview2;

import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.widget.ListView; import android.widget.AdapterView.OnItemClickListener; import android.widget.AdapterView; import android.view.View; import android.widget.Toast;

public class MainActivity extends AppCompatActivity { static final String[] PROGRAMS = new String[] { "Architectural", "Civil", "Geomatics", "Computing Systems", "Biomedical", "Instrumentation", "Electrical (Power)", "Telecommunications", "Chemical Processing", "Industrial", “Mechanical", "Manufacturing", "Petroleum" };

Page 33: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.java

@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main);

ListView programListView = (ListView) findViewById(R.id.programListView); programListView.setAdapter(new ProgramAdapter(this, PROGRAMS)); programListView.setTextFilterEnabled(true);

Page 34: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.java programListView.setOnItemClickListener(new OnItemClickListener() { @Override public void onItemClick(AdapterView<?> parent, View view, int position, long id) { String selectedValue = (String) parent.getItemAtPosition(position); Toast.makeText(getBaseContext(), selectedValue, Toast.LENGTH_SHORT).show(); } }); } }

Page 35: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ListView Intents

Page 36: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ListView Intents

ListView.3.zip

Now that we have a list of programs, how would one create a list of courses based on a selected program?

In order to do so, we have to create an Intent. In general, for each new view we have to:

Page 37: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ListView Intents

1. Create layout ( xml ) in res/layout

2. Create activity ( java ) in java/com.example.listview or similar

3. Create Intent in activity

4. Register activity in AndroidManifest.xml

Page 38: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ListView Intents

Create new layout courses.xml.

Since both, programs and courses are lists, copy content of activity_main.xml, paste it into courses.xml

Replace id programListView with courseListView.

Page 39: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

courses.xml<LinearLayout android:orientation="vertical" android:layout_width="match_parent" android:layout_height=“match_parent" android:background="#fff">

<ListView android:layout_width="wrap_content" android:layout_height="wrap_content" android:id="@+id/courseListView" android:layout_gravity="center" android:layout_marginLeft="16dp" android:layout_marginRight="16dp" android:background="#fff" android:clickable="true"/> </LinearLayout>

Page 40: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Courses Adapter

Before we implement ComputingActivity ( shows courses in Computing Systems ) we have to create CourseAdapter.java

ProgramAdapter’s subtext was constant - Engineering Technology. Here, subtext is course’s number.

Page 41: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CourseAdapter.java

package com.example.admin.listview3;

import android.widget.ArrayAdapter; import android.content.Context; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.TextView;

public class CourseAdapter extends ArrayAdapter <String> { private Context context; private String[] items;

Page 42: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CourseAdapter.java

public CourseAdapter(Context context, String[] items) { super(context, R.layout.rowlist, R.id.textid, items); this.context = context; this.items = items; }

@Override public View getView(int position, View convertView, ViewGroup parent) { LayoutInflater inflater = (LayoutInflater) context .getSystemService( Context.LAYOUT_INFLATER_SERVICE);

Page 43: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CourseAdapter.java

View rowView = inflater.inflate(R.layout.rowlist, parent, false); TextView textView = (TextView) rowView.findViewById(R.id.textid); TextView subTextView = (TextView) rowView.findViewById(R.id.subtextid); textView.setText(items[position]);

String s = items[position];

Page 44: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CourseAdapter.java if (s.equals("Active Circuit Applications")) subTextView.setText("AE3130"); else if (s.equals("Switching and L2 Security")) subTextView.setText("CE3370"); else if (s.equals("Software Engineering")) subTextView.setText("CP3490"); else if (s.equals("Databases")) subTextView.setText("CP3520"); else if (s.equals("Project Management")) subTextView.setText("PR3150"); else if (s.equals("Capstone Project")) subTextView.setText("PR2760");

return rowView; } }

Page 45: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Computing Activity

Create new file ComputingActivity.java in java subfolder folder, as you did before.

Computing Activity should simply display the list of courses when Computing Systems is selected ( onItemClick ) in MainActivity.

Page 46: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ComputingActivity.javapackage com.example.admin.listview3;

import android.os.Bundle; import android.support.v7.app.AppCompatActivity; import android.view.View; import android.widget.AdapterView; import android.widget.AdapterView.OnItemClickListener; import android.widget.ListView; import android.widget.Toast;

public class ComputingActivity extends AppCompatActivity { static final String[] COURSES = new String[] { "Active Circuit Applications", "Switching and L2 Security", "Software Engineering", "Databases", "Project Management", "Capstone Project" };

Page 47: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ComputingActivity.java

@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.courses);

ListView courseListView = (ListView) findViewById(R.id.courseListView); courseListView.setAdapter(new CourseAdapter(this, COURSES)); courseListView.setTextFilterEnabled(true);

Page 48: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ComputingActivity.java courseListView.setOnItemClickListener(new OnItemClickListener() { @Override public void onItemClick(AdapterView<?> parent, View view, int position, long id) { String selectedValue = (String) parent.getItemAtPosition(position); Toast.makeText(getBaseContext(), selectedValue, Toast.LENGTH_SHORT).show(); } }); }

Page 49: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

IntentNow, in order to link MainActivity to ComputingActivity, we have to create Intent in MainActivity ( instead of Toast ):

if(selectedValue.equals("Computing Systems")) { Intent computingScreen = newIntent(getApplicationContext(), ComputingActivity.class); startActivity(computingScreen); }

Page 50: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Intent

Before we can test our App, we have to register new activity ( ComputingActivity ) in Manifest file.

<activity android:name=".ComputingActivity" android:label="Courses" android:screenOrientation="portrait" />

Page 51: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Smooth Transitions

Android transitions between activities are quite simple - new view simply pops up. Animated transitions are accomplished through XML.

First of all, right-click on ListView/res and select New, Folder. Name it anim.

Copy slide_*xml files into anim folder.

Page 52: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Smooth Transitions

In MainActivity.java, after startActivity(computingScreen); add line:

overridePendingTransition( R.anim.slide_in_right, R.anim.slide_out_left);

Page 53: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Smooth Transitions

In Computing Activity.java, add method:

@Override public void onBackPressed() { super.onBackPressed(); overridePendingTransition( R.anim.slide_in_left, R.anim.slide_out_right ); }

Page 54: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ListView and XML

Page 55: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ListView and XMLSo far, our list views were populated by static data - array lists.

This is not normally the case - data is normally provided via XML files ( plain text files or output of database queries ).

Typically, data needs to be fetched from specified URL ( if network is available ), parsed and stored in a ArrayList. (ListView.4.zip)

Page 56: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ListView and XML

Networkavailable

class GetXML extends AsyncTask

doInBackground() { // fetch file }

onPostExecute() { // parse file }

T

Alert Error

F

Page 57: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Program’s XML structureEach program has associated XML file stored in Google cloud whose structure is:

<?xml version="1.0"?> <courses> <semester> <number>1</number> <course> <cid>CM1400</cid> <cname>Technical Report Writing I</cname> <credit>3</credit> <lect>3</lect> <lab>0</lab> </course> ... </semster> ... <courses>

Page 58: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

NetworkingBefore we can request particular file, we have to construct file’s name based on selection ( Computing Systems - cs.xml etc. )

In MainActivity.java declare class variable : private String loc = new String();

Now, in onItemClick() method determine which file is to be fetched:

Page 59: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

NetworkingStringBuffer sb = new StringBuffer(); sb.append("http://your-url.appspot.com/etcapp/programs/"); if(selectedValue.equals("Architectural")) sb.append("ae.xml"); else if(selectedValue.equals("Civil")) sb.append("ce.xml"); else if(selectedValue.equals("Geomatics")) sb.append("ge.xml"); else if(selectedValue.equals("Biomedical")) sb.append("eb.xml"); else if(selectedValue.equals("Computing Systems")) sb.append("cs.xml"); else if(selectedValue.equals("Electrical (Power)")) sb.append("ep.xml"); else if(selectedValue.equals("Instrumentation")) sb.append("ei.xml");

Page 60: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Networking

else if(selectedValue.equals("Telecommunications")) sb.append("te.xml"); else if(selectedValue.equals("Chemical Processing")) sb.append("cp.xml"); else if(selectedValue.equals("Industrial")) sb.append("in.xml"); else if(selectedValue.equals("Mechanical")) sb.append("me.xml"); else if(selectedValue.equals("Manufacturing")) sb.append("mm.xml"); else if(selectedValue.equals("Petroleum")) sb.append("pe.xml"); loc = sb.toString();

Page 61: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Networking

Before we can access network, we have to enable it in Manifest.xml ( before opening <application> tag ):

<uses-permission android:name="android.permission.INTERNET"/><uses-permission android:name="android.permission. ACCESS_NETWORK_STATE"/>

Page 62: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Networking

Now we can check the network status :

if(!isNetworkAvailable()) new AlertDialog.Builder(MainActivity.this). setTitle("Error").setMessage("No Network Connection"). setNeutralButton("Close", null).show(); else { // fetch and process data }

Page 63: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Networkingpublic boolean isNetworkAvailable() { ConnectivityManager cm = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE); NetworkInfo networkInfo = cm.getActiveNetworkInfo(); if (networkInfo != null && networkInfo.isConnected()) return true; else return false; }

Page 64: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Fetching data

To provide a good user experience all potentially slow running operations in an Android application should run asynchronously, e.g. via some way of concurrency.

This includes all potentially slow operations, like network, file and database access and complex calculations.

Page 65: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

AsyncTask classThe AsyncTask class encapsulates the creation of a background process and the synchronization with the main thread.

To use AsyncTask we must subclass it. Parameters are generics ( type of arguments, progress value and result value ), e.g : AsyncTask <String, Void, String>

Page 66: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

AsyncTask class

An AsyncTask is started via the execute() method.

The execute() method calls the doInBackGround() and the onPostExecute() method.

Page 67: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

AsyncTask class

The doInBackGround() method contains the coding instruction which should be performed in a background thread.

This method runs automatically in a separate Thread.

Page 68: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

AsyncTask class

The onPostExecute() method synchronizes itself again with the user interface thread and allows it to be updated.

This method is called by the framework once the doInBackGround() method finishes.

Page 69: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

AsyncTask class

The else part calls execute("") method of the subclass GetXML:

if(!isNetworkAvailable()) new AlertDialog.Builder(MainActivity.this). setTitle("Error").setMessage("No Network Connection"). setNeutralButton("Close", null).show(); else { new GetXML().execute(""); }

Page 70: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

AsyncTask classprivate class GetXML extends AsyncTask<String, Void, String> { String src = null; @Override protected String doInBackground(String... params) { try { URL url = new URL(loc); HttpURLConnection con = (HttpURLConnection) url.openConnection(); src = readStream(con.getInputStream()); } catch (Exception e) { e.printStackTrace(); } return src; }

Page 71: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

AsyncTask class @Override protected void onPostExecute(String result) { if(src == null) new AlertDialog.Builder(MainActivity.this). setTitle("Error").setMessage("No Courses Found"). setNeutralButton("Close", null).show(); else { System.out.println(src); } }

@Override protected void onPreExecute() {}

@Override protected void onProgressUpdate(Void... values) {} }

Page 72: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

readStream() Methodprivate String readStream(InputStream in) { BufferedReader reader = null; String line = null; StringBuffer sb = new StringBuffer(); try { reader = new BufferedReader(new InputStreamReader(in)); while ((line = reader.readLine()) != null { sb.append(line); } } catch (IOException e) { e.printStackTrace(); } finally { if (reader != null) { try { reader.close(); } catch (IOException e) { e.printStackTrace(); } } } return sb.toString(); }

Page 73: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML Parsing

Now that we fetched the file, we have to process it ( parse it ), in order to provide the data for courses list.

It is recommended to use the XmlPullParser ( simpler and faster than SAX and DOM Java parsers ). This parser is not available in standard Java.

Page 74: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML ParsingThere are two key methods: next() and nextToken().

While next() provides access to high level parsing events, nextToken() allows access to lower level tokens.

The current event state of the parser can be determined by calling the getEventType() method. Initially, the parser is in the START_DOCUMENT state.

Page 75: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML ParsingThe current event state of the parser can be determined by calling the getEventType() method.

Initially, the parser is in the START_DOCUMENT state.

The method next() advances the parser to the next event. Th following event types are seen by next():

Page 76: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML Parsing1. START_TAG -- An XML start tag was read.

2. TEXT -- Text content was read; getText() can retrieve it.

3. END_TAG -- An end tag was read

4. END_DOCUMENT -- No more events are available

Page 77: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML Parsing exampleimport java.io.IOException; import java.io.StringReader;

import org.xmlpull.v1.XmlPullParser; import org.xmlpull.v1.XmlPullParserException; import org.xmlpull.v1.XmlPullParserFactory;

public class SimpleXmlPullApp { public static void main (String args[]) throws XmlPullParserException, IOException {

XmlPullParserFactory factory = XmlPullParserFactory.newInstance(); factory.setNamespaceAware(true); XmlPullParser xpp = factory.newPullParser();

Page 78: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML Parsing example xpp.setInput(new StringReader("<foo>Hello</foo>")); int eventType = xpp.getEventType(); while (eventType != XmlPullParser.END_DOCUMENT) { if(eventType == XmlPullParser.START_DOCUMENT) { System.out.println("Start document"); } else if(eventType == XmlPullParser.START_TAG) { System.out.println("Start tag "+xpp.getName());           } else if(eventType == XmlPullParser.END_TAG) {               System.out.println("End tag "+xpp.getName());           } else if(eventType == XmlPullParser.TEXT) {               System.out.println("Text "+xpp.getText());           }           eventType = xpp.next(); } System.out.println("End document"); } }

Page 79: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML Parsing

The example would generate the output:

Start document Start tag foo Text Hello End tag foo End document

Page 80: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML Parsing

Where would we use XML parser?

We could use it in MainActivity, create ArrayList of courses and pass it to CoursesActivity, or

We could pass the String src to CoursesActivity and parse it there.

Page 81: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Courses Activity

We don’t need Computing Activity anymore.

Instead we will develop CoursesActivity which displays all the courses based on selected program in a ListView.

Page 82: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

courses.xml

MainActivity will pass program’s name and source ( XML file ). Parsing will be done in CoursesActivity.

We start with courses.xml -- similar to existing one, except that list is below header displaying program’s name.

Page 83: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

courses.xml<?xml version="1.0" encoding="utf-8"?>

<LinearLayout android:orientation="vertical" android:layout_width="fill_parent" android:layout_height="fill_parent" android:background="#fff" xmlns:android="http://schemas.android.com/apk/res/android"> <LinearLayout android:layout_width="match_parent" android:layout_height="96dp" android:orientation="vertical" android:background="#055b8c" android:gravity="center" android:layout_marginBottom="0dp">

Page 84: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

courses.xml <TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:id="@+id/programTitle" android:gravity="center" android:text="Computing Systems" android:textColor="#fff" android:textSize="20sp"/> <TextView android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="center" android:text="Engineering Technology" android:textColor="#fff" android:textSize="20sp"/>

Page 85: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

courses.xml

<ListView android:layout_width="wrap_content" android:layout_height="wrap_content" android:id="@+id/courseListView" android:layout_gravity="center" android:layout_marginLeft="16dp" android:layout_marginRight="16dp" android:background="#fff" android:clickable="true"/> </LinearLayout>

Page 86: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Courses Activity

We have to pass program’s name and xml file (src ) to CoursesActivity. But how to do that since Activity’s constructor takes no arguments?

Android provides mechanism for that through method putExtra("name", variable) as in :coursesScreen.putExtra("source", src);

Page 87: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CoursesActivity.java

package com.example.listview;

import android.os.Bundle; import android.app.Activity; import android.widget.TextView;

public class CoursesActivity extends Activity { private String source = null; private String programTitle = null;

@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.courses);

Page 88: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CoursesActivity.java Bundle extras = getIntent().getExtras(); source = extras.getString("source"); programTitle = extras.getString("programTitle"); TextView title = (TextView)findViewById(R.id.programTitle); title.setText(programTitle); System.out.println(source); }

@Override public void onBackPressed() { super.onBackPressed(); overridePendingTransition(R.anim.slide_in_left, R.anim.slide_out_right); } }

Page 89: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Main ActivityBack to MainActivity, onPostExecute() method, else part:

Intent coursesScreen = new Intent(getApplicationContext(), CoursesActivity.class); coursesScreen.putExtra("source", src); coursesScreen.putExtra("programTitle", title); startActivity(coursesScreen); overridePendingTransition(R.anim.slide_in_right, R.anim.slide_out_left);

Page 90: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Main Activity

There is an error, since variable title is not declared. Declare it under the declaration of variable loc:

private String title = new String();

Page 91: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Main Activity

Observe that title has the same value as selectedValue in onItemClick() method. So set it to:

title = selectedValue;

In Manifest, change ComputingActivity to CoursesActivity, cross fingers and run.

Page 92: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Parsing

Once we are done with parsing, for each semester we need ArrayList of courses, e.g ;

cname_1 cid_1credit lect lab

cname_2 cid_2credit lect lab

cname_2 cid_2credit lect lab

...

Page 93: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Parsing

Declare, therefore, array of ArrayLists of type Course. We’ll get an error, since we don’t have class Course.

private ArrayList<Course>[] courses;

Page 94: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Course.javapackage com.example.listview;

class Course { private String cname, cid; private String credit, lect, lab; public Course(String cid, String cname, String credit, String lect, String lab) { this.cid = cid; this.cname = cname; this.credit = credit; this.lect = lect; this.lab = lab; } public String getCid() { return cid; }

Page 95: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Course.java

public String getCname() { return cname; } public String getCredit() { return credit; } public String getLect() { return lect; } public String getLab() { return lab; } public String toString() { return cid + " " + cname + " " + credit + " " + lect + " " + lab; } }

Page 96: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Courses Activity

How many semesters are in a program?

Depends on the program. In order to create array courses we need to find out the number of semester:

Page 97: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Courses Activity

Where numberOfSections is class’ private variable

numberOfSections = 0; StringTokenizer st = new StringTokenizer(source); while(st.hasMoreTokens()) { String token = st.nextToken(); if(token.equals("<semester>")) numberOfSections++; } courses = new ArrayList[numberOfSections];parseXML(source);

Page 98: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

parseXML(String)public void parseXML(String src) { try { StringReader sr = new StringReader(src); XmlPullParserFactory factory = XmlPullParserFactory.newInstance(); factory.setNamespaceAware(true); XmlPullParser xpp = factory.newPullParser(); xpp.setInput(sr); String cid = new String(); String cname = new String(); String credit = new String(); String lect = new String(); String lab = new String(); int eventType = xpp.getEventType(); int semester = 0;

Page 99: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

parseXML(String)while (eventType != XmlPullParser.END_DOCUMENT) { String name = null; switch(eventType) { case XmlPullParser.START_TAG : name = xpp.getName(); if(name.equals("semester")) { courses[semester] = new ArrayList<Course>(); semester++; } else if(name.equals("cid")) { cid = xpp.nextText(); } else if(name.equals("cname")) { cname = xpp.nextText();

Page 100: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

parseXML(String) } else if(name.equals("credit")) { credit = xpp.nextText(); } else if(name.equals("lect")) { lect = xpp.nextText(); } else if(name.equals("lab")) { lab = xpp.nextText(); int index = semester - 1; Course c = new Course(cid, cname, credit, lect, lab); courses[index].add(c); } } eventType = xpp.next(); } }

Page 101: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

parseXML(String)

catch (Exception e) { e.printStackTrace(); }

for(int i = 0; i < courses.length; i++) { System.out.println(i); for(int j = 0; j < courses[i].size(); j++) { System.out.println(courses[i].get(j)); } } }

Page 102: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Course AdapterNow that we have array of linked list, we have to somehow pass course’s name and id to adapter.

Single array of strings is not going to do it. Hash map will, where cid is the key and cname is the value. In Courses Activity, after parseXML(source) add:

List<Map<String, String>> data = new LinkedList<Map<String, String>>();

Page 103: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Course AdapterWe will also need a couple of fields and a method for adding tuples ( before onCreate ):

public final static String ITEM_TITLE = "cid"; public final static String ITEM_CAPTION = "cname"; public Map<String, String> createItem(String cid, String cname) { Map<String,String> item = new HashMap<String,String>(); item.put(ITEM_TITLE, cid); item.put(ITEM_CAPTION, cname); return item; }

Page 104: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Course Adapter

Now we can populate our Map with data and create list view:

for(int i = 0; i < courses.length; i++) { for(int j = 0; j < courses[i].size(); j++) { data.add(createItem(courses[i].get(j).getCid(), courses[i].get(j).getCname())); } }

Page 105: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Course Adapter

ListView coursesListView = (ListView) findViewById(R.id.coursesListView); coursesListView.setAdapter(new CourseAdapter( this, data, R.layout.coursesrowlist, new String[] { ITEM_TITLE, ITEM_CAPTION }, new int[] { R.id.subtextid, R.id.textid })); coursesListView.setTextFilterEnabled(true);

Page 106: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Course Adapter

Observe the difference in Adapter’s constructor. Here we are extending SimpleAdapter, rather than ArrayAdapter.

SimpleAdapter is an adapter to map static data to views defined in an XML file. The Maps contain the data for each row.

Page 107: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Course AdapterConstructor takes context, data (map), resource (xml layout of each row), from (key and value) and to - text views in resource.

SimpleAdapter( this, data, R.layout.coursesrowlist, new String[] { ITEM_TITLE, ITEM_CAPTION }, new int[] { R.id.subtextid, R.id.textid } )

Page 108: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

courserowlist.xml<?xml version="1.0" encoding="utf-8"?>

<RelativeLayout xmlns:android= "http://schemas.android.com/apk/res/android" android:orientation="horizontal" android:layout_width="match_parent" android:layout_height="match_parent" android:padding="10dp">

<TextView android:id="@+id/textid" android:layout_width="wrap_content" android:layout_height="wrap_content" android:textColor="#666" android:textSize="14sp" android:text="Text"/>

Page 109: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

courserowlist.xml <TextView android:id="@+id/subtextid" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_below="@id/textid" android:textColor="#aaa" android:textSize="12sp" android:layout_marginTop="0dp" android:text="subtext"/>

<ImageView android:layout_width="wrap_content" android:layout_height="wrap_content" android:src="@drawable/right_arrow" android:layout_alignParentRight="true" android:layout_centerVertical="true"/> </RelativeLayout>

Page 110: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CourseAdapter.javapackage com.example.listview;

import java.util.List; import java.util.Map; import android.widget.SimpleAdapter; import android.content.Context; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.TextView;

public class CourseAdapter extends SimpleAdapter { private Context context; private List<? extends Map<String, String>> items; private int resource;

Page 111: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CourseAdapter.java

public CourseAdapter(Context context, List<? extends Map<String, String>> items, int resource, String[] from, int[] to) { super(context, items, resource, from, to); this.context = context; this.items = items; this.resource = resource; }

Page 112: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CourseAdapter.java@Override public View getView(int position, View convertView, ViewGroup parent) {

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

View rowView = inflater.inflate(resource, parent, false); Map <String, String> map = items.get(position); String title = map.get("cname"); String subtitle = map.get("cid");

Page 113: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CourseAdapter.java TextView textView = (TextView) rowView.findViewById(R.id.textid); textView.setText(title); TextView subTextView = (TextView) rowView.findViewById(R.id.subtextid); subTextView.setText(subtitle);

return rowView; } }

That’s it. Try to run it. (End of ListView.4.zip)

Page 114: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Dig deeper…

Page 115: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Detail Course View

ListView.5.zip

When user selects particular course from the list of courses, detailed view of course name, number, credit, lecture and lab hours should be displayed.

Page 116: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Detail Course View

We begin with the course.xml layout. Add it to res/layout folder.

Another file is required for round-corners background: listview_border.xml. Place it inside res/drawable-xxhdpi

Page 117: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

course.xml

TextView

LinearLayout

TableLayout

Page 118: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Detail Course ViewIn Android we can use Shape Drawables to define background, borders and gradients for Views.

listview_border.xml is an example of drawable shape.

More details at : http://developer.android.com/reference/android/graphics/drawable/shapes/package-summary

Page 119: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Course ActivityIn Courses Activity, we have to set onItemClick listener and based on selected value ( cid ), find requested course in our array of linked lists.

Courses name, number of credit, lecture and lab hours should be extracted and Course Activity start as new Intent.

See CoursesActivity.java and CourseActivity.java for details.

Page 120: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

SectionsListWithSections.zip

Unlike iOS, Android does not provide easy implementation of grouped lists.

Credit for adapter goes to Jeff Sharkey.

Page 121: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Separated List Adapter

SeparatedListAdapter class provides a single interface to multiple sections of other Adapters.

After using addSection() to construct the child sections, we can easily use ListView.setAdapter() to present the now-separated list to users.

Page 122: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

LayoutsThree layouts are required:

1. activity_main.xml - LinearLayout with no children. ListView is programatically added in MainActivity.

2. rowlist.xml - defines regular rows in ListView

3. list_header.xml - defines header for each section

Page 123: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity

Sections are created in MainActivity:List<Map<String,?>> construction = new LinkedList<Map<String,?>>(); construction.add(createItem("Architectural", "Engineering Technology")); construction.add(createItem("Civil", "Engineering Technology")); construction.add(createItem("Geomatics", “Engineering Technology"));

Page 124: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity

Instance of SeparatedListAdapter is created:

SeparatedListAdapter adapter = new SeparatedListAdapter(this);

Page 125: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity

Items are added to sections:

adapter.addSection("CONSTRUCTION", new SimpleAdapter(this, construction, R.layout.rowlist, new String[] { ITEM_TITLE, ITEM_CAPTION }, new int[] { R.id.textid, R.id.subtextid }));

Page 126: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Separated List Adapter

"CONSTRUCTION" is section’s title

SimpleAdapter is an adapter to map static data to views defined in an XML file.

Constructor takes several arguments:

Page 127: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Separated List Adapter

context -- The context where the View associated with this SimpleAdapter is running

data -- A List of Maps. Each entry in the List corresponds to one row in the list. The Maps contain the data for each row, and should include all the entries specified in "from".

Page 128: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Separated List Adapter

resource -- Resource identifier of a view layout that defines the views for this list item. The layout file should include at least those named views defined in “to".

from -- A list of column names that will be added to the Map associated with each item.

Page 129: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Separated List Adapter

to -- The views that should display column in the "from" parameter. These should all be TextViews. The first N views in this list are given the values of the first N columns in the from parameter.

Page 130: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Separated List AdapterOnce the sections are created, we define ListView programatically and add it to the LinearLayout defined in activity_main.xml:

ListView list = new ListView(this); list.setAdapter(adapter); list.setBackgroundColor(Color.WHITE); LinearLayout ll = (LinearLayout) findViewById(R.id.mainlayout); ll.addView(list);

Page 131: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Lazy Image Loader

In many applications (Play store, News etc.) it is impractical to download all images before they are displayed.

Instead, such apps begin by loading the relevant text from RSS feed, and then download icons asynchronously so that user interface is more responsive.

Page 132: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Lazy News

LazyNews.1.zip

Page 133: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Lazy Image Loader

There is a number of helper classes that need to be imported into the project:

AsyncResponse.java, FileCache.javaFileDownloader.java, ImageLoader.javaLazyNewsAdapter.java, MemoryCache.javaUtils.java as well as placeholder.png

Page 134: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity

MainActivity is quite simple: it sets UI activity_main.xml displaying a progress bar and checks for network connectivity.

If there is no network, it displays error_layout.xml, otherwise it transitions into NewsActivity which asynchronously fetches and displays news.

Page 135: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity

networkavailable

error_layout.xml

NewsActivity (parse and display

list of news)

YES

NO

MainActivity

Page 136: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

activity_main.xml<RelativeLayout xmlns:android="http://schemas.android.com/apk/res android" xmlns:tools="http://schemas.android.com/tools" android:id="@+id/loadingPanel" android:layout_width="match_parent" android:layout_height="match_parent" android:gravity = "center_vertical|center_horizontal" tools:context=".MainActivity">

<ProgressBar android:layout_width="wrap_content" android:layout_height="wrap_content" android:gravity = "center_vertical|center_horizontal" android:indeterminate="true"/> </RelativeLayout>

Page 137: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

error_layout.xml<RelativeLayout xmlns:android="http://schemas.android.com/apk/res android" android:layout_width="match_parent" android:layout_height="match_parent" android:background=“#eeeeee"> <TextView android:id="@+id/errorMessage" android:layout_width="match_parent" android:layout_height="wrap_content" android:text="Error" android:textSize="24dp" android:textColor="#888888" android:paddingLeft="24dp" android:paddingRight="24dp" android:layout_centerInParent="true" android:gravity="center"/> </RelativeLayout>

Page 138: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.javapublic class MainActivity extends AppCompatActivity {

@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main);

ConnectivityManager connManager = (ConnectivityManager) getSystemService(CONNECTIVITY_SERVICE); NetworkInfo mWifi = connManager.getNetworkInfo( ConnectivityManager.TYPE_WIFI); NetworkInfo mMobile = connManager.getNetworkInfo( ConnectivityManager.TYPE_MOBILE);

Page 139: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.java

if (mWifi.isConnected() == false && mMobile.isConnected() == false) { showErrorView(); } else { System.out.println("Connected"); setContentView(R.layout.activity_main); findViewById(R.id.loadingPanel). setVisibility(View.VISIBLE); FileDownloader news = new FileDownloader("http://branko-cirovic.appspot.com/ etcapp/news/news.xml", MainActivity.this);

Page 140: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.java news.setOnResultsListener(new AsyncResponse() { @Override public void processFinish(String output) { Intent newsScreen = new Intent(getApplicationContext(), NewsActivity.class); newsScreen.putExtra("xmlData", output); findViewById(R.id.loadingPanel). setVisibility(View.GONE); startActivity(newsScreen); } }); news.execute(); } }

Page 141: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity.java

private void showErrorView() { setContentView(R.layout.error_layout); TextView errorView = (TextView) findViewById(R.id.errorMessage); errorView.setText("App cannot connect to network. Check network settings and try again."); } }

Page 142: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

NewsActivityNewsActivity will now extract xmlData downloaded and passed from MainActivity, parse it and store it in ArrayList newsData.

This list provides data to LazyNewsAdapter.

ntitle_1ndate_1 nimage_1 nurl_1 ndescription_1

ntitle_2ndate_2 nimage_2 nurl_2 ndescription_2

ntitle_nndate_n nimage_n nurl_n ndescription_n

Page 143: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

NewsActivity.java

Required layouts are news_layout.xml (simple ListView) and news_cell.xml (image and textviews for headline and date.

We also need the News.java class for our ArrayList newsData.

Page 144: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

NewsActivity.java

Make sure that Network permissions are set in Manifest.xml:

<uses-permission android:name="android.permission.INTERNET"/> <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>

Register NewsActivity in Manifest and run. LazyNews.1

Page 145: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

DetailNewsActivity.java

To go into a detailed news display we need DetailNewsActivity.java and detail_news_layout.xml

Transition is created in onItemClickListener in NewsActvity.

DetailNewsActivity must be registered in Manifest.

Page 146: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

detail_news_layout.xmlScrollView

(top container)

RelativeView

ImageView

TextView

TextViewTextView

Page 147: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Lazy News

Page 148: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ViewPager

Page 149: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ViewPager

ViewPager is a layout manager that allows the user to flip left and right through pages of data.

Developer needs to supply an implementation of a PagerAdapter to generate the pages that the view shows.

Create new project ImageGallery.

Page 150: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

activity_main.xmlInside RelativeLayout we have ViewPager with PagerTabStrip (indicator) underneath.

<android.support.v4.view.ViewPager android:layout_width="match_parent" android:layout_height="match_parent" android:id="@+id/ViewPager">

<android.support.v4.view.PagerTabStrip android:id="@+id/pager_tab" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_gravity="bottom" android:background="#33b5e5" android:textColor="#fff"/> </android.support.v4.view.ViewPager>

Page 151: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

page.xml

Page itself is described in page.xml - a single ImageView inside LinearLayout:

<ImageView android:id="@+id/img_view" android:layout_width="match_parent" android:layout_height="match_parent"/>

Page 152: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CustomPagerAdapterCustomPagerAdapter extends PagerAdapter. We must override the following methods at minimum:

1. instantiateItem(ViewGroup, int)Create the page for the given position. In our example it sets ImageView’s resource to the image at specified position and adds newly created view to our ViewPager (container)

Page 153: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CustomPagerAdapter

2. destroyItem(ViewGroup, int, Object)Remove a page for the given position.

3. getCount()Return the number of views available.

Page 154: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CustomPagerAdapter

4. isViewFromObject(View, Object)Determines whether a page View is associated with a specific key object as returned by instantiateItem(ViewGroup, int).This method is required for a PagerAdapter to function properly.

Page 155: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

CustomPagerAdapter

In order to define titles for tabs we need method:

CharSequence getPageTitle(int)Which returns a character sequence for the tab at specified position.

Page 156: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivityIn MainActivity, we simply instantiate ViewPager and assign PagerAdapter:

ViewPager viewPager = findViewById(R.id.ViewPager); CustomPagerAdapter adapter = new CustomPagerAdapter(this); viewPager.setAdapter(adapter);

Required images in drawable-xxhdpi: slide0.png, …, slide5.png

Page 157: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

ImageGallery

Page 158: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

TimetableAnother application of ViewPager

Instead of ImageView we’ll have ListView for each day (Mon - Fri)

Page 159: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

activity_main.xmlInside RelativeLayout we have ViewPager with PagerTabStrip (indicator) on top.

<android.support.v4.view.ViewPager android:layout_width="match_parent" android:layout_height="match_parent" android:id="@+id/ViewPager">

<android.support.v4.view.PagerTabStrip android:id="@+id/pager_tab" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_gravity=“top" android:background="#3f51b5" android:textColor="#fff"/> </android.support.v4.view.ViewPager>

Page 160: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

page.xmlPage itself is described in page.xml - a ListView inside LinearLayout:

<ListView android:layout_width="wrap_content" android:layout_height="wrap_content" android:id="@+id/timetable" android:layout_gravity="center" android:layout_marginLeft="8dp" android:layout_marginRight="8dp" android:clickable="true" android:divider="@null" android:dividerHeight=“0dp"/>

Page 161: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

rowlist.xmlIn order to describe cells in ListView we need rowlist.xml - two TextViews describing time and course:

<TextView android:id="@+id/time" android:layout_width="56dp" android:layout_height="wrap_content" android:text="noon" android:gravity="right" android:textColor=“#aaa" android:padding="8dp" android:textSize="16sp"/>

Page 162: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

rowlist.xml

<TextView android:id="@+id/description" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_toRightOf="@id/time" android:padding="8dp" android:text="CP2530 Lecture ET328" android:textColor="#1870a2" android:textSize="18sp" android:layout_marginTop="0dp"/>

Page 163: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Adapters

We need two adapters:

1. TimeTableAdapter which extends SimpleAdapter and, as before, inflates Map<time,description> into rowlist.Required by the second adapter.

Page 164: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

2. CustomPagerAdapter which extends PagerAdapter and creates ListView with data based on the position.

Adapters

Page 165: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

MainActivity

In MainActivity, five HashMaps are created and populated to serve as data for five ListViews.

As before, ViewPager and CustomPagerAdapter are instantiated and associated.

Page 166: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Timetable

Page 167: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML and Timetable

Rather than populating ListViews for each day using hard-coded data, we’ll fetch XML file, parse it and provide model for our ViewPager.

Project: TimeTable.2.zip

The structure of XML file modelling timetable of classes is as follows:

Page 168: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML and Timetable<timetable> <program>CS</program> <semester>5</semester> <gid>M6</gid> <mon> <time>9</time> <cid></cid> <time>10</time> <cid></cid> <time>11</time> <cid></cid> <time>12</time> <cid>CP2530 Lecture ET328</cid> <time>13</time> <cid>CT2530 Lecture ET328</cid> ... </mon> ... <fri> ... </fri> </timetable>

Page 169: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML and Timetable

The only change is in MainActivity - in onCreate method we check if we have network.

If so, fetch and parse file through GetXML object. Otherwise, alert user that there is no network connection.

Page 170: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML and Timetable

File is asynchronously downloaded in doInBackground() method and stored in String class variable src.

Parsing is done in onPostExecute() method, if the XML source is not null (i.e., schedule exists).

Page 171: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

XML and Timetable

Parsing populates ArrayList schedule, from which individual schedules (per day) are reconstructed and stored in days[][] array.

This array (days) is now used to create HashMaps for ListView adapters.

Page 172: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

SpinnerFor some reason Google calls it Spinner, although nothing spins, unlike iOS’ UIPickerView (spinning wheel).

Anyway, Spinner provides a quick way to select one value from a set. It’s typically defined in XML:

<Spinner android:id="@+id/spinner_p" android:layout_width="match_parent" android:layout_height="wrap_content"/>

Page 173: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Spinner

Page 174: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Spinner

Page 175: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Spinner

Required files are:

1. listview_border.xml (spinners’ background in drawable-xxhdpi)

2. spinnerrow.xml which defines a layout for each entry in the Spinner

Page 176: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

SpinnerWe need two spinners in main_activity.xml: one for programs and one for years.

There is also a button, which generates proper url for xml timetables when clicked.

Spinners are instantiated in MainActivity:

Spinner spinner_p = (Spinner) findViewById(R.id.spinner_p);

Page 177: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

SpinnerIn order to populate spinner we need data - two arrays of strings - programs and years.

Adapters are created and set:

ArrayAdapter<String> arrayAdapter = new ArrayAdapter<String>( MainActivity.this, R.layout.spinnerrow, R.id.spinner_id, programs); spinner_p.setAdapter(arrayAdapter);

Page 178: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

SpinnerWe set onItemSelectedListener for both spinners.

Program spinner listener sets the value of variable cid.

Year spinner listener sets the value of variable semester based on the selected year and current month.

Page 179: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Spinner

Button, when clicked, generates url where appropriate timetable is hosted (not all timetables are implemented).

There is an issue, not related to Spinner but to Button - its transparency when clicked.

Page 180: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Spinner

For some reason, change of transparency in Button / ImageButton when touched is not default behaviour.

That can be overridden in onTouchListener by changing the button’s alpha value.

Page 181: INTENTS - appspot.combranko-cirovic.appspot.com/CP3490/ListViews.pdf · INTENTS activity_main.xml is quite simple - linear vertical layout containing one button and text, horizontally

Spinnerb.setOnTouchListener(new View.OnTouchListener() { @Override public boolean onTouch(View v, MotionEvent event) { if(v == b) { if(event.getAction() == MotionEvent.ACTION_DOWN) { v.setAlpha(.3f); } else { v.setAlpha(1f); } } return false; } });