问题
I've implemented two RecyclerView adapters, one is RecyclerViewAdapter and the other one is EmptyRecyclerViewAdapter. What I'm trying to do is to display the text Empty Text Here!
whenever all the items are removed.
Image 2
is working if there are no items yet in the list and it will display the text Empty Text Here!
which is shown on Image 2
below however, If there are already items on the list and If i will remove all of the items in the list, Image 1
will be the result which displays nothing, no text.
EmptyRecyclerViewAdapter.class
public class EmptyRecyclerViewAdapter extends RecyclerView.Adapter<EmptyRecyclerViewAdapter.ViewHolder> {
private String mMessage;
public EmptyRecyclerViewAdapter(){}
public EmptyRecyclerViewAdapter(String message){ mMessage = message;}
@Override
public EmptyRecyclerViewAdapter.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.empty_item, parent, false);
ViewHolder viewHolder = new ViewHolder(view);
if(mMessage != null){
viewHolder.mMessageView.setText(mMessage);
}
return viewHolder;
}
@Override
public void onBindViewHolder(EmptyRecyclerViewAdapter.ViewHolder holder, int position) {}
@Override
public int getItemCount() { return 1; }
public class ViewHolder extends RecyclerView.ViewHolder {
final View mView;
final TextView mMessageView;
public ViewHolder(View view) {
super(view);
mView = view;
mMessageView = (TextView) view.findViewById(R.id.empty_item_message);
}
}
}
RecyclerViewAdapter.class
public class RecyclerViewAdapter extends RecyclerView.Adapter <RecyclerView.ViewHolder> {
private List<ItemModel> list;
private Context mContext = null;
public RecyclerViewAdapter (Context context, List<ItemModel> itemList) {
mContext = context;
this.list = itemList;
}
@Override
public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.item, parent, false);
return new MyViewHolder(view);
}
@Override
public void onBindViewHolder(final RecyclerView.ViewHolder holder, int position) {
final ItemModel l = list.get(holder.getAdapterPosition());
final DataDb dataDb = new DataDb (mContext);
((MyViewHolder) holder).title.setText(l.getTitle());
((MyViewHolder) holder).caption.setText(l.getCaption());
((MyViewHolder) holder).removeBtn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
String confirmText = "Are you sure you want to remove this item ?";
AlertDialog.Builder builder = new AlertDialog.Builder(mContext, R.style.AlertDialogStyle);
builder.setTitle("Deleting..");;
builder.setPositiveButton("Remove", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
list.remove(holder.getAdapterPosition());
dataDb.removeItem(l.getId());
notifyDataSetChanged();
}
});
builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
});
AlertDialog alert = builder.create();
alert.getWindow().setLayout(600, 400);
alert.show();
}
});
}
@Override
public int getItemCount() {
return (list != null? list.size():0);
}
public class MyViewHolder extends RecyclerView.ViewHolder {
public TextView title;
public TextView caption;
ImageButton removeBtn;
public MyViewHolder(View itemView) {
super(itemView);
title = (TextView) itemView.findViewById(R.id.title);
caption = (TextView) itemView.findViewById(R.id.caption);
removeBtn = (ImageButton) itemView.findViewById(R.id.btnRemoveItem);
}
}
}
ActivityA.class
public class ActivityA extends Fragment {
List<ItemModel> list;
RecyclerView mRecyclerView;
RecyclerViewAdapter adapter;
ProgressBar progressBar;
DataDb dataDb;
EmptyRecyclerViewAdapter emptyRecyclerViewAdapter;
public ActivityA() {}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
super.onCreateView(inflater, container, savedInstanceState);
View rootView = inflater.inflate(activity_one_layout, container, false);
progressBar = (ProgressBar) rootView.findViewById(R.id.progressBar);
mRecyclerView = (RecyclerView) rootView.findViewById(R.id.recyclerview);
dataDb = new DataDb(getActivity());
list= dataDb .getList();
LinearLayoutManager linearLayoutManager = new LinearLayoutManager(getActivity());
mRecyclerView.setLayoutManager(linearLayoutManager);
mRecyclerView.setHasFixedSize(true);
linearLayoutManager.setOrientation(LinearLayoutManager.VERTICAL);
if(list == null || list.size() == 0) {
progressBar.setVisibility(View.GONE);
emptyRecyclerViewAdapter = new EmptyRecyclerViewAdapter("Empty Text Here!");
mRecyclerView.setAdapter(emptyRecyclerViewAdapter);
} else {
new LoadList().execute();
}
return rootView;
}
@Override
public void onResume() {
super.onResume();
}
private class LoadList extends AsyncTask<Void, Void, Void> {
@Override
protected void onPreExecute() {
super.onPreExecute();
progressBar.setVisibility(View.VISIBLE);
}
@Override
protected Void doInBackground(Void... voids) {
try {
Thread.sleep(1000);
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
@Override
protected void onPostExecute(Void params){
progressBar.setVisibility(View.GONE);
if(!list.isEmpty()) {
adapter = new RecyclerViewAdapter(getActivity(), list);
mRecyclerView.setAdapter(adapter);
adapter.notifyDataSetChanged();
} else {
Toast.makeText(getActivity(), "", Toast.LENGTH_SHORT).show();
}
}
}
}
Image 1 - output result
Image 2 - Output goal
回答1:
You've to let your Activity know that the list set in adapter has changed and item count comes down to zero. When the list size gets empty then you'll need to switch the adapter from Activity.
You can achieve this with an Interface. Basically, declare an interface first and hold an instance of it in Adapter. Whenever you call notifyDataSetChanged, you should call this instance of Interface as well. This will trigger the Interface method implemented in Activity. You can switch the Adapter from that point.
Modify your classes like following.
RecyclerViewAdapter.class
public class RecyclerViewAdapter extends RecyclerView.Adapter <RecyclerView.ViewHolder> {
//Declare an Interface which will work as a listener of notifyDataSetChanged.
// We'll then switch the adapter of Activity accordingly
public interface OnNotifyDataSetChanged {
void OnNotifyDataSetChangedFired(int dataSize);
}
private OnNotifyDataSetChanged onNotifyDataSetChanged;
private List<ItemModel> list;
private Context mContext = null;
public RecyclerViewAdapter (Context context, List<ItemModel> itemList, OnNotifyDataSetChanged onNotifyDataSetChanged) {
mContext = context;
this.list = itemList;
this.onNotifyDataSetChanged = onNotifyDataSetChanged;
}
@Override
public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext()).inflate(R.layout.item, parent, false);
return new MyViewHolder(view);
}
@Override
public void onBindViewHolder(final RecyclerView.ViewHolder holder, int position) {
final ItemModel l = list.get(holder.getAdapterPosition());
final DataDb dataDb = new DataDb (mContext);
((MyViewHolder) holder).title.setText(l.getTitle());
((MyViewHolder) holder).caption.setText(l.getCaption());
((MyViewHolder) holder).removeBtn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
String confirmText = "Are you sure you want to remove this item ?";
AlertDialog.Builder builder = new AlertDialog.Builder(mContext, R.style.AlertDialogStyle);
builder.setTitle("Deleting..");;
builder.setPositiveButton("Remove", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
list.remove(holder.getAdapterPosition());
dataDb.removeItem(l.getId());
notifyDataSetChanged();
// Trigger our Interface instance to let the Activity know that the adapter is updated
if(onNotifyDataSetChanged != null){
onNotifyDataSetChanged.OnNotifyDataSetChangedFired(list.size());
}
}
});
builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
dialog.dismiss();
}
});
AlertDialog alert = builder.create();
alert.getWindow().setLayout(600, 400);
alert.show();
}
});
}
@Override
public int getItemCount() {
return (list != null? list.size():0);
}
public class MyViewHolder extends RecyclerView.ViewHolder {
public TextView title;
public TextView caption;
ImageButton removeBtn;
public MyViewHolder(View itemView) {
super(itemView);
title = (TextView) itemView.findViewById(R.id.title);
caption = (TextView) itemView.findViewById(R.id.caption);
removeBtn = (ImageButton) itemView.findViewById(R.id.btnRemoveItem);
}
}
}
ActivityA.class
public class ActivityA extends Fragment implements OnNotifyDataSetChanged {
List<ItemModel> list;
RecyclerView mRecyclerView;
RecyclerViewAdapter adapter;
ProgressBar progressBar;
DataDb dataDb;
EmptyRecyclerViewAdapter emptyRecyclerViewAdapter;
public ActivityA() {}
@Override
void OnNotifyDataSetChangedFired(int dataSize){
//Now, switch the adapter if needed
if(dataSize <= 0){
mRecyclerView.setAdapter(new EmptyRecyclerViewAdapter("Empty Text Here!"));
}
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
super.onCreateView(inflater, container, savedInstanceState);
View rootView = inflater.inflate(activity_one_layout, container, false);
progressBar = (ProgressBar) rootView.findViewById(R.id.progressBar);
mRecyclerView = (RecyclerView) rootView.findViewById(R.id.recyclerview);
dataDb = new DataDb(getActivity());
list= dataDb .getList();
LinearLayoutManager linearLayoutManager = new LinearLayoutManager(getActivity());
mRecyclerView.setLayoutManager(linearLayoutManager);
mRecyclerView.setHasFixedSize(true);
linearLayoutManager.setOrientation(LinearLayoutManager.VERTICAL);
if(list == null || list.size() == 0) {
progressBar.setVisibility(View.GONE);
emptyRecyclerViewAdapter = new EmptyRecyclerViewAdapter("Empty Text Here!");
mRecyclerView.setAdapter(emptyRecyclerViewAdapter);
} else {
new LoadList().execute();
}
return rootView;
}
@Override
public void onResume() {
super.onResume();
}
private class LoadList extends AsyncTask<Void, Void, Void> {
@Override
protected void onPreExecute() {
super.onPreExecute();
progressBar.setVisibility(View.VISIBLE);
}
@Override
protected Void doInBackground(Void... voids) {
try {
Thread.sleep(1000);
} catch (Exception e) {
e.printStackTrace();
}
return null;
}
@Override
protected void onPostExecute(Void params){
progressBar.setVisibility(View.GONE);
if(!list.isEmpty()) {
// New updated constructor of the Adapter
adapter = new RecyclerViewAdapter(getActivity(), list, ActivityA.this);
mRecyclerView.setAdapter(adapter);
adapter.notifyDataSetChanged();
} else {
Toast.makeText(getActivity(), "", Toast.LENGTH_SHORT).show();
}
}
}
}
来源:https://stackoverflow.com/questions/41919781/textview-wont-display-after-removing-all-recyclerview-items