Set TextView text with a for loop so multiple lines show - java
So I have a for loop that I want to output a new line in a textview every single time it goes through. However, I am not sure if that is possible. I have TableLayout in there but it put the items vertically instead of horizontally. I thought about ListView but not sure how to set the text of it.
Here is my code
import android.app.Fragment;
import android.graphics.Color;
import android.os.Bundle;
import android.support.annotation.Nullable;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TableLayout;
import android.widget.TableRow;
import android.widget.TextView;
import com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route;
import org.joda.time.DateTime;
import org.w3c.dom.Text;
import java.io.IOException;
import java.util.Map;
import okhttp3.Request;
import okhttp3.Response;
/**
* Created by James Singleton on 8/13/2016.
*/
public class WeeklyDrives extends Fragment implements APIRequestsUtil.APIRequestResponseListener
{
View myView;
Map<String, Route> drives;
private TextView driveNumber;
private TextView driveDistance;
private TextView driveTime;
private TextView driveNumList;
private TextView driveDistList;
private TextView driveTimeList;
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
myView = inflater.inflate(R.layout.weekly_drives, container, false);
APIRequestsUtil.setOnNetWorkListener(this);
return myView;
}
private void populateView() {
this.getActivity().runOnUiThread(new Runnable() {
#Override
public void run() {
drives = APIRequestsUtil.getRoutes();
driveNumber = (TextView) myView.findViewById(R.id.Drive_Number);
driveDistance = (TextView) myView.findViewById(R.id.Drive_Distance);
driveTime = (TextView) myView.findViewById(R.id.Drive_Time);
driveNumber.setText("Drive Num.");
driveDistance.setText("Distance");
driveTime.setText("Time");
int driveNum = 0;
for (Map.Entry drive : drives.entrySet()) {
TableRow tr = new TableRow(getActivity());
Route route = (Route) drive.getValue();
tr.setId(driveNum++);
//tr.setLayoutParams(new ViewGroup.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT));
DateTime startTime = new DateTime(route.getStart_time());
DateTime endTime = new DateTime(route.getEnd_time());
driveNumList = (TextView) myView.findViewById(R.id.Drive_Number_List);
driveDistList = (TextView) myView.findViewById(R.id.Drive_Distance_List);
driveTimeList = (TextView) myView.findViewById(R.id.Drive_Time_List);
driveNumList.setText(driveNumList.getText().toString() + String.valueOf(driveNum) + System.getProperty("line.separator"));
driveDistList.setText(driveDistList.getText().toString() + Float.parseFloat(route.getLen()) / 1000 + " km" + System.getProperty("line.separator"));
driveTimeList.setText(driveTimeList.getText().toString() + ((endTime.getMillis() - startTime.getMillis())/ 1000)/60 + " min" + System.getProperty("line.separator"));
}
}
});
}
#Override
public void onFailure(Request request, Throwable throwable) {
}
#Override
public void onResponse(Response response) {
populateView();
}
}
Here is my XML:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<!--Header aligned to top -->
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="#+id/header"
android:gravity="center"
android:background="#FC9">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/Drive_Number"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#000"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/Drive_Distance"
android:layout_toRightOf="#+id/Drive_Number"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#000"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/Drive_Time"
android:layout_toRightOf="#+id/Drive_Distance"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#000"/>
</RelativeLayout>
<ScrollView
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:scrollbars="vertical"
android:background="#005"
android:layout_below="#+id/header"
android:id="#+id/scrollableContents">
<!--<TableLayout-->
<!--android:id="#+id/fragment1_tlayout"-->
<!--android:layout_width="wrap_content"-->
<!--android:layout_height="wrap_content"-->
<!--android:stretchColumns="0,1">-->
<!--</TableLayout>-->
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center"
android:orientation="horizontal">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/Drive_Number_List"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#CCCCCC" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/Drive_Distance_List"
android:layout_toRightOf="#+id/Drive_Number_List"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#CCCCCC"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/Drive_Time_List"
android:layout_toRightOf="#+id/Drive_Distance_List"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#CCCCCC"/>
</LinearLayout>
</ScrollView>
</RelativeLayout>
drive.entrySet() output
What is this:[2016-07-11--08-52-18=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#12a862, 2016-07-11--09-37-46=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#50bbdf3, 2016-07-11--18-54-22=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#6d21ab0, 2016-07-12--09-15-59=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#fb72d29, 2016-07-12--09-29-29=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#776e8ae, 2016-07-12--09-33-03=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#d1a464f, 2016-07-12--09-38-56=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#5b631dc, 2016-07-12--09-41-08=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#dec72e5, 2016-07-12--09-42-39=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#acce1ba, 2016-07-12--09-44-33=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#5def86b, 2016-07-12--09-49-31=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#d628fc8, 2016-07-12--09-54-06=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#7765861, 2016-07-12--19-04-34=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#8575f86, 2016-07-12--19-39-20=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#3f2b047, 2016-07-12--19-40-27=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#df4e074, 2016-07-12--19-41-28=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#b5f199d, 2016-07-13--08-45-17=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#db9ee12, 2016-07-13--09-01-32=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#2a009e3, 2016-07-13--15-02-04=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#9b98fe0, 2016-07-14--08-46-22=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#518b299, 2016-07-14--19-22-46=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#d44d95e, 2016-07-14--19-34-02=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#d3f613f, 2016-07-14--20-16-47=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#957ca0c, 2016-07-15--08-36-28=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#b38df55, 2016-07-15--09-52-32=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#c012d6a, 2016-07-15--12-09-57=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#252d25b, 2016-07-15--12-15-07=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#6bd7af8, 2016-07-15--15-36-10=com.example.jamessingleton.chffrapi.com.examples.jamessingleton.chffrapi.data.Route#df51bd1,
Add android:inputType="textMultiLine" to the TextView in the XML.
And add data into TextView like this:
driveNumList.setText(driveNumList.getText().toString() + String.valueOf(driveNum) + System.getProperty("line.separator"));
And so on.
Edit: you can use "\n" instead of System.getProperty("line.separator") for adding the new line character.
I would recommend a ListView for this type of thing so that it is automatically scrollable, uses View recycling to maintain efficiency, cleans up your code and organizes it into digestible segments.
To use a ListView, you first need to add it to your main XML file. So that would become the following:
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical" android:layout_width="match_parent"
android:layout_height="match_parent">
<!--Header aligned to top -->
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:id="#+id/header"
android:gravity="center"
android:background="#FC9">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/Drive_Number"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#000"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/Drive_Distance"
android:layout_toRightOf="#+id/Drive_Number"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#000"/>
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:id="#+id/Drive_Time"
android:layout_toRightOf="#+id/Drive_Distance"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#000"/>
</RelativeLayout>
<RelativeLayout
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:scrollbars="vertical"
android:background="#005"
android:layout_below="#+id/header"
android:id="#+id/scrollableContents">
<ListView
android:id="#+id/listView"
android:layout_width="fill_parent"
android:layout_height="fill_parent" />
</RelativeLayout>
</RelativeLayout>
Following that, you need to create your ListView adapter class. It is what handles what each individual list item's data is (the thing inside your for-loop).
Here is one that you might use, although you may have to make your own tweaks and import more of your own classes, add your package name to the top, etc.
So create a new Java class called DriveListAdapter.java and place the following code into it:
import android.app.Activity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.TextView;
import java.util.List;
import java.util.HashMap;
import java.util.Map;
public class DriveListAdapter extends ArrayAdapter<Map.Entry> {
private final Activity context;
// you may need to change List to something else (whatever is returned from drives.entrySet())
private final List<Map.Entry> drives;
// may also need to change List here (above comment)
public DriveListAdapter(Activity context, List<Map.Entry> drives) {
super(context, R.layout.drive_list_item, drives);
this.context = context;
this.drives = drives;
}
#Override
public View getView(int position, View view, ViewGroup parent) {
LayoutInflater inflater = context.getLayoutInflater();
View rowView = inflater.inflate(R.layout.drive_list_item, null, true);
Map.Entry drive = this.drives.get(position);
// position is the index of the drives.entrySet() array
int driveNum = position + 1;
// need to import your Route class
Route route = (Route) drive.getValue();
// need to import your DateTime class
DateTime startTime = new DateTime(route.getStart_time());
DateTime endTime = new DateTime(route.getEnd_time());
TextView driveNumList = (TextView) rowView.findViewById(R.id.Drive_Number_List);
TextView driveDistList = (TextView) rowView.findViewById(R.id.Drive_Distance_List);
TextView driveTimeList = (TextView) rowView.findViewById(R.id.Drive_Time_List);
driveNumList.setText(String.valueOf(driveNum));
driveDistList.setText(Double.parseDouble(route.getLen()) / 1000 + " km");
driveTimeList.setText((endTime.getMillis() - startTime.getMillis())/ 1000 + " s");
return rowView;
}
}
Then, create a new layout file, which will be what the individual list item looks like. This layout is rendered for each and every drive in the list. You can adjust this layout file so that everything is aligned properly. I gave an example of how to do that (create a layout file called drive_list_item.xml):
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent" android:layout_height="match_parent">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#CCCCCC"
android:text="Medium Text"
android:id="#+id/Drive_Number_List"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#CCCCCC"
android:text="Medium Text"
android:id="#+id/Drive_Distance_List"
android:layout_alignParentTop="true"
android:layout_alignParentLeft="true"
android:layout_alignParentStart="true" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="4dp"
android:textSize="20sp"
android:textColor="#CCCCCC"
android:text="Medium Text"
android:id="#+id/Drive_Time_List"
android:layout_alignParentTop="true"
android:layout_alignParentRight="true"
android:layout_alignParentEnd="true" />
</RelativeLayout>
And lastly, you just need to populate that ListView you created in the first step with this new adapter class.
So use the following method (populates the ListView instead of using the for loop):
private void populateView() {
this.getActivity().runOnUiThread(new Runnable() {
#Override
public void run() {
drives = APIRequestsUtil.getRoutes();
driveNumber = (TextView) myView.findViewById(R.id.Drive_Number);
driveDistance = (TextView) myView.findViewById(R.id.Drive_Distance);
driveTime = (TextView) myView.findViewById(R.id.Drive_Time);
driveNumber.setText("Drive Number");
driveDistance.setText("Drive Distance");
driveTime.setText("Drive Time");
// edit: you need to generate your List data from the entrySet
// the ArrayAdapter cannot take a Set argument - needs to be a List
List<Map.Entry> list = new ArrayList<Map.Entry>();
for (Map.Entry drive : drives.entrySet()) {
list.add(drive);
}
// populate the ListView
// may need to change "getActivity()" to something else
// this constructor needs the "this" context of the activity
DriveListAdapter drivesListAdapter = new DriveListAdapter(getActivity(), list);
ListView listView = (ListView)findViewById(R.id.listView);
listView.setAdapter(drivesListAdapter);
}
});
}
first of all you use LinearLayout instead of TableLayoyt
<LinearLayout
android:id="#+id/llMainLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center"
android:orientation="vertical">
try this code
LinearLayout llMain=(LinearLayout) myView.findViewById(R.id.llMainLayout);
for (Map.Entry drive : drives.entrySet()) {
LinearLayout tr = new LinearLayout(getActivity());
tr.setOrientation(1); // horizontal
Route route = (Route) drive.getValue();
tr.setId(driveNum++);
// set params
DateTime startTime = new DateTime(route.getStart_time());
DateTime endTime = new DateTime(route.getEnd_time());
TextView driveNumList = new TextView();
TextView driveDistList = new TextView();
TextView driveTimeList = new TextView();
driveNumList.setText(String.valueOf(driveNum));
driveDistList.setText(Double.parseDouble(route.getLen()) / 1000 + " km");
driveTimeList.setText((endTime.getMillis() - startTime.getMillis())/ 1000 + " s");
tr.addView(driveNumList);
tr.addView(driveDistList);
tr.addView(driveTimeList);
llMain.addView(tr);
}
}
Related
Unexpected behaviour with custom ListView adapter
So I've got a listView and each item basically displays 3 TextView-s one of the TextView-s represents username and if the username is equal to the logged user the item shall be highlighted(see code) import android.content.Context; import android.graphics.Color; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.ArrayAdapter; import android.widget.TextView; import java.util.List; public class ListAdapter extends ArrayAdapter<HallOfFame.User> { private int resourceLayout; private Context mContext; public ListAdapter(Context context, int resource, List<HallOfFame.User> items) { super(context, resource, items); this.resourceLayout = resource; this.mContext = context; } #Override public View getView(int position, View convertView, ViewGroup parent) { View v = convertView; if (v == null) { LayoutInflater vi; vi = LayoutInflater.from(mContext); v = vi.inflate(resourceLayout, null); } HallOfFame.User user = getItem(position); if (user != null) { TextView rankText = v.findViewById(R.id.rank); TextView usernameText = v.findViewById(R.id.username); TextView scoreText = v.findViewById(R.id.score); rankText.setText(Integer.toString(user.rank)); usernameText.setText(user.username); scoreText.setText(Integer.toString(user.overall)); if(Utils.USERNAME.equals(user.username)){ usernameText.setTextColor(Color.RED); } } return v; } } In this example only MikiThenics should be highlighted. Adding else after if(Utils.USERNAME.eq...) will stop the other usernames from being highlighted but there's still this weird shift with the number on the right. And the items that are "not working" aren't always the same. This is how the HallOfFame.User looks: public class User{ public String username; public int pullups=0,pushups,dips,handstandpushups,plank,pistolsquats,muscleups; public int overall; public int rank = 0; public User(String data,int i){ try { JSONObject jsonObject = new JSONObject(data); username = jsonObject.getString(Utils.S_USERNAME); pullups = jsonObject.getInt(Utils.S_PULL_UPS); pushups = jsonObject.getInt(Utils.S_PUSH_UPS); dips = jsonObject.getInt(Utils.S_DIPS); handstandpushups = jsonObject.getInt(Utils.S_HANDSTAND_PUSHUPS); plank = jsonObject.getInt(Utils.S_PLANK); pistolsquats = jsonObject.getInt(Utils.S_PISTOL_SQUATS); muscleups = jsonObject.getInt(Utils.S_MUSCLE_UPS); overall = pullups+pushups+dips+handstandpushups+pistolsquats+muscleups+plank/60; rank = i; if(username.equals(Utils.USERNAME)) yourPosition = i; }catch (Exception e){ } } } This is the example of the JSON I'm using String tmp = "[{\"username\":\"MikiThenics\",\"pullups\":\"25\",\"pushups\":\"70\",\"dips\":\"30\",\"handstandpushups\":\"16\",\"muscleups\":\"8\",\"pistolsquats\":\"1\",\"plank\":\"360\"},{\"username\":\"user01\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user02\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user0\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user1\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user2\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user3\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user4\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user5\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user6\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user7\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user8\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user9\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user10\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user11\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user12\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user13\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user14\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user15\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user16\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user17\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user18\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user19\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user20\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user21\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user22\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user23\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user24\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user25\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user26\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user27\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user28\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user29\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user30\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user31\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user32\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user33\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user34\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user35\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user36\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user37\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user38\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user39\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user40\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user41\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user42\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user43\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user44\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user45\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user46\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user47\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user48\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user49\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user50\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user51\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user52\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user53\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user54\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user55\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user56\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user57\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user58\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user59\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user60\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user61\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user62\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user63\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user64\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user65\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user66\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user67\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user68\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user69\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user70\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user71\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user72\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user73\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user74\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user75\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user76\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"},{\"username\":\"user77\",\"pullups\":\"0\",\"pushups\":\"0\",\"dips\":\"0\",\"handstandpushups\":\"0\",\"muscleups\":\"0\",\"pistolsquats\":\"0\",\"plank\":\"0\"}]"; The problem is caused by the username. Since setting username in User to fixed String solves the problem. Even though I'm using fixed string as JSON the "not working items" aren't the same when restarting the activity.
It's a XML issue. You can try with this. <?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" android:layout_height="wrap_content" android:orientation="vertical" android:layout_width="match_parent"> <RelativeLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:gravity="center" app:layout_constraintStart_toStartOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintTop_toTopOf="parent" android:paddingTop="10dp" android:paddingBottom="10dp" > <TextView android:id="#+id/rank" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginStart="8dp" android:text="RANK" android:textColor="#000000" android:textColorHighlight="#000000" android:textColorHint="#000000" android:textColorLink="#000000" android:textSize="16sp" android:layout_alignParentStart="true" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toTopOf="parent" /> <TextView android:id="#+id/username" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginStart="12dp" android:text="Name" android:textColor="#000000" android:textColorHighlight="#000000" android:textColorHint="#000000" android:textColorLink="#000000" android:textSize="16sp" android:layout_toEndOf="#+id/rank" /> <TextView android:id="#+id/score" android:layout_width="50dp" android:layout_height="wrap_content" android:layout_marginEnd="8dp" android:text="SCORE" android:textColor="#000000" android:textColorHighlight="#000000" android:textColorHint="#000000" android:textColorLink="#000000" android:textSize="16sp" android:layout_alignParentEnd="true" /> </RelativeLayout> </androidx.constraintlayout.widget.ConstraintLayout>
You can add an boolean into your if statement that at first it is true and when tries to highlited the username's text , set the boolean false if(Utils.USERNAME.equals(user.username) && boolean){ usernameText.setTextColor(Color.RED); }
Problems in Android FirebaseRecyclerView Implementing A Search Users Function
I'm looking to implement a search function. When it runs, logcat is telling me: E/RecyclerView: No adapter attached; skipping layout. I have searched SO and the net and the answers tell me that I need to set the adapter and the linear layout manager. As you will see with my code, I set both. Alex Mamo's (#AlexMamo) work on here seems to point me in the right direction but I'm still getting the error. My Activity import androidx.annotation.NonNull; import androidx.appcompat.app.AppCompatActivity; import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.RecyclerView; import android.os.Bundle; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.EditText; import android.widget.ImageButton; import android.widget.TextView; import android.widget.Toast; import com.MyApp.Objects.ParticipantsObject; import com.MyApp.R; import com.firebase.ui.database.FirebaseRecyclerAdapter; import com.firebase.ui.database.FirebaseRecyclerOptions; import com.google.firebase.database.DatabaseReference; import com.google.firebase.database.FirebaseDatabase; import com.google.firebase.database.Query; public class ParticipantsActivity extends AppCompatActivity { private EditText mSearchField; private ImageButton mSearchBtn; private RecyclerView mResultList; private DatabaseReference mUserDatabase; #Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_neighbors); mUserDatabase = FirebaseDatabase.getInstance().getReference().child("Users").child("Participants"); mSearchField = (EditText) findViewById(R.id.search_field); mSearchBtn = (ImageButton) findViewById(R.id.search_btn); mResultList = (RecyclerView) findViewById(R.id.result_list); mResultList.setHasFixedSize(true); mResultList.setLayoutManager(new LinearLayoutManager(this)); mSearchBtn.setOnClickListener(view -> { String searchText = mSearchField.getText().toString(); firebaseUserSearch(searchText); }); } private void firebaseUserSearch(String searchText) { Toast.makeText(ParticipantsActivity.this, "Started Search", Toast.LENGTH_LONG).show(); Query firebaseSearchQuery = mUserDatabase.orderByChild("name").startAt(searchText); FirebaseRecyclerOptions<ParticipantsObject> firebaseRecyclerOptions = new FirebaseRecyclerOptions.Builder<ParticipantsObject>() .setQuery(firebaseSearchQuery, ParticipantsObject.class) .build(); class UserHolder extends RecyclerView.ViewHolder { private TextView imageThumbTextView, nameTextView UserHolder(View itemView) { super(itemView); imageThumbTextView = itemView.findViewById(R.id.profile_image); nameTextView = itemView.findViewById(R.id.name_text); } void setUsers(ParticipantsObject participantsObject) { String imageThumb = driverObject.getThumb_image(); imageThumbTextView.setText(imageThumb); String name = participantsObject.getName(); nameTextView.setText(name); } } FirebaseRecyclerAdapter<ParticipantsObject, UserHolder> firebaseRecyclerAdapter; firebaseRecyclerAdapter = new FirebaseRecyclerAdapter<ParticipantsObject, UserHolder>(firebaseRecyclerOptions) { #Override protected void onBindViewHolder(#NonNull UserHolder userHolder, int position, #NonNull ParticipantsObject participantsObject) { userHolder.setUsers(participantsObject); } #Override public UserHolder onCreateViewHolder(ViewGroup parent, int viewType) { View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_layout, parent, false); return new UserHolder(view); } }; mResultList.setAdapter(firebaseRecyclerAdapter); firebaseRecyclerAdapter.startListening(); } } My Activity XML file <?xml version="1.0" encoding="utf-8"?> <RelativeLayout 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" android:background="#ffffff" tools:context="com.MyApp.ParticipantsActivity"> <TextView android:id="#+id/heading_label" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentStart="true" android:layout_alignParentTop="true" android:layout_marginLeft="30dp" android:layout_marginTop="30dp" android:text="Firebase Search" android:textColor="#555555" android:textSize="24sp" /> <EditText android:id="#+id/search_field" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignStart="#+id/heading_label" android:layout_below="#+id/heading_label" android:layout_marginRight="20dp" android:layout_marginTop="20dp" android:layout_toStartOf="#+id/search_btn" android:background="#drawable/search_layout" android:ems="10" android:hint="Search here" android:inputType="textPersonName" android:paddingBottom="10dp" android:paddingLeft="20dp" android:paddingRight="20dp" android:paddingTop="10dp" android:textColor="#999999" android:textSize="16sp" /> <ImageButton android:id="#+id/search_btn" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignBottom="#+id/search_field" android:layout_alignParentEnd="true" android:layout_alignTop="#+id/search_field" android:layout_marginRight="30dp" android:background="#android:color/background_light" app:srcCompat="#mipmap/search_button" /> <androidx.recyclerview.widget.RecyclerView android:id="#+id/result_list" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_below="#+id/search_field" android:layout_marginTop="50dp"> </androidx.recyclerview.widget.RecyclerView> </RelativeLayout> My list layout <?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" android:layout_width="match_parent" android:layout_height="wrap_content"> <ImageView android:id="#+id/profile_image" android:layout_width="80dp" android:layout_height="80dp" android:layout_alignParentStart="true" android:layout_alignParentTop="true" android:layout_marginLeft="30dp" android:layout_marginTop="20dp" app:srcCompat="#mipmap/ic_default_user" /> <TextView android:id="#+id/name_text" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentTop="true" android:layout_alignParentEnd="true" android:layout_marginStart="14dp" android:layout_marginLeft="20dp" android:layout_marginTop="50dp" android:layout_marginEnd="213dp" android:layout_marginRight="20dp" android:layout_toEndOf="#+id/profile_image" android:text="Username" android:textColor="#555555" android:textSize="16sp" /> </RelativeLayout> Any ideas or advice would be much appreciated.
Your code is setting the adapter only after a button is pushed. Because you didn't set it before the first time the RecyclerView needed to render itself on screen, it's going to warn you about that with the message you see in the log. The RecyclerView must have an adapter attached at the time of rendering in order for it to display anything.
Android app crashing when I start an activity using ListView and a custom ArrayAdapter [duplicate]
This question already has answers here: Null pointer Exception - findViewById() (12 answers) findViewById returns null (4 answers) What is a NullPointerException, and how do I fix it? (12 answers) Closed 3 years ago. I've created a Location class and when I click on Cinemas in MainActivity, I want to open another activity that contains the list of Location objects. For this goal I have created a custom location_list_item layout file and a custom ArrayAdapter. For some reason, when I click on Cinemas, my app crashes. Why? MainActivity.java package com.example.android.tourguide; import androidx.appcompat.app.AppCompatActivity; import android.content.Intent; import android.os.Bundle; import android.view.View; public class MainActivity extends AppCompatActivity { #Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); View cinemasView = findViewById(R.id.cinemas_layout); cinemasView.setOnClickListener(new View.OnClickListener() { #Override public void onClick(View v) { Intent intent = new Intent(MainActivity.this, CinemasActivity.class); startActivity(intent); } }); } } activity_main.xml <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" android:background="#fff8e1" tools:context=".MainActivity"> <TextView android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="#string/main_activity_title" android:textSize="30sp" android:textStyle="bold" android:textColor="#android:color/black" android:layout_gravity="center_horizontal" android:layout_marginBottom="16dp"/> <LinearLayout android:id="#+id/cinemas_layout" android:layout_width="match_parent" android:layout_height="120dp" android:background="#4a148c"> <ImageView android:layout_width="90dp" android:layout_height="90dp" android:src="#drawable/category_cinemas" android:layout_gravity="center_vertical" android:layout_marginLeft="16dp"/> <TextView android:layout_width="match_parent" android:layout_height="match_parent" android:gravity="center" android:text="#string/category_cinemas" android:textSize="25sp" android:textColor="#android:color/white"/> </LinearLayout> <View android:layout_width="fill_parent" android:layout_height="1dp" android:background="#android:color/darker_gray" /> <LinearLayout android:id="#+id/restaurants_layout" android:layout_width="match_parent" android:layout_height="120dp" android:background="#4a148c"> <ImageView android:layout_width="90dp" android:layout_height="90dp" android:src="#drawable/category_restaurants" android:layout_gravity="center_vertical" android:layout_marginLeft="16dp"/> <TextView android:layout_width="match_parent" android:layout_height="match_parent" android:gravity="center" android:text="#string/category_restaurants" android:textSize="25sp" android:textColor="#android:color/white"/> </LinearLayout> <View android:layout_width="fill_parent" android:layout_height="1dp" android:background="#android:color/darker_gray" /> <LinearLayout android:id="#+id/gyms_layout" android:layout_width="match_parent" android:layout_height="120dp" android:background="#4a148c"> <ImageView android:layout_width="90dp" android:layout_height="90dp" android:src="#drawable/category_gyms" android:layout_gravity="center_vertical" android:layout_marginLeft="16dp"/> <TextView android:layout_width="match_parent" android:layout_height="match_parent" android:gravity="center" android:text="#string/category_gyms" android:textSize="25sp" android:textColor="#android:color/white"/> </LinearLayout> <View android:layout_width="fill_parent" android:layout_height="1dp" android:background="#android:color/darker_gray" /> <LinearLayout android:id="#+id/parks_layout" android:layout_width="match_parent" android:layout_height="100dp" android:background="#4a148c"> <ImageView android:layout_width="90dp" android:layout_height="90dp" android:src="#drawable/category_parks" android:layout_gravity="center_vertical" android:layout_marginLeft="16dp"/> <TextView android:layout_width="match_parent" android:layout_height="match_parent" android:gravity="center" android:text="#string/category_parks" android:textSize="25sp" android:textColor="#android:color/white"/> </LinearLayout> </LinearLayout> location_category_list_item.xml <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical" > <ImageView android:id="#+id/location_image" android:layout_width="wrap_content" android:layout_height="wrap_content" /> <TextView android:id="#+id/location_hours_title" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginLeft="16dp" android:text="Hours" android:textStyle="bold"/> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="horizontal"> <TextView android:id="#+id/location_working_days" android:layout_width="0dp" android:layout_weight="1" android:layout_height="wrap_content" android:layout_marginLeft="16dp" tools:text="Every Day" /> <TextView android:id="#+id/location_working_hours" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginRight="16dp" tools:text="09:00 – 00:00" /> </LinearLayout> <TextView android:id="#+id/location_address_title" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginLeft="16dp" android:text="Address" android:textStyle="bold"/> <TextView android:id="#+id/location_address" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginLeft="16dp" tools:text="09:00 – 00:00" /> <TextView android:id="#+id/location_phone_title" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_marginLeft="16dp" android:text="Phone" android:textStyle="bold"/> <TextView android:id="#+id/location_phone" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_marginLeft="16dp" tools:text="+7 (555) 555-55-55" /> </LinearLayout> Location.java package com.example.android.tourguide; import androidx.annotation.NonNull; public class Location { private int mImageResourceId; private String mAddress; private String mPhone; private String mWorkingDays; private String mWorkingHours; public Location(int imageResourceId, String address, String phone, String workingDays, String workingHours) { mImageResourceId = imageResourceId; mAddress = address; mPhone = phone; mWorkingDays = workingDays; mWorkingHours = workingHours; } public int getImageResourceId() { return mImageResourceId; } public String getAddress() { return mAddress; } public String getPhone() { return mPhone; } public String getWorkingDays() { return mWorkingDays; } public String getWorkingHours() { return mWorkingHours; } #NonNull #Override public String toString() { return mImageResourceId + mAddress + mWorkingDays + mWorkingDays + mPhone; } } LocationAdapter.java package com.example.android.tourguide; import android.app.Activity; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.ArrayAdapter; import android.widget.ImageView; import android.widget.TextView; import java.util.ArrayList; public class LocationAdapter extends ArrayAdapter<Location> { /** * This is our own custom constructor (it doesn't mirror a superclass constructor). * The context is used to inflate the layout file, and the list is the data we want * to populate into the lists. * * #param context The current context. Used to inflate the layout file. * #param locations A List of Location objects to display in a list */ public LocationAdapter(Activity context, ArrayList<Location> locations) { // Here, we initialize the ArrayAdapter's internal storage for the context and the list. // the second argument is used when the ArrayAdapter is populating a single TextView. // Because this is a custom adapter for one ImageView and 4 TextViews, the adapter is not // going to use this second argument, so it can be any value. Here, we used 0. super(context, 0, locations); } /** * Provides a view for an AdapterView (ListView, GridView, etc.) * * #param position The position in the list of data that should be displayed in the * list item view. * #param convertView The recycled view to populate. * #param parent The parent ViewGroup that is used for inflation. * #return The View for the position in the AdapterView. */ #Override public View getView(int position, View convertView, ViewGroup parent) { // Check if the existing view is being reused, otherwise inflate the view View listItemView = convertView; if (listItemView == null) { listItemView = LayoutInflater.from(getContext()).inflate( R.layout.location_category_list_item, parent, false); } // Get the {#link Location} object located at this position in the list Location currentLocation = getItem(position); // Find the ImageView in the location_category_list_item.xml layout // with the ID location_image ImageView image = listItemView.findViewById(R.id.location_image); // Get the image resource ID from the current Location object and // set the image to imageView image.setImageResource(currentLocation.getImageResourceId()); // Find the TextView in the location_category_list_item.xml layout // with the ID location_working_days TextView workingDaysTextView = listItemView.findViewById(R.id.location_working_days); // Get the working days from the current Location object and // set this text on the workingDaysTextView workingDaysTextView.setText(currentLocation.getWorkingDays()); // Find the TextView in the location_category_list_item.xml layout // with the ID location_working_hours TextView workingHoursTextView = listItemView.findViewById(R.id.location_working_hours); // Get the working hours from the current Location object and // set this text on the workingHoursTextView workingHoursTextView.setText(currentLocation.getWorkingHours()); // Find the TextView in the location_category_list_item.xml layout // with the ID location_address TextView addressTextView = listItemView.findViewById(R.id.location_address); // Get the address from the current Location object and // set this text on the addressTextView addressTextView.setText(currentLocation.getAddress()); // Find the TextView in the location_category_list_item.xml layout // with the ID location_phone TextView phoneTextView = listItemView.findViewById(R.id.location_phone); // Get the address from the current Location object and // set this text on the phoneTextView phoneTextView.setText(currentLocation.getPhone()); // Return the whole list item layout // so that it can be shown in the ListView return listItemView; } } CinemasActivity.java package com.example.android.tourguide; import androidx.appcompat.app.AppCompatActivity; import android.os.Bundle; import android.widget.ListView; import java.util.ArrayList; public class CinemasActivity extends AppCompatActivity { #Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.location_category_list_item); //Create a list of cinemas final ArrayList<Location> locations = new ArrayList<>(); locations.add(new Location(R.drawable.cinemas_byl, "Zhukova mikrorayon, 38", "+7 (929) 002-20-09", "Every Day", "09:00 – 00:00")); locations.add(new Location(R.drawable.cinemas_charly, "Ol'minskogo mikrorayon, 17", "+7 (472) 523-34-56", "Every Day", "09:30 – 02:00")); locations.add(new Location(R.drawable.cinemas_cinema_5, "Molodezhnyy Proyezd, 10", "+7 (472) 523-37-27", "Every Day", "09:00 – 00:00")); // Create an {#link LocationAdapter}, whose data source is a list of // {#link Locations}. The adapter knows how to create list item views // for each item in the list. LocationAdapter locationAdapter = new LocationAdapter(this, locations); // Get a reference to the ListView, and attach the adapter to the listView. ListView listView = (ListView) findViewById(R.id.list); listView.setAdapter(locationAdapter); } }
Probably you set wrong layout in your CinemasActivity. setContentView(R.layout.location_category_list_item); R.layout.location_category_list_item is item view for your ListView. There is no ListView in location_category_list_item which causes the crash
App crash - My android app
I programmed my app to be using listview and I create my addapter class to extend ArrayAddapter and also I create my getter class to get my words into the view I want to inflate but when I run the app it stops. my addapter class code package charpman.com.quakereport; import android.content.Context; import android.graphics.Typeface; import android.support.annotation.NonNull; import android.support.annotation.Nullable; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.ArrayAdapter; import android.widget.TextView; import java.util.ArrayList; /** * Created by DCharpMan on 4/19/2017. * <p> * class to populate each list view item */ public class QuakeAdapter extends ArrayAdapter<earthquakeClass> { /** * Constructor * * #param context The current context. * #param earthquakeClass the array to be populated */ public QuakeAdapter(#NonNull Context context, ArrayList<earthquakeClass> earthquakeClass) { super(context, R.layout.description_house, earthquakeClass); } #NonNull #Override public View getView(int position, #Nullable View convertView, #NonNull ViewGroup parent) { View Customize = convertView; if (Customize == null) { Customize = LayoutInflater.from(getContext()).inflate(R.layout.description_house, parent, false); } earthquakeClass earthquakeClass = getItem(position); TextView textView = (TextView) Customize.findViewById(R.id.text_magnitude); textView.setText(earthquakeClass.getMagnitude()); textView.setTypeface(Typeface.MONOSPACE, 2 + 1); TextView textView1 = (TextView) Customize.findViewById(R.id.text_loctaion); textView1.setText(earthquakeClass.getLocation()); textView1.setTypeface(Typeface.SERIF, 1); TextView textView2 = (TextView) Customize.findViewById(R.id.text_daye); textView2.setText(earthquakeClass.getDate()); textView2.setTypeface(Typeface.DEFAULT_BOLD, 3); return Customize; } } my mainActivity.java code package charpman.com.quakereport; import android.os.Bundle; import android.support.v7.app.AppCompatActivity; import android.widget.ListView; import java.util.ArrayList; public class MainActivity extends AppCompatActivity { #Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); final ArrayList<earthquakeClass> country = new ArrayList<earthquakeClass>(); country.add(new earthquakeClass("7.2", "nigeria", "23,07,2017")); country.add(new earthquakeClass("7.2", "nigeria", "23,07,2017")); country.add(new earthquakeClass("7.2", "nigeria", "23,07,2017")); country.add(new earthquakeClass("7.2", "nigeria", "23,07,2017")); country.add(new earthquakeClass("7.2", "nigeria", "23,07,2017")); ListView listView = (ListView) findViewById(R.id.list_view); QuakeAdapter quakeAdapter = new QuakeAdapter(this, country); listView.setAdapter(quakeAdapter); } } my getter class code package charpman.com.quakereport; /** * Created by CharpMan on 4/19/2017. * class to get the earthQuake details * details includes Magnitude,location and date of earthquake */ public class earthquakeClass { // globale variables that holds the earthquake information String magnitude; String location; String date; //contructor for the class takes in three params // #param Magnitude tell the magnitude of the quake // #params Location tells the location where the quake occured // #params date tells the day of the quake public earthquakeClass(String Magnitude, String Location, String Date){ magnitude = Magnitude; location = Location; date = Date; } // create public methods that returns each information // method to the the magnitude public String getMagnitude(){ return magnitude; } // methid to return the loctaion public String getLocation(){ return location; } // methid to return the day of quake occurence public String getDate (){ return date; } } My MainActivity.xml code <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" tools:context="charpman.com.quakereport.MainActivity"> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_margin="5dp" android:background="#android:color/darker_gray" android:orientation="horizontal"> <TextView android:layout_width="0dp" android:layout_height="wrap_content" android:layout_weight="1" android:paddingLeft="10dp" android:text="Magnitude" android:textAllCaps="true" /> <TextView android:layout_width="0dp" android:layout_height="wrap_content" android:layout_weight="1" android:gravity="center_horizontal" android:paddingLeft="10dp" android:text="Location" android:textAllCaps="true" /> <TextView android:layout_width="0dp" android:layout_height="wrap_content" android:layout_weight="1" android:gravity="center_horizontal" android:paddingLeft="20dp" android:text="date" android:textAllCaps="true" /> </LinearLayout> <ListView android:background="#android:color/secondary_text_light" android:id="#+id/list_view" android:layout_width="match_parent" android:layout_height="match_parent"> </ListView> </LinearLayout> xml code for the Layout I inflate in my Addapter class's GetView method <?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:orientation="vertical" android:padding="10dp"> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="horizontal"> <TextView android:id="#+id/text_magnitude" android:layout_width="0dp" android:layout_height="wrap_content" android:layout_weight="1" android:background="#android:color/white" android:paddingLeft="14dp" android:text="7.8" /> <TextView android:id="#+id/text_loctaion" android:layout_width="0dp" android:layout_height="wrap_content" android:layout_weight="1" android:background="#android:color/white" android:gravity="center" android:paddingLeft="5dp" android:text="Nigeria" android:typeface="serif" /> <TextView android:id="#+id/text_daye" android:layout_width="0dp" android:layout_height="wrap_content" android:layout_gravity="center_horizontal" android:layout_weight="1" android:background="#android:color/white" android:paddingLeft="25dp" android:text="28,02,2017" /> </LinearLayout> </LinearLayout> I include a screenshot of my logcat
I was trying to read through the Code and i notice that ion my ListView code I added a backgroud tag android:background="#android:color/secondary_text_light" I ought to have define/copy the color code in project colors.xml and use it. Thanks
As per the error log i think in your XML file there is something which is not compatible as per your adapter or maybe you are using an object in your adapter which is not present in your XML file.
How to add icon to tabs
I am trying to add an icon to my tabs and it isnt working, I tried adding getResources().getDrawable(R.drawable.bodyicon)); and it still isnt working. When I run the application the tab bar just has the text and there is no icon I outlined where my code is. If someone could figure out why it isnt working that would be great. import android.app.Activity; import android.app.AlertDialog; import android.content.Context; import android.content.Intent; import android.os.Bundle; import android.view.LayoutInflater; import android.view.MotionEvent; import android.view.View; import android.view.View.OnClickListener; import android.view.View.OnTouchListener; import android.view.Window; import android.view.WindowManager; import android.widget.AdapterView; import android.widget.AdapterView.OnItemSelectedListener; import android.widget.Button; import android.widget.ImageView; import android.widget.Spinner; import android.widget.TabHost; import android.widget.TabHost.TabSpec; public class Body extends Activity implements OnTouchListener, OnClickListener { Button bAbs, bQuad2, bPecs; TabHost th; ImageView body; final Context context = this; StretchType pop; // above I am defining all of the buttons and images, etc... #Override protected void onCreate(Bundle savedInstanceState) { // TODO Auto-generated method stub super.onCreate(savedInstanceState); requestWindowFeature(Window.FEATURE_NO_TITLE); getWindow().setFlags( WindowManager.LayoutParams.FLAG_FORCE_NOT_FULLSCREEN, WindowManager.LayoutParams.FLAG_FORCE_NOT_FULLSCREEN); // here I am saying get rid of the nav bar setContentView(R.layout.body); th = (TabHost) findViewById(R.id.thbodyview); bAbs = (Button) findViewById(R.id.bAbss); bPecs = (Button) findViewById(R.id.bPecss); bAbs.setOnClickListener(this); bPecs.setOnClickListener(this); //*********************below are my tabs******************************************* th.setup(); TabSpec specs = th.newTabSpec("Front"); specs.setContent(R.id.Front); specs.setIndicator("Front",getResources().getDrawable(R.drawable.bodyicon)); th.addTab(specs); specs = th.newTabSpec("tag2"); specs.setContent(R.id.Back); specs.setIndicator("Back"); th.addTab(specs); specs = th.newTabSpec("tag3"); specs.setContent(R.id.tab3); specs.setIndicator("More..."); th.addTab(specs); } //***************************Above are my tabs ******************************* #Override public void onClick(View v) { // TODO Auto-generated method stub switch (v.getId()) { case R.id.bAbss: // below I am creating the alert dialogue LayoutInflater li = LayoutInflater.from(context); View promptsView = li.inflate(R.layout.abs, null); // above I am setting the customview of the alert dialogue AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder( context); alertDialogBuilder.setView(promptsView); // here I am officially setting the custom layout // set dialog message alertDialogBuilder.setTitle("Stretch Type"); // alert dialogue title // create alert dialog final AlertDialog alertDialog = alertDialogBuilder.create(); // above is creating the alert dialogue final Spinner mSpinner = (Spinner) promptsView .findViewById(R.id.sSType); // above is initializing the spinner /* * dont need this button final Button mButton = (Button) promptsView * .findViewById(R.id.bSpinclose); */ // reference UI elements from my_dialog_layout in similar fashion mSpinner.setOnItemSelectedListener(new OnSpinnerItemClicked()); // show it alertDialog.show(); alertDialog.setCanceledOnTouchOutside(false); break; } } #Override public boolean onTouch(View arg0, MotionEvent arg1) { // TODO Auto-generated method stub return false; } public class OnSpinnerItemClicked implements OnItemSelectedListener { #Override public void onItemSelected(AdapterView<?> parent, View view, int pos, long id) { switch (pos) { case (1): Intent i = new Intent(Body.this, Practice.class); Body.this.startActivity(i); break; } } #Override public void onNothingSelected(AdapterView parent) { // Do nothing. } } } Here is the xml <TabHost android:id="#+id/thbodyview" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_alignParentBottom="true" android:layout_alignParentLeft="true" > <RelativeLayout android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" > <TabWidget android:id="#android:id/tabs" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_alignParentBottom="true" android:layout_alignParentLeft="true" > </TabWidget> <FrameLayout android:id="#android:id/tabcontent" android:layout_width="match_parent" android:layout_height="match_parent" > <LinearLayout android:id="#+id/Front" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" > <RelativeLayout android:layout_width="match_parent" android:layout_height="match_parent" > <LinearLayout android:id="#+id/llbottomtop" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_centerVertical="true" android:orientation="vertical" > <TextView android:id="#+id/tvupper" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="#+id/bAbs" android:text="Upper" android:textAppearance="?android:attr/textAppearanceLarge" android:textColor="#FFFFFF" /> <View android:layout_width="match_parent" android:layout_height="5dp" android:layout_centerVertical="true" android:background="#color/orange" /> <TextView android:id="#+id/tvlower" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="#+id/linearLayout1" android:text="Lower" android:textAppearance="?android:attr/textAppearanceLarge" android:textColor="#FFFFFF" /> </LinearLayout> <ImageView android:id="#+id/ivBody" android:layout_width="210dp" android:layout_height="430dp" android:layout_centerHorizontal="true" android:layout_centerVertical="true" android:src="#drawable/body_front" /> <Button android:id="#+id/bPecss" android:layout_width="83dp" android:layout_height="50dp" android:layout_above="#+id/bAbss" android:layout_alignRight="#+id/bAbss" android:text="Pecs" /> <Button android:id="#+id/bAbss" android:layout_width="80dp" android:layout_height="77dp" android:layout_alignBottom="#+id/llbottomtop" android:layout_centerHorizontal="true" android:layout_marginBottom="42dp" android:text="Abs" /> </RelativeLayout> </LinearLayout> <LinearLayout android:id="#+id/Back" android:layout_width="match_parent" android:layout_height="match_parent" > <RelativeLayout android:layout_width="match_parent" android:layout_height="match_parent" > <LinearLayout android:id="#+id/llbottomtop" android:layout_width="match_parent" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_centerVertical="true" android:orientation="vertical" > <TextView android:id="#+id/tvupper" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="#+id/bAbs" android:text="Upper" android:textAppearance="?android:attr/textAppearanceLarge" android:textColor="#FFFFFF" /> <View android:layout_width="match_parent" android:layout_height="5dp" android:layout_centerVertical="true" android:background="#color/orange" /> <TextView android:id="#+id/tvlower" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_below="#+id/linearLayout1" android:text="Lower" android:textAppearance="?android:attr/textAppearanceLarge" android:textColor="#FFFFFF" /> </LinearLayout> <ImageView android:id="#+id/ivBody" android:layout_width="210dp" android:layout_height="430dp" android:layout_centerHorizontal="true" android:layout_centerVertical="true" android:src="#drawable/body_back" /> </RelativeLayout> </LinearLayout> <LinearLayout android:id="#+id/tab3" android:layout_width="match_parent" android:layout_height="match_parent" > </LinearLayout> </FrameLayout> </RelativeLayout> </TabHost>
My tip is to get access to the tab title textview and set left|top|right|bottom drawable Example: //to get first tab title as textView from tabHost TextView tabTitle = (TextView) tabHost.getTabWidget().getChildAt(0) .findViewById(android.R.id.title); //to set the icon to left of the tab title tabTitle.setCompoundDrawablesWithIntrinsicBounds( getActivity().getResources().getDrawable( R.drawable.ic_tab_icon), null, null, null);
I have two physical devices one 2.2 and the other 4.2.2. on 2.2 there is no issue and the icon appears. on 4.2.2 there is no icon. Somethings changed in how tabs are laid out in Android. If you really required to use a TabHost i saw you can pass in a view as the tabindicator. This code is kinda pseudo code as it still some adjustment in the UI in terms of layout but try this: define a layout called tabindicator_layout.xml and put it in res/layout. the contents of which look like this: <?xml version="1.0" encoding="utf-8"?> <ImageView android:id="#+id/image" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center_horizontal|top" android:scaleType="center" > </ImageView> <TextView android:id="#+id/title" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center_horizontal" /> then in your class code at runtime inflate this view and populate the image and textview with what you desire. do this for each tab: //*********************below are my tabs******************************************* th.setup(); TabSpec specs = th.newTabSpec("Front"); specs.setContent(R.id.Front); View tabIndicator = LayoutInflater.from(this).inflate( R.layout.tabindicator_layout, th.getTabWidget(), false); ((TextView) tabIndicator.findViewById(R.id.title)).setText("Front"); ((ImageView) tabIndicator.findViewById(R.id.image)) .setImageResource(R.drawable.ic_launcher); specs.setIndicator(tabIndicator); TabSpec specs2 = th.newTabSpec("tag2"); specs2.setContent(R.id.Back); View tabIndicator2 = LayoutInflater.from(this).inflate( R.layout.tabindicator_layout, th.getTabWidget(), false); ((TextView) tabIndicator2.findViewById(R.id.title)).setText("Back"); ((ImageView) tabIndicator2.findViewById(R.id.image)) .setImageResource(R.drawable.ic_launcher); specs2.setIndicator(tabIndicator2); TabSpec specs3 = th.newTabSpec("tag3"); specs3.setContent(R.id.tab3); View tabIndicator3 = LayoutInflater.from(this).inflate( R.layout.tabindicator_layout, th.getTabWidget(), false); ((TextView) tabIndicator3.findViewById(R.id.title)).setText("...More"); ((ImageView) tabIndicator3.findViewById(R.id.image)) .setImageResource(R.drawable.ic_launcher); specs3.setIndicator(tabIndicator3); th.addTab(specs); th.addTab(specs2); th.addTab(specs3); of course replace R.drawable.ic_launcher with whatever icon you want to show another interesting thing that might help..i notice if i pass in a blank for the title that the original way works but shows no title. So you could go into photoshop and just add the title to the image and make it even better looking. Try this way: TabSpec specs = th.newTabSpec("Front"); specs.setContent(R.id.Front); specs.setIndicator("",getResources().getDrawable(R.drawable.ic_launcher)); th.addTab(specs);