从 CursorAdapter onClick 更新 UI
Update UI from CursorAdapter onClick
我有一个 listView,当用户单击 cardView 时,我从与该职位相关联的 employeeNumber 调用 Web 服务。我从 OkHttp3s enqueue 获取新的 Web 服务调用 onResponse 的数据。如何更新 listView 以从响应中填充新数据?
真的迷路了,因为我知道 listView 正在使用点击时生成的适配器。所以不确定如何调用 listView,以在响应完成后填充适配器。
我的 MainActivity,其中填充了第一个 ListView 并附加了适配器。
public class MainActivity extends AppCompatActivity {
private ProgressBar mProgressBar;
EmployeeDBHandler dbHandler;
private int mStartingEmployeeID = myStartingID;
private String table = "employees";
private static final String DATABASE_NAME = "OneTeam";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mProgressBar = (ProgressBar) findViewById(R.id.progressBar);
dbHandler = new EmployeeDBHandler(getApplicationContext());
mProgressBar.setVisibility(View.VISIBLE);
SharedPreferences sharedPref = PreferenceManager.getDefaultSharedPreferences(getApplicationContext());
getXMLData();
//GUI for seeing android SQLite Database in Chrome Dev Tools
Stetho.InitializerBuilder inBuilder = Stetho.newInitializerBuilder(this);
inBuilder.enableWebKitInspector(Stetho.defaultInspectorModulesProvider(this));
Stetho.Initializer in = inBuilder.build();
Stetho.initialize(in);
}
public void getXMLData() {
OkHttpClient client = getUnsafeOkHttpClient();
Request request = new Request.Builder()
.url(getString(R.string.API_FULL_URL))
.build();
client.newCall(request).enqueue(new Callback() {
@Override
public void onFailure(Call call, IOException e) {
e.printStackTrace();
}
@Override
public void onResponse(Call call, final Response response) throws IOException {
final String responseData = response.body().string();
final InputStream stream = new ByteArrayInputStream(responseData.getBytes());
final XMLPullParserHandler parserHandler = new XMLPullParserHandler();
final ArrayList<Employee> employees = (ArrayList<Employee>) parserHandler.parse(stream);
for (Employee e : employees) {
dbHandler.addEmployee(e);
}
runOnUiThread(new Runnable() {
@Override
public void run() {
mProgressBar.setVisibility(View.GONE);
displayTopList();
displayBottomList();
}
});
}
});
}
public void displayTopList() {
SQLiteDatabase db = dbHandler.getWritableDatabase();
Cursor mTopListCursor = db.rawQuery("SELECT * FROM " + table + " WHERE " + "Employee_number" + "=" + mStartingEmployeeID, null);
ListView mTopListView = (ListView) findViewById(R.id.mTopList);
TopListCursorAdapter topAdapter = new TopListCursorAdapter(this, mTopListCursor);
mTopListView.setAdapter(topAdapter);
}
public void displayBottomList() {
SQLiteDatabase db = dbHandler.getWritableDatabase();
Cursor mBottomListCursor = db.rawQuery("SELECT * FROM " + table + " WHERE " + "Employee_number" + "!=" + mStartingEmployeeID, null);
ListView mBottomListView = (ListView) findViewById(R.id.mDirectReportList);
BottomListViewAdapter bottomAdapter = new BottomListViewAdapter(this, mBottomListCursor);
mBottomListView.setAdapter(bottomAdapter);
}
@Override
public void onBackPressed() {
moveTaskToBack(false);
}
}
具有按钮 onClick 的 CursorAdapter
public class BottomListViewAdapter extends CursorAdapter {
private String mEmployeeNumber;
private EmployeeDBHandler dbHandler;
public BottomListViewAdapter(Context context, Cursor cursor) {
super(context, cursor, 0);
}
@Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
return LayoutInflater.from(context).inflate(R.layout.contact_cardview_layout, parent, false);
}
@Override
public void bindView(View view, final Context context, final Cursor cursor) {
ViewHolder holder;
holder = new ViewHolder();
holder.tvFirstName = (TextView) view.findViewById(R.id.personFirstName);
holder.tvLastName = (TextView) view.findViewById(R.id.personLastName);
holder.tvTitle = (TextView) view.findViewById(R.id.personTitle);
holder.mPeepPic = (ImageView) view.findViewById(R.id.person_photo);
holder.mDetailsButton = (ImageButton) view.findViewById(R.id.fullDetailButton);
holder.mCardView = (CardView) view.findViewById(R.id.home_screen_cardView);
String mFirstName = cursor.getString(cursor.getColumnIndexOrThrow("First_name"));
String mLastName = cursor.getString(cursor.getColumnIndexOrThrow("Last_name"));
String mTitle = cursor.getString(cursor.getColumnIndexOrThrow("Payroll_title"));
String mThumbnail = cursor.getString(cursor.getColumnIndexOrThrow("ThumbnailData"));
holder.tvFirstName.setText(mFirstName);
holder.tvLastName.setText(mLastName);
holder.tvTitle.setText(mTitle);
if (mThumbnail != null) {
byte[] imageAsBytes = Base64.decode(mThumbnail.getBytes(), Base64.DEFAULT);
Bitmap parsedImage = BitmapFactory.decodeByteArray(imageAsBytes, 0, imageAsBytes.length);
holder.mPeepPic.setImageBitmap(parsedImage);
} else {
holder.mPeepPic.setImageResource(R.drawable.img_place_holder_adapter);
}
final int position = cursor.getPosition();
holder.mDetailsButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
cursor.moveToPosition(position);
String mEmployeeNumber = cursor.getString(1);
String mEmail = cursor.getString(8);
String mFirstName = cursor.getString(2);
String mLastName = cursor.getString(3);
String mPhoneMobile = cursor.getString(4);
String mPhoneOffice = cursor.getString(5);
String mCostCenter = cursor.getString(10);
String mHasDirectReports = cursor.getString(7);
String mTitle = cursor.getString(6);
String mPic = cursor.getString(9);
Intent mIntent = new Intent(context, EmployeeFullInfo.class);
mIntent.putExtra("Employee_number", mEmployeeNumber);
mIntent.putExtra("Email", mEmail);
mIntent.putExtra("First_name", mFirstName);
mIntent.putExtra("Last_name", mLastName);
mIntent.putExtra("Phone_mobile", mPhoneMobile);
mIntent.putExtra("Phone_office", mPhoneOffice);
mIntent.putExtra("Cost_center_id", mCostCenter);
mIntent.putExtra("Has_direct_reports", mHasDirectReports);
mIntent.putExtra("Payroll_title", mTitle);
mIntent.putExtra("ThumbnailData", mPic);
mIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
view.getContext().startActivity(mIntent);
}
});
holder.mCardView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
cursor.moveToPosition(position);
mEmployeeNumber = cursor.getString(1);
Toast.makeText(context, mEmployeeNumber, Toast.LENGTH_SHORT).show();
dbHandler = new EmployeeDBHandler(context);
callNewDirectReport();
}
});
}
public static class ViewHolder {
TextView tvFirstName;
TextView tvLastName;
TextView tvTitle;
ImageView mPeepPic;
ImageButton mDetailsButton;
CardView mCardView;
}
private void callNewDirectReport() {
String mDirectReportUrl = "https://b2aproxy.supervalu.com/OneTeam/OneTeamService.asmx/GetDirectReportsWithPicture";
HttpUrl.Builder urlBuilder = HttpUrl.parse(mDirectReportUrl).newBuilder();
urlBuilder.addQueryParameter("manager_employee_number", mEmployeeNumber);
String url = urlBuilder.build().toString();
OkHttpClient client = getUnsafeOkHttpClient();
Request request = new Request.Builder()
.url(url)
.build();
client.newCall(request).enqueue(new Callback() {
@Override
public void onFailure(Call call, IOException e) {
e.printStackTrace();
}
@Override
public void onResponse(Call call, Response response) throws IOException {
final String responseData = response.body().string();
final InputStream stream = new ByteArrayInputStream(responseData.getBytes());
final XMLPullParserHandler parserHandler = new XMLPullParserHandler();
final ArrayList<Employee> employees = (ArrayList<Employee>) parserHandler.parse(stream);
for (Employee e : employees) {
dbHandler.addEmployee(e);
}
}
});
}
}
也许你可以尝试使用Loaders。
他们让您将数据源(Content Provider 或其他)与 Activity 或 Fragment 绑定。当加载器处于活动状态时,它们应该监视数据源并在内容更改时提供新结果。
我将向您介绍如何实现它们(尤其是 CursorLoader)的一般方法。我希望清楚:
public class MainActivity extends AppCompatActivity implements
LoaderManager.LoaderCallbacks<Cursor> {
private static final int LOADER_INTEGER = 1;
// ... existing code
@Override
public void onActivityCreated(Bundle savedInstanceState) {
getLoaderManager().initLoader(LOADER_INTEGER, null, this);
super.onActivityCreated(savedInstanceState);
}
@Override
public Loader<Cursor> onCreateLoader(int id, Bundle args) {
return new CursorLoader(
this,
ContentProvider.CONTENT_URI,
projection,
null,
null,
sortOrder
);
}
@Override
public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) {
mCursorAdapter.swapCursor(cursor);
}
@Override
public void onLoaderReset(Loader<Cursor> loader) {
mCursorAdapter.swapCursor(null);
}
}
您可以在互联网上阅读很多关于此的内容,例如 here。
是一个好的开始
希望对您有所帮助!
我有一个 listView,当用户单击 cardView 时,我从与该职位相关联的 employeeNumber 调用 Web 服务。我从 OkHttp3s enqueue 获取新的 Web 服务调用 onResponse 的数据。如何更新 listView 以从响应中填充新数据?
真的迷路了,因为我知道 listView 正在使用点击时生成的适配器。所以不确定如何调用 listView,以在响应完成后填充适配器。
我的 MainActivity,其中填充了第一个 ListView 并附加了适配器。
public class MainActivity extends AppCompatActivity {
private ProgressBar mProgressBar;
EmployeeDBHandler dbHandler;
private int mStartingEmployeeID = myStartingID;
private String table = "employees";
private static final String DATABASE_NAME = "OneTeam";
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mProgressBar = (ProgressBar) findViewById(R.id.progressBar);
dbHandler = new EmployeeDBHandler(getApplicationContext());
mProgressBar.setVisibility(View.VISIBLE);
SharedPreferences sharedPref = PreferenceManager.getDefaultSharedPreferences(getApplicationContext());
getXMLData();
//GUI for seeing android SQLite Database in Chrome Dev Tools
Stetho.InitializerBuilder inBuilder = Stetho.newInitializerBuilder(this);
inBuilder.enableWebKitInspector(Stetho.defaultInspectorModulesProvider(this));
Stetho.Initializer in = inBuilder.build();
Stetho.initialize(in);
}
public void getXMLData() {
OkHttpClient client = getUnsafeOkHttpClient();
Request request = new Request.Builder()
.url(getString(R.string.API_FULL_URL))
.build();
client.newCall(request).enqueue(new Callback() {
@Override
public void onFailure(Call call, IOException e) {
e.printStackTrace();
}
@Override
public void onResponse(Call call, final Response response) throws IOException {
final String responseData = response.body().string();
final InputStream stream = new ByteArrayInputStream(responseData.getBytes());
final XMLPullParserHandler parserHandler = new XMLPullParserHandler();
final ArrayList<Employee> employees = (ArrayList<Employee>) parserHandler.parse(stream);
for (Employee e : employees) {
dbHandler.addEmployee(e);
}
runOnUiThread(new Runnable() {
@Override
public void run() {
mProgressBar.setVisibility(View.GONE);
displayTopList();
displayBottomList();
}
});
}
});
}
public void displayTopList() {
SQLiteDatabase db = dbHandler.getWritableDatabase();
Cursor mTopListCursor = db.rawQuery("SELECT * FROM " + table + " WHERE " + "Employee_number" + "=" + mStartingEmployeeID, null);
ListView mTopListView = (ListView) findViewById(R.id.mTopList);
TopListCursorAdapter topAdapter = new TopListCursorAdapter(this, mTopListCursor);
mTopListView.setAdapter(topAdapter);
}
public void displayBottomList() {
SQLiteDatabase db = dbHandler.getWritableDatabase();
Cursor mBottomListCursor = db.rawQuery("SELECT * FROM " + table + " WHERE " + "Employee_number" + "!=" + mStartingEmployeeID, null);
ListView mBottomListView = (ListView) findViewById(R.id.mDirectReportList);
BottomListViewAdapter bottomAdapter = new BottomListViewAdapter(this, mBottomListCursor);
mBottomListView.setAdapter(bottomAdapter);
}
@Override
public void onBackPressed() {
moveTaskToBack(false);
}
}
具有按钮 onClick 的 CursorAdapter
public class BottomListViewAdapter extends CursorAdapter {
private String mEmployeeNumber;
private EmployeeDBHandler dbHandler;
public BottomListViewAdapter(Context context, Cursor cursor) {
super(context, cursor, 0);
}
@Override
public View newView(Context context, Cursor cursor, ViewGroup parent) {
return LayoutInflater.from(context).inflate(R.layout.contact_cardview_layout, parent, false);
}
@Override
public void bindView(View view, final Context context, final Cursor cursor) {
ViewHolder holder;
holder = new ViewHolder();
holder.tvFirstName = (TextView) view.findViewById(R.id.personFirstName);
holder.tvLastName = (TextView) view.findViewById(R.id.personLastName);
holder.tvTitle = (TextView) view.findViewById(R.id.personTitle);
holder.mPeepPic = (ImageView) view.findViewById(R.id.person_photo);
holder.mDetailsButton = (ImageButton) view.findViewById(R.id.fullDetailButton);
holder.mCardView = (CardView) view.findViewById(R.id.home_screen_cardView);
String mFirstName = cursor.getString(cursor.getColumnIndexOrThrow("First_name"));
String mLastName = cursor.getString(cursor.getColumnIndexOrThrow("Last_name"));
String mTitle = cursor.getString(cursor.getColumnIndexOrThrow("Payroll_title"));
String mThumbnail = cursor.getString(cursor.getColumnIndexOrThrow("ThumbnailData"));
holder.tvFirstName.setText(mFirstName);
holder.tvLastName.setText(mLastName);
holder.tvTitle.setText(mTitle);
if (mThumbnail != null) {
byte[] imageAsBytes = Base64.decode(mThumbnail.getBytes(), Base64.DEFAULT);
Bitmap parsedImage = BitmapFactory.decodeByteArray(imageAsBytes, 0, imageAsBytes.length);
holder.mPeepPic.setImageBitmap(parsedImage);
} else {
holder.mPeepPic.setImageResource(R.drawable.img_place_holder_adapter);
}
final int position = cursor.getPosition();
holder.mDetailsButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
cursor.moveToPosition(position);
String mEmployeeNumber = cursor.getString(1);
String mEmail = cursor.getString(8);
String mFirstName = cursor.getString(2);
String mLastName = cursor.getString(3);
String mPhoneMobile = cursor.getString(4);
String mPhoneOffice = cursor.getString(5);
String mCostCenter = cursor.getString(10);
String mHasDirectReports = cursor.getString(7);
String mTitle = cursor.getString(6);
String mPic = cursor.getString(9);
Intent mIntent = new Intent(context, EmployeeFullInfo.class);
mIntent.putExtra("Employee_number", mEmployeeNumber);
mIntent.putExtra("Email", mEmail);
mIntent.putExtra("First_name", mFirstName);
mIntent.putExtra("Last_name", mLastName);
mIntent.putExtra("Phone_mobile", mPhoneMobile);
mIntent.putExtra("Phone_office", mPhoneOffice);
mIntent.putExtra("Cost_center_id", mCostCenter);
mIntent.putExtra("Has_direct_reports", mHasDirectReports);
mIntent.putExtra("Payroll_title", mTitle);
mIntent.putExtra("ThumbnailData", mPic);
mIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
view.getContext().startActivity(mIntent);
}
});
holder.mCardView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
cursor.moveToPosition(position);
mEmployeeNumber = cursor.getString(1);
Toast.makeText(context, mEmployeeNumber, Toast.LENGTH_SHORT).show();
dbHandler = new EmployeeDBHandler(context);
callNewDirectReport();
}
});
}
public static class ViewHolder {
TextView tvFirstName;
TextView tvLastName;
TextView tvTitle;
ImageView mPeepPic;
ImageButton mDetailsButton;
CardView mCardView;
}
private void callNewDirectReport() {
String mDirectReportUrl = "https://b2aproxy.supervalu.com/OneTeam/OneTeamService.asmx/GetDirectReportsWithPicture";
HttpUrl.Builder urlBuilder = HttpUrl.parse(mDirectReportUrl).newBuilder();
urlBuilder.addQueryParameter("manager_employee_number", mEmployeeNumber);
String url = urlBuilder.build().toString();
OkHttpClient client = getUnsafeOkHttpClient();
Request request = new Request.Builder()
.url(url)
.build();
client.newCall(request).enqueue(new Callback() {
@Override
public void onFailure(Call call, IOException e) {
e.printStackTrace();
}
@Override
public void onResponse(Call call, Response response) throws IOException {
final String responseData = response.body().string();
final InputStream stream = new ByteArrayInputStream(responseData.getBytes());
final XMLPullParserHandler parserHandler = new XMLPullParserHandler();
final ArrayList<Employee> employees = (ArrayList<Employee>) parserHandler.parse(stream);
for (Employee e : employees) {
dbHandler.addEmployee(e);
}
}
});
}
}
也许你可以尝试使用Loaders。
他们让您将数据源(Content Provider 或其他)与 Activity 或 Fragment 绑定。当加载器处于活动状态时,它们应该监视数据源并在内容更改时提供新结果。
我将向您介绍如何实现它们(尤其是 CursorLoader)的一般方法。我希望清楚:
public class MainActivity extends AppCompatActivity implements
LoaderManager.LoaderCallbacks<Cursor> {
private static final int LOADER_INTEGER = 1;
// ... existing code
@Override
public void onActivityCreated(Bundle savedInstanceState) {
getLoaderManager().initLoader(LOADER_INTEGER, null, this);
super.onActivityCreated(savedInstanceState);
}
@Override
public Loader<Cursor> onCreateLoader(int id, Bundle args) {
return new CursorLoader(
this,
ContentProvider.CONTENT_URI,
projection,
null,
null,
sortOrder
);
}
@Override
public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) {
mCursorAdapter.swapCursor(cursor);
}
@Override
public void onLoaderReset(Loader<Cursor> loader) {
mCursorAdapter.swapCursor(null);
}
}
您可以在互联网上阅读很多关于此的内容,例如 here。
是一个好的开始希望对您有所帮助!