Impossibile trovare ViewByID in Adapter personalizzato
-
21-12-2019 - |
Domanda
Ho creato il mio adattatore personalizzato che estende l'adattatore di array:
public class AdapterGeoArea extends ArrayAdapter<GeoArea>{
private Context _context;
private int resource;
private ArrayList<GeoArea> _myGeoArea;
public AdapterGeoArea(Context context, ArrayList<GeoArea> myGeoArea) {
super(context, 0, myGeoArea);
_context = context;
_myGeoArea = myGeoArea;
}
public int getCount() {
return _myGeoArea.size();
}
public View getView(int position, View convertView, ViewGroup parent) {
LinearLayout GeoAreaView;
if (convertView == null) {
GeoAreaView = new LinearLayout(_context);
LayoutInflater li = LayoutInflater.from(_context);
convertView = li.inflate(R.layout.layout_geo_areas, null);
}
else {
GeoAreaView = (LinearLayout) convertView;
}
GeoArea curGeoArea = _myGeoArea.get(position);
TextView name = (TextView) GeoAreaView.findViewById(R.id.txtGeoAreaName);
name.setText(curGeoArea.name);
return convertView;
}
static class ViewHolder {
TextView name;
RelativeLayout childContainer;
}
@Override
public Filter getFilter() {
return null;
}
}
.
Ed ecco come lo sto usando nel mio principale:
public class ActivityGeoAreas extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.layout_geo_areas);
GeoArea.searchTerm = "Bar & Grill";
GeoArea torontoArea = new GeoArea("cityOfToronto");
ArrayList<GeoArea> testList = new ArrayList<GeoArea>();
testList.add(torontoArea);
AdapterGeoArea adapter = new AdapterGeoArea(this, testList);
ListView lv = (ListView) findViewById(R.id.textGeoArea);
lv.setAdapter(adapter);
}
}
.
Tutto sembra stare bene tranne che per questa linea:
TextView name = (TextView) GeoAreaView.findViewById(R.id.textGeoArea);
.
Ed ecco come ho definito il mio layout:
<RelativeLayout 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:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context=".ActivityGeoAreas" >
<TextView
android:id="@+id/textGeoArea"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentLeft="true"
android:layout_alignParentTop="true"
android:text="Choose Area"
android:textAppearance="?android:attr/textAppearanceLarge" />
<LinearLayout
android:id="@+id/LinearLayoutGeoAreas"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignLeft="@+id/textGeoArea"
android:layout_below="@+id/textGeoArea"
android:orientation="vertical" >
<ListView
android:id="@+id/listViewGeoArea"
android:layout_width="wrap_content"
android:layout_height="match_parent" >
</ListView>
</LinearLayout>
</RelativeLayout>
.
Semplicemente non riesce a trovare il testo TextGeaarea e questa riga diventa nulla, cosa sto facendo male?
Soluzione
Cambia questo
TextView name = (TextView) GeoAreaView.findViewById(R.id.txtGeoAreaName);
.
a
TextView name = (TextView) convertView.findViewById(R.id.txtGeoAreaName);
.
Immagino che tu sia stato confuso.
Sposta TestyVisualizza su un nuovo layout 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:id="@+id/textGeoArea"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_centerHorizontal="true"
android:layout_marginTop="14dp"
android:text="Choose Area"
android:textAppearance="?android:attr/textAppearanceLarge" />
</RelativeLayout>
.
Ora cambia il tuo getView
come sotto
LayoutInflater inflater;
public AdapterGeoArea(Context context, ArrayList<GeoArea> myGeoArea) {
super(context, 0, myGeoArea);
_context = context;
_myGeoArea = myGeoArea;
inflater = LayoutInflater.from(context); // initialize inflater
}
public View getView(int position, View convertView, ViewGroup parent) {
ViewHolder holder;
if (convertView == null) {
convertView = inflater.inflate(R.layout.list_row,parent,false);
holder = new ViewHolder();
holder.tv = (TextView)convertView.findViewById(R.id.textGeoArea);
holder.setTag(convertView);
}
else {
holder = (ViewHolder) convertView.getTag();
}
GeoArea curGeoArea = _myGeoArea.get(position);
holder.tv.setText(curGeoArea.name);
return convertView;
}
static class ViewHolder // use a view holder for smooth scrolling an performance
{
TextView tv;
}
. Altri suggerimenti
Sul primo passaggio, GeoAreaView
è un LinearLayout
senza figli da quando lo hai appena creato.convertView
è il View
Inizializzato il layout
che tiene il TextView
.Quindi è necessario utilizzarlo per trovare il TextView
.
TextView name = (TextView) convertView.findViewById(R.id.txtGeoAreaName);
.
Vedo che hai un ViewHolder
ma non sembra di usarlo.Potresti voler prendere un po 'di tempo e passare attraverso un buon tutorial sull'uso del ListView
.