Recyclerview initially not scrolling smoothly while loading data from web service - android-recyclerview

I'm using recycler view as a single child inside the swipe refresh layout. Initially, its not scrolling smoothly while loading data from webservice both upwards and downwards. But after first scroll, it scrolls smoothly. How to make it scroll smoothly at very first scroll itself.
private RecyclerView newsFeedList;
newsFeedList = (RecyclerView) view.findViewById(R.id.rv_feed_list);
newsFeedList.setHasFixedSize(true);
LinearLayoutManager llm = new LinearLayoutManager(getActivity());
llm.setOrientation(LinearLayoutManager.VERTICAL);
newsFeedList.setLayoutManager(llm);
newsFeedAdapter = new NewsFeedAdapter(getActivity(), new ArrayList<NewsFeedParser.NewsFeed>(), newsFeedList);
newsFeedList.setAdapter(newsFeedAdapter);
and updated recyclerview after getting response from web service by calling below method:
private void parseDataToNewsFeed(String response, boolean isLoadMore) {
Gson gson = new Gson();
NewsFeedParser newsFeedParser = gson.fromJson(response, NewsFeedParser.class);
if (newsFeedParser.data != null && newsFeedParser.data.size() > 0) {
if (isLoadMore) {
newsFeedAdapter.removeProgress(newsFeedAdapter.getItemCount());
newsFeedAdapter.addList(newsFeedParser.data);
} else {
currentPageCount = 1;
newsFeedAdapter.updateList(newsFeedParser.data);
}
} else {
newsFeedAdapter.updateList(newsFeedParser.data);
txtNoResult.setText(getString(R.string.no_clubs_socities_subscribed));
txtNoResult.setVisibility(View.VISIBLE);
}
}
Adaper class:
public class NewsFeedAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
private final DisplayImageOptions options;
private Context context;
private ArrayList<NewsFeedParser.NewsFeed> itemList;
private int lastVisibleItem, totalItemCount, visibleThreshold = 2;
private boolean loading;
public OnLoadMoreListener onLoadMoreListener;
private OnItemClickListener itemClickListener;
// private ImageLoader mImageLoader;
private final int VIEW_ITEM = 1;
private final int VIEW_PROG = 0;
private long mLastClickTimeListViewItem = 0;
public NewsFeedAdapter(Context context, ArrayList<NewsFeedParser.NewsFeed> itemList, RecyclerView recyclerView) {
this.context = context;
this.itemList = itemList;
options = new DisplayImageOptions.Builder()
.showImageOnLoading(R.drawable.ic_default_news)
.showImageForEmptyUri(R.drawable.ic_default_news)
.showImageOnFail(R.drawable.ic_default_news)
.cacheInMemory(true)
.cacheOnDisk(true)
.considerExifParams(true)
.bitmapConfig(Bitmap.Config.RGB_565)
.build();
if (recyclerView.getLayoutManager() instanceof LinearLayoutManager) {
final LinearLayoutManager linearLayoutManager = (LinearLayoutManager) recyclerView.getLayoutManager();
recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() {
#Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
super.onScrolled(recyclerView, dx, dy);
totalItemCount = linearLayoutManager.getItemCount();
lastVisibleItem = linearLayoutManager.findLastVisibleItemPosition();
if (!loading && totalItemCount <= (lastVisibleItem + visibleThreshold)) {
if (onLoadMoreListener != null) {
onLoadMoreListener.onLoadMore();
}
loading = true;
}
}
});
}
}
#Override
public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
RecyclerView.ViewHolder vh;
if (viewType == VIEW_ITEM) {
View itemView = LayoutInflater.from(context).inflate(R.layout.fragment_news_feed_trending_list_item, parent, false);
vh = new NewsFeedViewHolder(itemView);
} else {
View progView = LayoutInflater.from(context).inflate(R.layout.view_refresh_footer, parent, false);
vh = new ProgressViewHolder(progView);
}
return vh;
}
#Override
public int getItemViewType(int position) {
return itemList.get(position) != null ? VIEW_ITEM : VIEW_PROG;
}
#Override
public int getItemCount() {
return itemList.size();
}
#Override
public void onBindViewHolder(final RecyclerView.ViewHolder holder, final int position) {
if (holder instanceof NewsFeedViewHolder) {
final NewsFeedParser.NewsFeed singleItem = itemList.get(position);
((NewsFeedViewHolder) holder).txtNews.setText(Html.fromHtml(singleItem.title));
((NewsFeedViewHolder) holder).txtDays.setText(DateConversion.getStatusTiming(context, singleItem.modified));
((NewsFeedViewHolder) holder).imgNewsPhoto.setImageResource(R.drawable.ic_default_news);
if (singleItem.featured_image != null) {
if (singleItem.featured_image.attachment_meta != null) {
if (singleItem.featured_image.attachment_meta.sizes != null) {
if (singleItem.featured_image.attachment_meta.sizes.thumbnail != null) {
if (!TextUtils.isNullOrEmpty(singleItem.featured_image.attachment_meta.sizes.thumbnail.url)) {
ImageLoader.getInstance().displayImage(singleItem.featured_image.attachment_meta.sizes.thumbnail.url, ((NewsFeedViewHolder) holder).imgNewsPhoto, options);
} else {
if (!TextUtils.isNullOrEmpty(singleItem.featured_image.source)) {
ImageLoader.getInstance().displayImage(singleItem.featured_image.source, ((NewsFeedViewHolder) holder).imgNewsPhoto, options);
}
}
}
}
}
}
if (singleItem.read_status == 0) {
((NewsFeedViewHolder) holder).rlFeedItem.setBackgroundColor(ContextCompat.getColor(context, R.color.clr_news_feed_item_bg));
} else {
((NewsFeedViewHolder) holder).rlFeedItem.setBackgroundColor(ContextCompat.getColor(context, R.color.transparent));
}
holder.itemView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (SystemClock.elapsedRealtime() - mLastClickTimeListViewItem < 1000) {
return;
}
mLastClickTimeListViewItem = SystemClock.elapsedRealtime();
if (itemClickListener != null) {
itemClickListener.onItemClick(singleItem);
singleItem.read_status = 1;
notifyItemChanged(position);
}
}
});
} else {
((ProgressViewHolder) holder).progressBar.setLinearProgress(true);
}
}
public void addList(ArrayList<NewsFeedParser.NewsFeed> items) {
if (items == null) {
this.itemList.add(null);
} else {
for (NewsFeedParser.NewsFeed item : items) {
this.itemList.add(item);
}
}
notifyDataSetChanged();
}
public void updateList(ArrayList<NewsFeedParser.NewsFeed> items) {
if (items != null) {
this.itemList = items;
}
notifyDataSetChanged();
}
public void removeProgress(int itemCount) {
this.itemList.remove(itemCount - 1);
notifyItemRemoved(itemCount);
}
public static class NewsFeedViewHolder extends RecyclerView.ViewHolder {
USUTextView txtNews, txtDays;
ImageView imgNewsPhoto;
RelativeLayout rlFeedItem;
public NewsFeedViewHolder(View itemView) {
super(itemView);
txtNews = (USUTextView) itemView.findViewById(R.id.txt_news);
txtDays = (USUTextView) itemView.findViewById(R.id.txt_days);
imgNewsPhoto = (ImageView) itemView.findViewById(R.id.img_news_photo);
rlFeedItem = (RelativeLayout) itemView.findViewById(R.id.rl_feed_list_item);
}
}
public static class ProgressViewHolder extends RecyclerView.ViewHolder {
public ProgressWheel progressBar;
public ProgressViewHolder(View progView) {
super(progView);
progressBar = (ProgressWheel) progView.findViewById(R.id.progress_bar);
}
}
public void setLoaded() {
loading = false;
}
public void setOnLoadMoreListener(OnLoadMoreListener onLoadMoreListener) {
this.onLoadMoreListener = onLoadMoreListener;
}
public interface OnLoadMoreListener {
void onLoadMore();
}
public void setOnItemClickListener(OnItemClickListener recyclerClickListener) {
this.itemClickListener = recyclerClickListener;
}
public interface OnItemClickListener {
void onItemClick(NewsFeedParser.NewsFeed item);
}
}
Please suggest me any idea.....

