自定义 CursorAdapter 未填充 ListView
当我运行具有尝试填充的列表视图的活动时,它显示为空。但是,在 logcat 中,我可以看到自定义 CursorAdapter 运行我的数据并至少返回一些视图。
public class JobAdapter extends CursorAdapter {
private String status;
private static final String tag ="TESTING CursorAdapter";
public JobAdapter(Context context, Cursor cur, boolean autoRequery, String s) {
super(context, cur, autoRequery);
Log.d(tag, "Job adapter create");
status = s;
}
@Override
public void bindView(View row, Context context, Cursor cursor) {
Log.d(tag, "Starting a bind");
Cursor c = getCursor();
if(!c.isClosed()){
TextView companyName = (TextView) row.findViewById(R.id.listCompanyName);
TextView positionTitle = (TextView) row.findViewById(R.id.listPositionTitle);
while(!c.isLast() && !c.getString(c.getColumnIndex(JobsDbAdapter.KEY_STATUS)).equalsIgnoreCase(status)){
Log.d(tag, "bind - moving c to next 1");
c.moveToNext();
}
if(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_STATUS)).equalsIgnoreCase(status)){
Log.d(tag, "found a status and trying to populate the view");
companyName.setText(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_COMPANY)));
positionTitle.setText(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_POSITION)));
Log.d(tag, "Company name = "+c.getString(c.getColumnIndex(JobsDbAdapter.KEY_COMPANY)));
if(c.isLast()) {
Log.d(tag, "bind - Closing c 1");
c.close();
}else {
Log.d(tag, "bind - moving c to next 2");
c.moveToNext();
}
}
}
}
@Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
Cursor c = getCursor();
Log.d(tag, "Starting a new");
final LayoutInflater inflater = LayoutInflater.from(context);
View row = inflater.inflate(R.layout.job_list_item, parent, false);
if(!c.isClosed()){
TextView companyName = (TextView) row.findViewById(R.id.listCompanyName);
TextView positionTitle = (TextView) row.findViewById(R.id.listPositionTitle);
while(!c.isLast() && !c.getString(c.getColumnIndex(JobsDbAdapter.KEY_STATUS)).equalsIgnoreCase(status)){
Log.d(tag, "new - moving c to next 1");
c.moveToNext();
}
if(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_STATUS)).equalsIgnoreCase(status)){
Log.d(tag, "new - found a status and trying to populate the view");
companyName.setText(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_COMPANY)));
positionTitle.setText(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_POSITION)));
if(c.isLast()) {
Log.d(tag, "new - Closing c 1");
c.close();
}else {
Log.d(tag, "new - moving c to next 2");
c.moveToNext();
}
}
Log.d(tag, "new - returning row");
return row;
}
?
我应该检查光标是否已到达数据库末尾吗 或者这件事会帮我处理吗?
我使用这个适配器的类很简单
public class AppliedForActivity extends ListActivity {
private JobsDbAdapter mDbHelper;
public void onCreate(Bundle savedInstanceState) {
Log.d("TESTING C", "STARTING THE APPLIED FOR ACTIVITY");
super.onCreate(savedInstanceState);
setContentView(R.layout.job_list);
mDbHelper = new JobsDbAdapter(this);
mDbHelper.open();
Cursor c = mDbHelper.fetchAllJobs();
setListAdapter(new JobAdapter(this, c, false, "applied for"));
}
}
请原谅花括号,我可能复制错了。
When I run my activity that has the list view I am trying to populate, it shows as empty. However, in logcat I can see that the custom CursorAdapter runs through my data and returns at least some views.
public class JobAdapter extends CursorAdapter {
private String status;
private static final String tag ="TESTING CursorAdapter";
public JobAdapter(Context context, Cursor cur, boolean autoRequery, String s) {
super(context, cur, autoRequery);
Log.d(tag, "Job adapter create");
status = s;
}
@Override
public void bindView(View row, Context context, Cursor cursor) {
Log.d(tag, "Starting a bind");
Cursor c = getCursor();
if(!c.isClosed()){
TextView companyName = (TextView) row.findViewById(R.id.listCompanyName);
TextView positionTitle = (TextView) row.findViewById(R.id.listPositionTitle);
while(!c.isLast() && !c.getString(c.getColumnIndex(JobsDbAdapter.KEY_STATUS)).equalsIgnoreCase(status)){
Log.d(tag, "bind - moving c to next 1");
c.moveToNext();
}
if(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_STATUS)).equalsIgnoreCase(status)){
Log.d(tag, "found a status and trying to populate the view");
companyName.setText(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_COMPANY)));
positionTitle.setText(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_POSITION)));
Log.d(tag, "Company name = "+c.getString(c.getColumnIndex(JobsDbAdapter.KEY_COMPANY)));
if(c.isLast()) {
Log.d(tag, "bind - Closing c 1");
c.close();
}else {
Log.d(tag, "bind - moving c to next 2");
c.moveToNext();
}
}
}
}
@Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
Cursor c = getCursor();
Log.d(tag, "Starting a new");
final LayoutInflater inflater = LayoutInflater.from(context);
View row = inflater.inflate(R.layout.job_list_item, parent, false);
if(!c.isClosed()){
TextView companyName = (TextView) row.findViewById(R.id.listCompanyName);
TextView positionTitle = (TextView) row.findViewById(R.id.listPositionTitle);
while(!c.isLast() && !c.getString(c.getColumnIndex(JobsDbAdapter.KEY_STATUS)).equalsIgnoreCase(status)){
Log.d(tag, "new - moving c to next 1");
c.moveToNext();
}
if(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_STATUS)).equalsIgnoreCase(status)){
Log.d(tag, "new - found a status and trying to populate the view");
companyName.setText(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_COMPANY)));
positionTitle.setText(c.getString(c.getColumnIndex(JobsDbAdapter.KEY_POSITION)));
if(c.isLast()) {
Log.d(tag, "new - Closing c 1");
c.close();
}else {
Log.d(tag, "new - moving c to next 2");
c.moveToNext();
}
}
Log.d(tag, "new - returning row");
return row;
}
}
Should I be checking to see if the cursor has reached the end of the database ? Or will this be handled for me ?
My class that uses this adapter is simply
public class AppliedForActivity extends ListActivity {
private JobsDbAdapter mDbHelper;
public void onCreate(Bundle savedInstanceState) {
Log.d("TESTING C", "STARTING THE APPLIED FOR ACTIVITY");
super.onCreate(savedInstanceState);
setContentView(R.layout.job_list);
mDbHelper = new JobsDbAdapter(this);
mDbHelper.open();
Cursor c = mDbHelper.fetchAllJobs();
setListAdapter(new JobAdapter(this, c, false, "applied for"));
}
}
Please excuse the curly braces, I may have copied wrong.
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
CursorAdapter 的想法是封装代码中的所有定位,只留给您可视化。也就是说你不需要使用moveToNext等定位方法。
正如我在您的代码中看到的,您正在尝试实现一些过滤。但使用数据库的想法是在 SQL 查询中制定您的标准。您不应查询所有作业,而应仅选择应在 ListView 中显示的作业。
bindView 和 newView 应该只适用于光标指向的当前记录,并且永远不应该调用 moveToNext 或 close。此外,CursorAdapter 假设您的光标有一个名为“_id”的整数字段。
另请参阅此处和那里。
The idea of CursorAdapter is to incapsulate all the postioning from your code and to leave only visualizing to you. That is you need not use moveToNext and other positioning methods.
As I can see in your code you are trying to implement some filtering. But the idea of working with database is to formulate your criteria in SQL query. Instead of querying ALL the jobs you should select only those which should be displayed in the ListView.
bindView and newView should only work with current record the cursor is pointed to and should never call moveToNext or close. Also, CursorAdapter assumes your cursor has an integer field named '_id'.
See also here and there.