I have a Imageview its load image from Firebase Database url with Picasso Image loader. I wish to hide imageview when firebase database url is empty. How to set Imageview setVisibility gone in that time.
My code is
LoadData(categoryId);
}
private void LoadData(String categoryId) {
options = new FirebaseRecyclerOptions.Builder<TrollModel>().setQuery(MCC,TrollModel.class).build();
adapter = new FirebaseRecyclerAdapter<TrollModel, TrollViewHolder>(options) {
#Override
protected void onBindViewHolder(#NonNull TrollViewHolder trollViewHolder, int i, #NonNull TrollModel trollModel) {
trollViewHolder.thrillername.setText(trollModel.getTitle());
Picasso.get().load(trollModel.getImage())
.into(trollViewHolder.thrillersimage);
trollViewHolder.setItemClickListner(new ItemClickListner() {
#Override
public void onClick(View view, int position, boolean isLongClick) {
Intent detailsIntent = new Intent(TrollActivity.this, TrollDetailActivity.class);
detailsIntent.putExtra("CategoryId", adapter.getRef(position).getKey());
startActivity(detailsIntent);
}
});
}
#NonNull
#Override
public TrollViewHolder onCreateViewHolder(#NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.troll_items, parent, false);
return new TrollViewHolder(v);
}
};
adapter.startListening();
recyclerView.setAdapter(adapter);
}
}
There is setVisibility() funciton for every View in android. You can find this if you google it in right way.
Refer below code to solve your problem.
if (trollModel.getImage().isEmpty()) {
trollViewHolder.thrillersimage.setVisibility(View.GONE);
} else {
trollViewHolder.thrillersimage.setVisibility(View.VISIBLE);
Picasso.get().load(trollModel.getImage())
.into(trollViewHolder.thrillersimage);
}
Related
My Recyclerview is filled with a list containing links to images. But the images can change (let's say the user can draw something on them), but the link to the image itself does not change. I need to make it so that when the image changes, it is also drawn again in the recycler.
notifyDataSetChanged() does not work in this case, apparently because it reacts to changes in the sheet, and in fact there are no changes in the sheet itself, the links are the same in it. But the images are changed by links.
Maybe somehow you can push the recycler so that it is updated or draws items again?
My Activity:
public class MyDrawing extends Fragment {
private RecyclerView recyclerView;
private RecyclerViewAdapter recyclerViewAdapter;
private View root;
private TextView text;
public MyDrawing() {
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
root = inflater.inflate(R.layout.fragment_my_drawing, container, false);
recyclerView = root.findViewById(R.id.recyclerViewMyDrawing);
text = root.findViewById(R.id.text);
List<CacheImageModel> cacheImageModels = getCacheImageByState();
recyclerViewAdapter = new RecyclerViewAdapter(cacheImageModels, getContext());
recyclerView.setHasFixedSize(true);
recyclerView.setLayoutManager(new GridLayoutManager(getContext(), 2));
recyclerView.setAdapter(recyclerViewAdapter);
recyclerViewAdapter.notifyDataSetChanged();
return root;
}
My Adapter:
public class RecyclerViewAdapter extends RecyclerView.Adapter<RecyclerViewAdapter.ViewHolder> {
private List<CacheImageModel> cacheImageModels;
private Context context;
private String imgUrl;
private int imageKey;
private String category;
private String nameImage;
private ProgressBar progressBarItem;
public RecyclerViewAdapter(List<CacheImageModel> cacheImageModels, Context context) {
this.cacheImageModels = cacheImageModels;
this.context = context;
}
#NonNull
#Override
public ViewHolder onCreateViewHolder(#NonNull ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext())
.inflate(R.layout.recycler_view_item, parent, false);
return new ViewHolder(view);
}
#Override
public void onBindViewHolder(#NonNull ViewHolder holder, int position) {
imgUrl = cacheImageModels.get(position).getImageCacheUrl();
nameImage = cacheImageModels.get(position).getName();
category = cacheImageModels.get(position).getCategory();
imageKey = cacheImageModels.get(position).getImageKey();
holder.progressBarItem.setVisibility(View.VISIBLE);
holder.relativeLayout.setLayoutParams(new FrameLayout.LayoutParams(MyApp.getScreenWidth(context) / 2,
MyApp.getScreenWidth(context) / 2));
Glide.with(context)
.load(imgUrl)
.listener(new RequestListener<Drawable>() {
#Override
public boolean onLoadFailed(#Nullable GlideException e, Object model, Target<Drawable> target, boolean isFirstResource) {
return false;
}
#Override
public boolean onResourceReady(Drawable resource, Object model, Target<Drawable> target, DataSource dataSource, boolean isFirstResource) {
holder.progressBarItem.setVisibility(View.GONE);
return false;
}
})
.into(holder.image);
holder.image.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
int posit = holder.getAdapterPosition();
if (posit < 0 || posit >= cacheImageModels.size()) {
Log.d("POSITION", "Number postition " + posit + " its error");
} else {
String urlImagePosition = cacheImageModels.get(posit).getImageCacheUrl();
String namePosition = cacheImageModels.get(posit).getName();
String categoryPosition = cacheImageModels.get(posit).getCategory();
int imageKeyPosition = cacheImageModels.get(posit).getImageKey();
Uri uri = ContentUris.withAppendedId(MCDataContract.CONTENT_URI, imageKeyPosition);
Intent intent = new Intent(v.getContext(),
ColoringActivity.class);
intent.putExtra("urlImagePosition", urlImagePosition);
intent.putExtra("nameImage", namePosition);
intent.putExtra("keyPosition", imageKeyPosition);
intent.putExtra("categoryPosition", categoryPosition);
intent.setData(uri);
v.getContext().startActivity(intent);
}
}
});
}
#Override
public long getItemId(int position) {
return super.getItemId(position);
}
#Override
public int getItemCount() {
return cacheImageModels.size();
}
public class ViewHolder extends RecyclerView.ViewHolder {
private ImageView image;
private ProgressBar progressBarItem;
private RelativeLayout relativeLayout;
private CardView cardView;
public ViewHolder(#NonNull View itemView) {
super(itemView);
image = itemView.findViewById(R.id.imageView);
progressBarItem = itemView.findViewById(R.id.progressBarItem);
relativeLayout = itemView.findViewById(R.id.parentItem);
cardView = itemView.findViewById(R.id.cardView);
}
}
}
notifyDataSetChanged() is most likely working as planned. You can set a breakpoint in your view holder binding code to check this.
It is more likely that Glide is pulling the cached versions of the images. You will need a way to get Glide to ignore what's in cache and reload from the URL.
This post addresses the same issue and may be of help to you.
I have built a note-taking app with Room, ViewModel, LiveData, and RecyclerView using this tutorial. Everything is working very well. However, when I began to implement the ability to select an image for each note, the RecyclerView became really laggy and slow as more notes with images were added.
After some research, I discovered that using image loading frameworks like Glide and Picasso can make loading faster. So, I tried using Glide to load images from a Uri into the RecyclerView items.
NoteAdapter.java
public class NoteAdapter extends ListAdapter<Note, NoteAdapter.NoteHolder> {
Context context;
public NoteAdapter() {
super(DIFF_CALLBACK);
}
private static final DiffUtil.ItemCallback<Note> DIFF_CALLBACK = new DiffUtil.ItemCallback<Note>() {
#Override
public boolean areItemsTheSame(#NonNull Note note, #NonNull Note t1) {
return note.getId() == t1.getId();
}
#Override
public boolean areContentsTheSame(#NonNull Note note, #NonNull Note t1) {
return note.getTitle().equals(t1.getTitle()) && note.getDescription().equals(t1.getDescription()) && note.getImageUri().equals(t1.getImageUri());
}
};
private OnItemClickListener listener;
#NonNull
#Override
public NoteHolder onCreateViewHolder(#NonNull ViewGroup viewGroup, int i) {
View itemView = LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.note_item, viewGroup, false);
return new NoteHolder(itemView);
}
#Override
public void onBindViewHolder(#NonNull NoteHolder noteHolder, int i) {
Note currentNote = getItem(i);
noteHolder.textViewTitle.setText(currentNote.getTitle());
noteHolder.textViewDescription.setText(currentNote.getDescription());
Glide.with(context)
.load(Uri.parse(currentNote.getImageUri()))
.fit()
.centerCrop()
.into(noteHolder.image);
}
public Note getNoteAt(int position) {
return getItem(position);
}
class NoteHolder extends RecyclerView.ViewHolder {
private TextView textViewTitle;
private TextView textViewDescription;
private ImageView image;
public NoteHolder(#NonNull View itemView) {
super(itemView);
textViewTitle = itemView.findViewById(R.id.text_view_title);
textViewDescription = itemView.findViewById(R.id.text_view_description);
image = itemView.findViewById(R.id.image_view);
itemView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
int position = getAdapterPosition();
if (listener != null && position != RecyclerView.NO_POSITION) {
listener.onItemClick(getItem(position));
}
}
});
}
}
public interface OnItemClickListener {
void onItemClick(Note note);
}
public void setOnItemClickListener(OnItemClickListener listener) {
this.listener = listener;
}
}
However, Android Studio gives me the following error - Cannot resolve symbol 'context'. My question is, what context should I be passing in for this argument? Also, any other suggestions to make the RecyclerView faster when loading images would be greatly appreciated. Thanks!
PS - I am not a professional whatsoever, and only program as a hobby, so I apologize for any misused terms.
you need to define global variable
Context context ;
and change your code to the following :
public class NoteAdapter extends ListAdapter<Note, NoteAdapter.NoteHolder> {
....
Context context;
#NonNull
#Override
public NoteHolder onCreateViewHolder(#NonNull ViewGroup viewGroup, int i) {
context = viewGroup.getContext();
View itemView = LayoutInflater.from(context).inflate(R.layout.note_item, viewGroup, false);
return new NoteHolder(itemView);
}
#Override
public void onBindViewHolder(#NonNull NoteHolder noteHolder, int i) {
Note currentNote = getItem(i);
noteHolder.textViewTitle.setText(currentNote.getTitle());
noteHolder.textViewDescription.setText(currentNote.getDescription());
Glide.with(context)
.load(Uri.parse(currentNote.getImageUri()))
.fit()
.centerCrop()
.into(noteHolder.image);
}
....
}
I am having trouble showing images that I collected from a website into a recycle view. I first got the image urls using jsoup. Then I added the urls in a list called imgURLS. Now I want to show those images in gridview that has recycle view. The code I have no errors but the images are not showen when I run my android project. Its just blank. Here is some of my code
MAINACTIVITY.JAVA
#Override
protected void onCreate(Bundle savedInstanceState) {
setTheme(R.style.AppTheme);
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
new URLcollector().execute();
imageView = findViewById(R.id.imageView);
//setBKG = findViewById(R.id.setBKG);
rvMain = findViewById(R.id.rvMain);
// can add another parameter here like text
MyAdapter adapter = new MyAdapter(imgURLS);
rvMain.setLayoutManager(new GridLayoutManager(MainActivity.this, 2));
rvMain.setAdapter(adapter);
}
then still in mainactivity.java
public class MyAdapter extends RecyclerView.Adapter<MyViewHolder> {
// String[] companyList;
List<String> logoList;
ImageView currentView;
Bitmap imgBitmaps;
public MyAdapter( List<String> logoList) {
// this.companyList = companyList;
this.logoList = logoList;
}
#Override
public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.recycler_item, parent, false);
MyViewHolder viewHolder = new MyViewHolder(v);
return viewHolder;
}
#Override
public void onBindViewHolder(MyViewHolder holder, int position) {
// load image from picasso and then
Context context = holder.logo.getContext(); //<----- Add this line
Picasso.with(context).load(imgURLS.get(position)).into(holder.logo);
}
#Override
public int getItemCount() {
return logoList.size();
}
}
My questions are
1) Am I using Picasso correctly?
2) Why did I not be able to see the images(keep in mind visible is on in xml)?
Let me know if I need to provide more of my code.
#Override
public void onBindViewHolder(MyViewHolder holder, final int position) {
// load image from picasso and then pass it to set Image
Picasso.with(MainActivity.this)
.load(logoList.get(position))
.placeholder(R.mipmap.ic_launcher) // optional
.error(R.mipmap.ic_launcher) //if error
.into(holder.logo);
holder.logo.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Toast.makeText(MainActivity.this, "This is: " , Toast.LENGTH_SHORT).show();
}
});
// holder.name.setText(companyList[position]);
}
If your url is correct. try something like this and don't forget to set INTERNT permission in Manifest.
<uses-permission android:name="android.permission.INTERNET"/>
I am having trouble with populating my Firebase recycler adapter. What I want to do in the end is that a user searches for a name and the result from the database will populate the recyclerView.
The database structure looks like this:
The code to populate looks like this, this is all in onCreate():
Query mQuery = FirebaseDatabase.getInstance().getReference().orderByChild("users");
FirebaseRecyclerOptions<Users> options =
new FirebaseRecyclerOptions.Builder<Users>()
.setQuery(mQuery, Users.class)
.build();
mAdapter = new FirebaseRecyclerAdapter<Users, UsersViewHolder>(options) {
#NonNull
#Override
public UsersViewHolder onCreateViewHolder(#NonNull ViewGroup parent, int viewType) {
View view = LayoutInflater.from(parent.getContext())
.inflate(R.layout.user_single_layout, parent, false);
return new UsersViewHolder(view);
}
#Override
protected void onBindViewHolder(#NonNull UsersViewHolder holder, int position, #NonNull Users model) {
holder.setName(model.getFirstName());
}
};
mUserList.setAdapter(mAdapter);
Right now I just want it to populate with all the users in the database but nothing seems to be populated.
mUserList is a recyclerView.
This is the UsersViewHolder class:
public static class UsersViewHolder extends RecyclerView.ViewHolder {
View mView;
TextView mUsername;
UsersViewHolder(View itemView) {
super(itemView);
mView = itemView;
mUsername = mView.findViewById(R.id.user_single_name);
}
public void setName(String name) {
mUsername.setText(name);
}
}
To solve this, change the following line of code:
Query mQuery = FirebaseDatabase.getInstance().getReference().orderByChild("users");
with:
Query mQuery = FirebaseDatabase.getInstance().getReference()
.child("users")
.orderByChild("first_name");
You are missing a child. Don't also forget to start listening for changes:
#Override
protected void onStart() {
super.onStart();
mAdapter.startListening();
}
And also to stop listening when not needed.
#Override
protected void onStop() {
super.onStop();
if( mAdapter!= null) {
mAdapter.stopListening();
}
}
Use that way. Follow my code for yourself.
FirebaseRecyclerOptions<Data> options=
new FirebaseRecyclerOptions.Builder<Data>()
.setQuery(mIncomeDatabase,Data.class)
.setLifecycleOwner(this)
.build();
FirebaseRecyclerAdapter<Data, MyViewHolder> firebaseRecyclelerAdapter = new FirebaseRecyclerAdapter<Data, MyViewHolder>(options) {
#NonNull
#Override
public MyViewHolder onCreateViewHolder(#NonNull ViewGroup parent, int viewType) {
return new MyViewHolder(LayoutInflater.from(parent.getContext()).inflate(R.layout.income_recycler_data,parent,false));
}
#Override
protected void onBindViewHolder(#NonNull MyViewHolder holder, int position, #NonNull Data model) {
holder.setName(model.getName());
holder.setAmount(model.getAmount());
holder.setType(model.getType());
holder.setNote(model.getNote());
holder.setAmount(model.getAmount());
holder.setDate(model.getDate());
}
};
recyclerView.setAdapter(firebaseRecyclelerAdapter);
Given below is my Firebase Schema:
Book {
Book-1: {title, author}
Book-2: {title, author}
Book-3: {title, author}
Book-4: {title, author}
}
I have listed them in RecyclerView and populating through FirebaseRecyclerAdapter. The code for the same is given below:
final DatabaseReference ref = FirebaseDatabase.getInstance().getReference("Book");
firebaseRecyclerAdapter = new FirebaseRecyclerAdapter<Book, BookListHolder>(
Book.class,
R.layout.simple_book_vertical_list,
BookListHolder.class,
ref) {
#Override
protected void populateViewHolder(BookListHolder viewHolder, Book model, int position) {
viewHolder.setBookTitle(model.getTitle());
viewHolder.setBookAuthor(model.getAuthor());
}
};
Now, after clicking the view, I want to show the data from the view that is clicked, i.e. their title and author.
What do I have to do?
Set on click listener:
#Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
ViewHolder viewHolder = super.onCreateViewHolder(parent, viewType);
viewHolder.itemView.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String key = firebaseRecyclerAdapter.getRef(mRecycler.getChildLayoutPosition(v)).getKey();
// do your magic here
}
});
return viewHolder;
}