Related

How to implement an Action on Item Click in Order to show the result in CardView of RecyclerView

I am very new to Android programming. I can't find a solution for my current problem which I've been trying to solve for days.
I want to click on item of populated Array List and get the position i.e. the searched word result in Cardview (neither ItemClickListener nor OnSuggestionListener did work here. Here is my code of MainActivity and I would be very thankful if somebody could help me out:
RecyclerView recyclerView;
RecyclerView.LayoutManager layoutManager;
SearchAdapter adapter;
MaterialSearchBar materialSearchBar;
List<String> suggestList = new ArrayList<>();
Database database;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
//init View
recyclerView = (RecyclerView) findViewById(R.id.recycler_search);
layoutManager = new LinearLayoutManager(this);
recyclerView.setLayoutManager(layoutManager);
recyclerView.setHasFixedSize(true);
materialSearchBar = (MaterialSearchBar) findViewById(R.id.search_bar);
database = new Database(this);
materialSearchBar.setHint("Search");
materialSearchBar.setCardViewElevation(10);
loadSuggestList();
materialSearchBar.addTextChangeListener (new TextWatcher() {
#Override
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
#Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
List<String> suggest = new ArrayList<>();
for (String search : suggestList) {
if (search.toLowerCase().contains(materialSearchBar.getText().toLowerCase()))
suggest.add(search);
}
materialSearchBar.setLastSuggestions(suggest);
}
#Override
public void afterTextChanged(Editable s) {
}
});
materialSearchBar.setOnSearchActionListener (new MaterialSearchBar.OnSearchActionListener() {
#Override
public void onSearchStateChanged(boolean enabled) {
if (!enabled)
adapter = new SearchAdapter(getBaseContext(), database.getLughats());
recyclerView.setAdapter(adapter);
}
#Override
public void onSearchConfirmed(CharSequence text) {
startSearch(text.toString());
}
#Override
public void onButtonClicked(int buttonCode) {
}
});
adapter = new SearchAdapter(this, database.getLughats());
recyclerView.setAdapter(adapter);
}
private void startSearch(String text) {
adapter = new SearchAdapter(this, database.getLughatByWort(text));
recyclerView.setAdapter(adapter);
}
private void loadSuggestList() {
suggestList = database.getWorts();
materialSearchBar.setLastSuggestions(suggestList);
}
}```
Let me know if I should post here also my AdapterCode for the ViewHolder.
Thank you for your help in advance!
Here ist my AdapterCode:
class SearchViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener{
RecyclerItemClick itemClickListener;
public TextView wort, praeteritum, partizip2, artikelGrammatik, uebersetzung1, uebersetzung2;
public ImageButton button1, button2;
public SearchViewHolder(#NonNull View itemView) {
super(itemView);
wort = (TextView)itemView.findViewById(R.id.wort);
praeteritum = (TextView)itemView.findViewById(R.id.praeteritum);
partizip2 = (TextView)itemView.findViewById(R.id.partizip2);
artikelGrammatik = (TextView)itemView.findViewById(R.id.artikelGrammatik);
uebersetzung1 = (TextView)itemView.findViewById(R.id.uebersetzung1);
uebersetzung2 = (TextView)itemView.findViewById(R.id.uebersetzung2);
button1 = (ImageButton)itemView.findViewById(R.id.button_id_1);
button2 = (ImageButton) itemView.findViewById(R.id.button_id_2);
itemView.setOnClickListener(this);
}
#Override
public void onClick(View v) {
this.itemClickListener.onItemClickListener(v, getLayoutPosition());
}
public void setItemClickListener(RecyclerItemClick ic) {
this.itemClickListener = ic;
}
}
public class SearchAdapter extends RecyclerView.Adapter<SearchViewHolder> {
private Context context;
private List<Lughat> lughats;
public SearchAdapter(Context context, List<Lughat> lughats) {
this.context = context;
this.lughats = lughats;
}
#NonNull
#Override
public SearchViewHolder onCreateViewHolder(#NonNull ViewGroup parent, int viewType) {
LayoutInflater inflater = LayoutInflater.from(parent.getContext());
final View itemView = inflater.inflate(R.layout.layout_item, parent, false);
return new SearchViewHolder(itemView);
}
#Override
public void onBindViewHolder(#NonNull final SearchViewHolder holder, final int position) {
holder.wort.setText(lughats.get(position).getWort());
holder.praeteritum.setText(lughats.get(position).getPraeteritum());
holder.partizip2.setText(lughats.get(position).getPartizip2());
holder.artikelGrammatik.setText(lughats.get(position).getArtikelGrammatik());
holder.uebersetzung1.setText(lughats.get(position).getUebersetzung1());
holder.uebersetzung2.setText(lughats.get(position).getUebersetzung2());
CharSequence praet;
praet = holder.praeteritum.getText();
if (praet.length() == 0) {
holder.praeteritum.setVisibility(View.GONE);
holder.button1.setVisibility(View.GONE);
} else {
holder.praeteritum.setVisibility(View.VISIBLE);
holder.button1.setVisibility(View.VISIBLE);
}
CharSequence part2;
part2 = holder.partizip2.getText();
if (part2.length() == 0) {
holder.partizip2.setVisibility(View.GONE);
} else {
holder.partizip2.setVisibility(View.VISIBLE);
}
CharSequence artGr;
artGr = holder.artikelGrammatik.getText();
if (artGr.length() == 0) {
holder.artikelGrammatik.setVisibility(View.GONE);
holder.button2.setVisibility(View.GONE);
} else {
holder.artikelGrammatik.setVisibility(View.VISIBLE);
holder.button2.setVisibility(View.VISIBLE);
}
CharSequence ueb2;
ueb2 = holder.uebersetzung2.getText();
if (ueb2.length() == 0) {
holder.uebersetzung2.setVisibility(View.GONE);
} else {
holder.uebersetzung2.setVisibility(View.VISIBLE);
}
holder.button1.setOnClickListener(new ToastMaker(context.getApplicationContext()));
holder.button2.setOnClickListener(new ToastMaker(context.getApplicationContext()));
holder.setItemClickListener(new RecyclerItemClick() {
#Override
public void onItemClickListener(View v, int position) {
Toast.makeText(context, "Begriff", Toast.LENGTH_LONG).show();
}
});
}
#Override
public int getItemCount() {
return lughats.size();
}
}
If I do it also with OnClickListener it does not work too, it does not call the method startSearch.
button3.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
CharSequence text = materialSearchBar.getText();
Toast.makeText(getApplicationContext(), text, Toast.LENGTH_LONG).show();
startSearch(text.toString());
}

how to confirm selected items in recyclerview item list and make selected on layout

i am preparing textview seat numbers list by using recyclerview grid layout manager. i can select the multiple items in the recyclerview list by red color. now i want to keep this seat item selected as red color when on cliking on confirm seat button. when i reopen the recyclerview list it should show the seat selected red color and other seat item in normal color.
confirm seat button clickconfrim seat button click
SelectionAdapter
'''
public class SelectionAdapter extends RecyclerView.Adapter<SelectionAdapter.MygridViewHolder> {
private Context applicationContext;
private ArrayList<Seatnos> list, selected;
public SelectionAdapter(Context applicationContext, ArrayList<Seatnos> list) {
this.applicationContext = applicationContext;
this.list = list;
this.selected = new ArrayList<>();
}
#NonNull
#Override
public MygridViewHolder onCreateViewHolder(#NonNull ViewGroup parent, int viewType) {
LayoutInflater layoutInflater=LayoutInflater.from(parent.getContext());
View view=layoutInflater.inflate(R.layout.list_layout_selection,parent,false);
return new MygridViewHolder(view);
}
#Override
public void onBindViewHolder(#NonNull final MygridViewHolder holder, final int position) {
final Seatnos seatnos = list.get(position);
holder.textView.setText(String.valueOf(position));
holder.textView.setText(seatnos.getTextno());
holder.textView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
if (selected.contains(seatnos)) {
selected.remove(seatnos);
unhighlightView(holder);
} else {
selected.add(seatnos);
highlightView(holder);
}
}
});
if (selected.contains(seatnos))
highlightView(holder);
else
unhighlightView(holder);
}
private void highlightView(MygridViewHolder holder) {
holder.itemView.setBackgroundColor(ContextCompat.getColor(applicationContext, R.color.red));
}
private void unhighlightView(MygridViewHolder holder) {
holder.itemView.setBackgroundColor(ContextCompat.getColor(applicationContext, android.R.color.transparent));
}
#Override
public int getItemCount() {
return list.size();
}
class MygridViewHolder extends RecyclerView.ViewHolder {
TextView textView;
MygridViewHolder(#NonNull View itemView) {
super(itemView);
textView = (TextView) itemView.findViewById(R.id.textViewsA);
}
}
public void addAll(ArrayList<Seatnos> list) {
clearAll(false);
this.list = list;
notifyDataSetChanged();
}
public void clearAll(boolean isNotify) {
list.clear();
selected.clear();
if (isNotify) notifyDataSetChanged();
}
public void clearSelected() {
selected.clear();
notifyDataSetChanged();
}
public void selectAll() {
selected.clear();
selected.addAll(list);
notifyDataSetChanged();
}
public ArrayList<Seatnos> getSelected() {
return selected;
}
}
'''
SeatSelectionactivity.java
'''
public class SeatSelectionActivity extends AppCompatActivity {
RecyclerView recyclerView;
Activity activity = SeatSelectionActivity.this;
Button btnGetSelected,btnreset;
FirebaseDatabase database;
DatabaseReference ref;
SelectionAdapter selectionAdapter;
ArrayList<Seatnos> list;
Update update;
ChildEventListener mChildListner;
ValueEventListener mValueEventListner;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_seat_selection);
btnGetSelected = (Button) findViewById(R.id.btconfirm);
recyclerView=(RecyclerView) findViewById(R.id.viewseat);
list = new ArrayList<>();
String uid = getIntent().getStringExtra(UpdateAdapter.USER_KEY);
DatabaseReference databaseReference = FirebaseDatabase.getInstance().getReference("updates").child(uid);
selectionAdapter=new SelectionAdapter(this, list);
RecyclerView.LayoutManager layoutManager=new GridLayoutManager(this,4);
recyclerView.setLayoutManager(layoutManager);
recyclerView.setItemAnimator(new DefaultItemAnimator());
mValueEventListner = new ValueEventListener() {
#Override
public void onDataChange(#NonNull DataSnapshot dataSnapshot) {
Update update =dataSnapshot.getValue(Update.class);
update.setUid(dataSnapshot.getKey());
int seat= Integer.parseInt(update.getSeat());
ArrayList<String> array = new ArrayList<String>(seat);
for(long i=0; i<seat; i++) {
array.add(String.valueOf(i));
Seatnos seatnos = new Seatnos();
seatnos.setTextno(""+(i+1));
if(i==0){
seatnos.setChecked(true);
}
list.add(seatnos);
}
recyclerView.setAdapter(selectionAdapter);
}
#Override
public void onCancelled(#NonNull DatabaseError databaseError) {
}
};
databaseReference.addValueEventListener(mValueEventListner);
}
public void reset(View view) {
}
public void bookconfirm(View view) {
if (selectionAdapter.getSelected().size() > 0) {
//ArrayList<Integer> mlist = new ArrayList<>();
StringBuilder stringBuilder = new StringBuilder();
for (int i = 0; i < selectionAdapter.getSelected().size(); i++) {
stringBuilder.append(selectionAdapter.getSelected().get(i).getTextno());
stringBuilder.append("\n");
}
Toast.makeText(activity, String.format("Selected %d items", selectionAdapter.getSelected().size()), Toast.LENGTH_SHORT).show();
showToast(stringBuilder.toString().trim());
} else {
showToast("No Selection");
}
};
public void selectAll(View v) {
selectionAdapter.selectAll();
}
public void deselectAll(View v) {
selectionAdapter.clearSelected();
}
public void doAction(View v) {
Toast.makeText(activity, String.format("Selected %d items", selectionAdapter.getSelected().size()), Toast.LENGTH_SHORT).show();
}
private void showToast(String msg) {
Toast.makeText(this, msg, Toast.LENGTH_SHORT).show();
}
}
'''
model class
'''
public class Seatnos implements Serializable {
String textno;
String sid;
private boolean isChecked = false;
public Seatnos() {
}
public boolean isChecked() {
return isChecked;
}
public void setChecked(boolean checked) {
isChecked = checked;
}
public String getSid() {
return sid;
}
public void setSid(String sid) {
this.sid = sid;
}
public Seatnos(String textno) {
this.textno = textno;
}
public String getTextno() {
return textno;
}
public void setTextno(String textno) {
this.textno = textno;
}
}
'''
You would use shared preferences to save the state of the selected item:
Do this in onBindViewHolder:
#Override
public void onBindViewHolder(#NonNull final MygridViewHolder holder, final int position) {
final Seatnos seatnos = list.get(position);
holder.textView.setText(String.valueOf(position));
holder.textView.setText(seatnos.getTextno());
//read from preferences
SharedPreferences pref = getSharedPreferences("item", MODE_PRIVATE);
String state = pref.getString(String.valueOf(position)+"state", "default");
if(state.equals("selected")){
//selected
highlightView(holder);
}else{
//not selected
unhighlightView(holder);
}
//on click
holder.textView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
if (selected.contains(seatnos)) {
selected.remove(seatnos);
unhighlightView(holder);
//save state
SharedPreferences.Editor editor = getSharedPreferences("item", MODE_PRIVATE).edit();
editor.putString(String.valueOf(position)+"state", "not_selected");
editor.apply();
} else {
selected.add(seatnos);
highlightView(holder);
//save state
SharedPreferences.Editor editor = getSharedPreferences("item", MODE_PRIVATE).edit();
editor.putString(String.valueOf(position)+"state", "selected");
editor.apply();
}
}
});
......................
......................
......................
}
UPDATE:
Yes you should use the context passed to your adapter to access the shared prederences:
This:
getSharedPreferences("item", MODE_PRIVATE);
Becomes:
applicationContext.getSharedPreferences("item", MODE_PRIVATE);
This:
getSharedPreferences("item", MODE_PRIVATE).edit();
Becomes:
applicationContext.getSharedPreferences("item", MODE_PRIVATE).edit();

Loading more data in recyclerview on scroll

I am getting Json data in list which has like 100 of items. I am passing this list to the recyclerview adapter. But i want to pass only 10 items at first. after 10 items when user scrolls the list it should load more data from the list.I have Implemented the scroll listeners and other adapter.I am not sure how to pass 10 items from the json list to adapter.
ScrollListener
public abstract class PaginationScrollListener extends RecyclerView.OnScrollListener {
LinearLayoutManager layoutManager;
/**
* Supporting only LinearLayoutManager for now.
*
* #param layoutManager
*/
public PaginationScrollListener(LinearLayoutManager layoutManager) {
this.layoutManager = layoutManager;
}
#Override
public void onScrolled(RecyclerView recyclerView, int dx, int dy) {
super.onScrolled(recyclerView, dx, dy);
int visibleItemCount = layoutManager.getChildCount();
int totalItemCount = layoutManager.getItemCount();
int firstVisibleItemPosition = layoutManager.findFirstVisibleItemPosition();
if (!isLoading() && !isLastPage()) {
if ((visibleItemCount + firstVisibleItemPosition) >= totalItemCount
&& firstVisibleItemPosition >= 0
&& totalItemCount >= getTotalPageCount()) {
loadMoreItems();
}
}
}
protected abstract void loadMoreItems();
public abstract int getTotalPageCount();
public abstract boolean isLastPage();
public abstract boolean isLoading();
}
Adapter
public class PaginationAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
private static final int ITEM = 0;
private static final int LOADING = 1;
private List<Movie> movies;
private Context context;
private boolean isLoadingAdded = false;
public PaginationAdapter(Context context) {
this.context = context;
movies = new ArrayList<>();
}
public List<Movie> getMovies() {
return movies;
}
public void setMovies(List<Movie> movies) {
this.movies = movies;
}
#Override
public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
RecyclerView.ViewHolder viewHolder = null;
LayoutInflater inflater = LayoutInflater.from(parent.getContext());
switch (viewType) {
case ITEM:
viewHolder = getViewHolder(parent, inflater);
break;
case LOADING:
View v2 = inflater.inflate(R.layout.item_progress, parent, false);
viewHolder = new LoadingVH(v2);
break;
}
return viewHolder;
}
#NonNull
private RecyclerView.ViewHolder getViewHolder(ViewGroup parent, LayoutInflater inflater) {
RecyclerView.ViewHolder viewHolder;
View v1 = inflater.inflate(R.layout.item_list, parent, false);
viewHolder = new MovieVH(v1);
return viewHolder;
}
#Override
public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
Movie movie = movies.get(position);
switch (getItemViewType(position)) {
case ITEM:
MovieVH movieVH = (MovieVH) holder;
movieVH.textView.setText(movie.getTitle());
break;
case LOADING:
break;
}
}
#Override
public int getItemCount() {
return movies == null ? 0 : movies.size();
}
#Override
public int getItemViewType(int position) {
return (position == movies.size() - 1 && isLoadingAdded) ? LOADING : ITEM;
}
public void add(Movie mc) {
movies.add(mc);
notifyItemInserted(movies.size() - 1);
}
public void addAll(List<Movie> mcList) {
for (Movie mc : mcList) {
add(mc);
}
}
public void remove(Movie city) {
int position = movies.indexOf(city);
if (position > -1) {
movies.remove(position);
notifyItemRemoved(position);
}
}
public void clear() {
isLoadingAdded = false;
while (getItemCount() > 0) {
remove(getItem(0));
}
}
public boolean isEmpty() {
return getItemCount() == 0;
}
public void addLoadingFooter() {
isLoadingAdded = true;
add(new Movie());
}
public void removeLoadingFooter() {
isLoadingAdded = false;
int position = movies.size() - 1;
Movie item = getItem(position);
if (item != null) {
movies.remove(position);
notifyItemRemoved(position);
}
}
public Movie getItem(int position) {
return movies.get(position);
}
public MovieVH(View itemView) {
super(itemView);
textView = (TextView) itemView.findViewById(R.id.item_text);
}
}
protected class LoadingVH extends RecyclerView.ViewHolder {
public LoadingVH(View itemView) {
super(itemView);
}
}
}
**Getting Api response **
private void callApi() {
apiInterfacePages = ApiClient.getRetrofit().create(APIInterface.class);
Call<CamerasItem> camerasCall = apiInterfacePages.getCameras();
camerasCall.enqueue(new Callback<CamerasItem>() {
#Override
public void onResponse(Call<CamerasItem> call, Response<CamerasItem> response) {
CamerasItem camerasItem = response.body();
itemList = new ArrayList<>();
itemList = camerasItem.getItems();
Log.i("Item", "" + getChannel().getName());
for (int i = 0; i < itemList.size(); i++) {
if (itemList.get(i).getCategory().equals(getChannel().getName())){
if (!itemList.get(i).getUrlMjpeg().endsWith("=mediaRedirect")) {
String videoUrl = itemList.get(i).getUrlMjpeg();
String imageUrl = itemList.get(i).getThumbnail();
String name = itemList.get(i).getName();
String city = itemList.get(i).getCity();
String flag = itemList.get(i).getFlag();
String country= itemList.get(i).getCountry();
modelList.add(new MyModel(videoUrl, imageUrl, name, city, flag,country));
}
}
}
#Override
public void onFailure(Call<CamerasItem> call, Throwable t) {
Log.i("Item", "" + t.getMessage());
}
});
}
So now how to pass to 10 items to recyclerview for the first time and 10 items at each scroll.
You have to set Progressbar inside the activity's xml where Recyclerview is defined.
and loadThumbnail is a function to download thumbnail. it just gives a little delay to scroll down. Now the complete code for the adapter class is as following
public class CamerasAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
private List<MyModel> list;
private Activity mActivity;
private static final int TYPE_VIDEO = 0, TYPE_ADD = 1;
private static final int PAGE_LIMIT = 5;
private int mCurrentLimit = PAGE_LIMIT;
private boolean mIsLoading;
RelativeLayout mLoaderProgress;
public CamerasAdapter(FragmentActivity activity, RelativeLayout loaderLayout) {
mActivity = activity;
mLoaderProgress = loaderLayout;
}
#NonNull
#Override
public RecyclerView.ViewHolder onCreateViewHolder(#NonNull ViewGroup viewGroup, int i) {
View itemView = LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.li_web_cam_view, viewGroup, false);
return new CamsViewHolder(itemView);
}
#Override
public void onBindViewHolder(#NonNull RecyclerView.ViewHolder viewHolder, int i) {
if (mCurrentLimit == (i + 1) && mCurrentLimit <= list.size() && !mIsLoading) {
mLoaderProgress.setVisibility(View.VISIBLE);
mIsLoading = true;
loadThumbnail(0, i + 1);
} else {
//do nothing
}
((CamsViewHolder) viewHolder).onBindData(mActivity, list.get(i), i);
((CamsViewHolder) viewHolder).emptyView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
itemClickListner.onClick(i, ((CamsViewHolder) viewHolder).tvCamName, list.get(i));
}
});
}
private void loadThumbnail(final int count, int position) {
try {
if (count > 2 || position >= list.size()) {
new Handler().postDelayed(new Runnable() {
#Override
public void run() {
mIsLoading = false;
mCurrentLimit = mCurrentLimit + PAGE_LIMIT;
notifyItemChanged(position - count);
mLoaderProgress.setVisibility(View.GONE);
return;
}
}, 2000);
} else {
if (list.get(position) == null) {
loadThumbnail(count, position + 1);
} else {
Glide.with(mActivity).load(list.get(position).getImage_url()).downloadOnly(new SimpleTarget<File>() {
#Override
public void onResourceReady(File resource, GlideAnimation<? super File> glideAnimation) {
loadThumbnail((count + 1), (position + 1));
}
#Override
public void onLoadFailed(Exception e, Drawable errorDrawable) {
loadThumbnail((count + 1), (position + 1));
}
});
}
}
} catch (Exception e) {
e.printStackTrace();
mLoaderProgress.setVisibility(View.GONE);
mIsLoading = false;
}
}
#Override
public int getItemCount() {
return mCurrentLimit <= list.size() ? mCurrentLimit : list.size();
}
public void setData(List<MyModel> dataList) {
this.list = dataList;
notifyDataSetChanged();
}
ItemClickListner itemClickListner;
public void setListener(ItemClickListner listener) {
itemClickListner = listener;
}
ProgressLoadListener progressLoadListener;
public void setProgressLoadListener(ProgressLoadListener listener) {
progressLoadListener = listener;
}
}
code for xml file
<android.support.v7.widget.RecyclerView
android:id="#+id/recycler_view"
android:layout_width="match_parent"
android:visibility="gone"
android:layout_height="match_parent"
android:layout_above="#+id/loader_progress_bar_layout"
android:background="#f5f5f5"
android:layout_gravity="center" />
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentBottom="true"
android:id="#+id/loader_progress_bar_layout"
android:visibility="gone"
android:background="#fff"
>
<ProgressBar
android:id="#+id/progress_bar_loader"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"
android:layout_gravity="center" />
</RelativeLayout>
initialize Recyclerview with adapter
public class Main2Activity extends AppCompatActivity {
RecyclerView recyclerView;
RelativeLayout layoutProgressBar;
CamerasAdapter adapter;
List<Item> itemList;
LinearLayoutManager mLayoutManager;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main2);
layoutProgressBar = findViewById(R.id.loader_progress_bar_layout);
recyclerView = findViewById(R.id.recycler_view);
adapter = new CamerasAdapter(getActivity(), loaderLayout);
mLayoutManager = new LinearLayoutManager(getActivity());
recyclerView.setLayoutManager(mLayoutManager);
recyclerView.setAdapter(adapter);
adapter.setProgressLoadListener(new ProgressLoadListener() {
#Override
public void loadProgressBar() {
layoutProgressBar.setVisibility(View.VISIBLE);
}
});
adapter.setData(setAdaperData());
}
public List<MyModel> setAdaperData(){
List<MyModel> modelList = new ArrayList<>();
/*addItemsto list*/
return modelList;
}
}

Single radio button check uncheck issue in recyclerview

I'm unable to play with Radio Button which is in Recyclerview. Please, check below images to get the problem.
1. First Image
2. Second Image
3. Third Image
4. Fourth Image
What is the problem?
First Image show when this screen initially comes first time. When I select anyone option it will be highlighted in green colour and appropriate radio button get checked that is shown in Second Image.
When I want to select another option, it unchecked the previous selection but not checking the new one i.e shown in Third Image.
When I again click, It get checked which is wrong. It should unchecked previous selection and checked new selection on first click only. i.e shown in Fourth Image.
My Adapter class is like below.
public class PaymentOptionsAdapter extends RecyclerView.Adapter<PaymentOptionsAdapter.ViewHolder> {
Context context;
List<String> listOfPaymentOptions;
int mCheckedPostion = -1;
private boolean isChecked = false;
public PaymentOptionsAdapter(Context context, List<String> listOfPaymentOptions) {
this.context = context;
this.listOfPaymentOptions = listOfPaymentOptions;
}
#Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View view = LayoutInflater.from(context).inflate(R.layout.row_payment_options, parent, false);
ViewHolder viewHolder = new ViewHolder(view);
return viewHolder;
}
#Override
public void onBindViewHolder(final ViewHolder holder, final int position) {
holder.txtOption.setText(listOfPaymentOptions.get(position));
if (mCheckedPostion == position) {
holder.txtOption.setTextColor(context.getResources().getColor(R.color.green_txt));
holder.radioSelect.setChecked(true);
if (position == 0) {
new AppShare(context).setPaymentOption(context.getString(R.string.cod));
} else if (position == 1) {
new AppShare(context).setPaymentOption(context.getString(R.string.payu));
} else if (position == 2) {
new AppShare(context).setPaymentOption(context.getString(R.string.online));
}
} else {
holder.txtOption.setTextColor(context.getResources().getColor(R.color.black));
holder.radioSelect.setChecked(false);
}
holder.layoutContainer.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (!isChecked) {
notifyItemChanged(mCheckedPostion);
mCheckedPostion = position;
notifyItemChanged(mCheckedPostion);
isChecked = true;
} else {
notifyItemChanged(mCheckedPostion);
mCheckedPostion = -1;
notifyItemChanged(position);
isChecked = false;
new AppShare(context).setPaymentOption(null);
}
}
});
holder.radioSelect.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
if (!isChecked) {
notifyItemChanged(mCheckedPostion);
mCheckedPostion = position;
notifyItemChanged(mCheckedPostion);
isChecked = true;
} else {
notifyItemChanged(mCheckedPostion);
mCheckedPostion = -1;
notifyItemChanged(position);
isChecked = false;
new AppShare(context).setPaymentOption(null);
}
}
});
}
#Override
public int getItemCount() {
return listOfPaymentOptions.size();
}
public class ViewHolder extends RecyclerView.ViewHolder {
RelativeLayout layoutContainer;
TextView txtOption;
RadioButton radioSelect;
public ViewHolder(View itemView) {
super(itemView);
layoutContainer = (RelativeLayout) itemView.findViewById(R.id.layoutContainer);
txtOption = (TextView) itemView.findViewById(R.id.txtOption);
radioSelect = (RadioButton) itemView.findViewById(R.id.radioSelect);
txtOption.setTypeface(FontUtils.getInstance(context).getRobotoTypeFace());
}
}
}
row_payment_options.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="#dimen/card_view_height"
android:background="#color/white"
android:orientation="vertical">
<RelativeLayout
android:id="#+id/layoutContainer"
android:layout_width="match_parent"
android:layout_height="wrap_content">
<TextView
android:id="#+id/txtOption"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:paddingLeft="#dimen/large_margin"
android:text="TextView"
android:textColor="#color/black"
android:textSize="#dimen/text_title" />
<RadioButton
android:id="#+id/radioSelect"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_centerVertical="true"
android:checked="false"
android:paddingRight="#dimen/large_margin" />
<View
android:layout_width="match_parent"
android:layout_height="0.5dp"
android:layout_alignParentBottom="true"
android:layout_marginLeft="#dimen/large_margin"
android:layout_marginRight="#dimen/x_large_margin"
android:layout_toLeftOf="#+id/radioSelect"
android:background="#color/gray_border" />
</RelativeLayout>
</RelativeLayout>
In your adapter first add local RadioButton:
private RadioButton lastCheckedRadio;
and change your onBindViewHolder like this and it should work
#Override
public void onBindViewHolder(final ViewHolder holder, final int position) {
holder.txtOption.setText(listOfPaymentOptions.get(position));
holder.radioSelect.setTag(new Integer(position));
if(position == 0 && holder.radioSelect.isChecked())
{
lastCheckedRadio = holder.radioSelect;
mCheckedPostion = 0;
}
holder.layoutContainer.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v)
{
int clickedPos = ((Integer)holder.radioSelect.getTag()).intValue();
if(mCheckedPostion!=position)
{
if(lastCheckedRadio != null)
{
lastCheckedRadio.setChecked(false);
}
lastCheckedRadio = holder.radioSelect;
lastCheckedRadio.setChecked(true);
mCheckedPostion = clickedPos;
if (position == 0) {
new AppShare(context).setPaymentOption(context.getString(R.string.cod));
} else if (position == 1) {
new AppShare(context).setPaymentOption(context.getString(R.string.payu));
} else if (position == 2) {
new AppShare(context).setPaymentOption(context.getString(R.string.online));
}
}
else
lastCheckedRadio = holder.radioSelect;
}
});
holder.radioSelect.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
int clickedPos = ((Integer)holder.radioSelect.getTag()).intValue();
if(holder.radioSelect.isChecked())
{
if(lastCheckedRadio != null)
{
lastCheckedRadio.setChecked(false);
holder.layoutContainer.setFocusable(false);
}
lastCheckedRadio = holder.radioSelect;
lastCheckedRadio.setChecked(true);
mCheckedPostion = clickedPos;
if (position == 0) {
new AppShare(context).setPaymentOption(context.getString(R.string.cod));
} else if (position == 1) {
new AppShare(context).setPaymentOption(context.getString(R.string.payu));
} else if (position == 2) {
new AppShare(context).setPaymentOption(context.getString(R.string.online));
}
}
else
lastCheckedRadio = holder.radioSelect;
}
});
}
I changed my Adapter class like below. Working fine. You can check subrahmanyam boyapati's answer on This Link.
public class PaymentOptionsAdapter extends RecyclerView.Adapter<PaymentOptionsAdapter.ViewHolder> {
Context context;
List<String> listOfPaymentOptions;
private int lastCheckedPosition = -1;
public PaymentOptionsAdapter(Context context, List<String> listOfPaymentOptions) {
this.context = context;
this.listOfPaymentOptions = listOfPaymentOptions;
}
#Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View view = LayoutInflater.from(context).inflate(R.layout.row_payment_options, parent, false);
ViewHolder viewHolder = new ViewHolder(view);
return viewHolder;
}
#Override
public void onBindViewHolder(final ViewHolder holder, final int position) {
holder.txtOption.setText(listOfPaymentOptions.get(position));
holder.radioSelect.setChecked(position == lastCheckedPosition);
if (lastCheckedPosition == position) {
holder.txtOption.setTextColor(context.getResources().getColor(R.color.green_txt));
holder.radioSelect.setChecked(true);
if (position == 0) {
new AppShare(context).setPaymentOption(context.getString(R.string.cod));
} else if (position == 1) {
new AppShare(context).setPaymentOption(context.getString(R.string.payu));
} else if (position == 2) {
new AppShare(context).setPaymentOption(context.getString(R.string.online));
} else {
new AppShare(context).setPaymentOption(null);
}
} else {
holder.txtOption.setTextColor(context.getResources().getColor(R.color.black));
holder.radioSelect.setChecked(false);
}
}
#Override
public int getItemCount() {
return listOfPaymentOptions.size();
}
public class ViewHolder extends RecyclerView.ViewHolder {
RelativeLayout layoutContainer;
TextView txtOption;
RadioButton radioSelect;
public ViewHolder(View itemView) {
super(itemView);
layoutContainer = (RelativeLayout) itemView.findViewById(R.id.layoutContainer);
txtOption = (TextView) itemView.findViewById(R.id.txtOption);
radioSelect = (RadioButton) itemView.findViewById(R.id.radioSelect);
txtOption.setTypeface(FontUtils.getInstance(context).getRobotoTypeFace());
layoutContainer.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
lastCheckedPosition = getAdapterPosition();
notifyItemRangeChanged(0, listOfPaymentOptions.size());
}
});
radioSelect.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
lastCheckedPosition = getAdapterPosition();
notifyItemRangeChanged(0, listOfPaymentOptions.size());
}
});
}
}
}

getFilter()' on a null object reference

i'm trying to implement search on my list view
this is my custom adapter:
public class AllContactsAdapter extends BaseAdapter implements Filterable {
Context context;
ArrayList<Contact> contactList;
ArrayList<Contact> mStringFilterList;
ValueFilter valueFilter;
public AllContactsAdapter(Context context, ArrayList<Contact> list) {
this.context = context;
contactList = list;
mStringFilterList = list;
}
#Override
public int getCount() {
return contactList.size();
}
#Override
public Object getItem(int position) {
return contactList.get(position);
}
#Override
public long getItemId(int position) {
return contactList.get(position).getID();
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
Contact item = contactList.get(position);
if (convertView == null) {
LayoutInflater inflater = (LayoutInflater) context
.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
convertView = inflater.inflate(R.layout.row_name_phone_view, null);
}
TextView name = (TextView) convertView.findViewById(R.id.txtAllFullName);
name.setText(item.getName());
TextView phone = (TextView) convertView.findViewById(R.id.txtAllPhoneNumber);
phone.setText(item.getPhoneNumber());
return convertView;
}
#Override
public Filter getFilter() {
if (valueFilter == null) {
valueFilter = new ValueFilter();
}
return valueFilter;
}
private class ValueFilter extends Filter {
#Override
protected FilterResults performFiltering(CharSequence constraint) {
FilterResults results = new FilterResults();
if (constraint != null && constraint.length() > 0) {
ArrayList<Contact> filterList = new ArrayList<Contact>();
for (int i = 0; i < mStringFilterList.size(); i++) {
if ((mStringFilterList.get(i).getName().toUpperCase())
.contains(constraint.toString().toUpperCase())) {
Contact contact = new Contact(mStringFilterList.get(i)
.getName(), mStringFilterList.get(i)
.getPhoneNumber());
filterList.add(contact);
}
}
results.count = filterList.size();
results.values = filterList;
} else {
results.count = mStringFilterList.size();
results.values = mStringFilterList;
}
return results;
}
#Override
protected void publishResults(CharSequence constraint,
FilterResults results) {
contactList = (ArrayList<Contact>) results.values;
notifyDataSetChanged();
}
}
}
this is my call in main activity:
#Override
public boolean onQueryTextChange(String newText) {
adapter.getFilter().filter(newText);
return false;
}
i'm getting this error:
java.lang.NullPointerException: Attempt to invoke virtual method 'android.widget.Filter com.example.shaka.contactsmanager.AllContactsAdapter.getFilter()' on a null object reference
can you please help me?
The variable adapter is null and you're trying to call the method getFilter() on it.
You need to initialize the adapter variable before using it. I can't be sure of how to do it because I can't see the MainActivity code, but it's definetely this problem.