Загрузка в адаптер из другой коллекции Firestore

152
21 октября 2019, 17:00

В адаптере в методе bind устанавливаю данные из List (во фрагменте загружаю их туда из Firestore). Но еще нужны данные, которые находятся в другой коллекции. Здесь же пытаюсь создать другой запрос к Firestore и вывести данные, он прокрутка интерфейса зависает и иногда данные выводятся в неправильных карточках. Понимаю, что неправильно здесь так делать, но как сделать правильно не понимаю

Adapter

public class MeetingAdapter extends RecyclerView.Adapter<MeetingAdapter.MyViewHolder> {
    private List<Meeting> meetingsList;
    private Context context;
    public MeetingAdapter(List<Meeting> meetingsList, Context context) {
        this.meetingsList = meetingsList;
        this.context = context;
    }
    @NonNull
    @Override
    public MeetingAdapter.MyViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
        View itemView = LayoutInflater.from(context).inflate(R.layout.item_meeting, parent, false);
        return new MeetingAdapter.MyViewHolder(itemView);
    }
    @Override
    public void onBindViewHolder(@NonNull MeetingAdapter.MyViewHolder holder, final int position) {
        bind(holder);
    }
    @Override
    public int getItemCount() {
        return meetingsList.size();
    }
    class MyViewHolder extends RecyclerView.ViewHolder {
        TextView title, dateAdd;
        LinearLayout userLink;
        ImageView photo;
        MyViewHolder(View itemView) {
            super(itemView);
            title = itemView.findViewById(R.id.title);
            dateAdd = itemView.findViewById(R.id.dateAdd);
            userLink = itemView.findViewById(R.id.userLink);
            photo = itemView.findViewById(R.id.photo);
        }
    }
    private void bind(final MeetingAdapter.MyViewHolder holder) {
        final int position = holder.getAdapterPosition();

        DocumentReference docRef = FirebaseFirestore.getInstance().collection("users").document(meetingsList.get(position).getUser() + "");
        docRef.addSnapshotListener(new EventListener<DocumentSnapshot>() {
            @Override
            public void onEvent(@Nullable DocumentSnapshot snapshot, @Nullable FirebaseFirestoreException e) {
                if (e != null) {
                    return;
                }
                if (snapshot != null && snapshot.exists()) {
                    holder.title.setText(snapshot.getData().get("name") + "");
                }
            }
        });

        holder.dateAdd.setText(meetingsList.get(position).getDateAdd());
        holder.userLink.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Log.d("butt", "click " + position);
                MeetingAdapter.this.notifyItemChanged(position, "payload " + position);
                Toast.makeText(context, "userId " + meetingsList.get(position).getUser(), Toast.LENGTH_SHORT).show();
            }
        });
    }
}

Fragment

public class HomeFragment extends Fragment {
    private final int LIMIT_ITEM_LOAD = 5;
    private View item_1, item_2, item_3, item_4, item_5;
    private SwipeRefreshLayout swipeRefresh;
    private RotateLoading loading;

    private RecyclerView recyclerView;
    private LinearLayoutManager linearLayoutManager;
    private DocumentSnapshot lastVisible;
    private boolean isScrolling;
    private boolean isLastItemReached;
    private List<Meeting> list;
    private MeetingAdapter adapter;

    @Nullable
    @Override
    public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        View view = inflater.inflate(R.layout.fragment_home, container, false);
        item_1 = getActivity().findViewById(R.id.item_1);
        item_2 = getActivity().findViewById(R.id.item_2);
        item_3 = getActivity().findViewById(R.id.item_3);
        item_4 = getActivity().findViewById(R.id.item_4);
        item_5 = getActivity().findViewById(R.id.item_5);
        loading = getActivity().findViewById(R.id.loading);
        BottomNavigationView navigation = getActivity().findViewById(R.id.navigation);
        navigation.getMenu().getItem(0).setChecked(true);
        setBorderItemSelected(item_1);
        Toolbar toolbar = view.findViewById(R.id.toolbar);
        ((AppCompatActivity)getActivity()).setSupportActionBar(toolbar);
        ((AppCompatActivity)getActivity()).getSupportActionBar().setDisplayShowTitleEnabled(false);
        toolbar.setTitle("Лента событий");
        setHasOptionsMenu(true);

        recyclerView = view.findViewById(R.id.recyclerView);
        linearLayoutManager = new LinearLayoutManager(getContext());
        recyclerView.setLayoutManager(linearLayoutManager);
        swipeRefresh = view.findViewById(R.id.swipeRefresh);
        swipeRefresh.setColorSchemeResources(
                R.color.orange_300,
                R.color.pink_300,
                R.color.green_300,
                R.color.blue_300);
        swipeRefresh.setOnRefreshListener(refreshListener);
        loading.start();
        getDataFirebase();
        recyclerView.addOnScrollListener(onScrollListener);
        return view;
    }

    private SwipeRefreshLayout.OnRefreshListener refreshListener = new SwipeRefreshLayout.OnRefreshListener() {
        @Override
        public void onRefresh() {
            new Handler().postDelayed(new Runnable() {
                @Override public void run() {
                    swipeRefresh.setRefreshing(true);
                    refreshPage();
                    swipeRefresh.setRefreshing(false);
                }
            },1000);
        }
    };

    private void getDataFirebase() {
        Query query = FirebaseFirestore.getInstance()
                .collection("meetings")
                .orderBy("id", Query.Direction.DESCENDING)
                .limit(LIMIT_ITEM_LOAD);
        query.get().addOnCompleteListener(new OnCompleteListener<QuerySnapshot>() {
            @Override
            public void onComplete(@NonNull Task<QuerySnapshot> task) {
                if (task.isSuccessful()) {
                    list = new ArrayList<>();
                    for (DocumentSnapshot document : task.getResult()) {
                        Meeting meeting = document.toObject(Meeting.class);
                        list.add(meeting);
//                        adapter.notifyItemInserted(list.size());
                    }
                    adapter = new MeetingAdapter(list, getContext());
                    recyclerView.setAdapter(adapter);
                    lastVisible = task.getResult().getDocuments().get(task.getResult().size() - 1);
                    Toast.makeText(getContext(), "Загружено. lastVisible = " + lastVisible.get("id"), Toast.LENGTH_SHORT).show();
                    loading.stop();
                    recyclerView.addOnScrollListener(onScrollListener);
                }
            }
        });
    }

    private void refreshPage() {
        isLastItemReached = false;
        Query query = FirebaseFirestore.getInstance()
                .collection("meetings")
                .orderBy("id", Query.Direction.DESCENDING)
                .limit(LIMIT_ITEM_LOAD);
        query.get().addOnCompleteListener(new OnCompleteListener<QuerySnapshot>() {
            @Override
            public void onComplete(@NonNull Task<QuerySnapshot> task) {
                if (task.isSuccessful()) {
                    list.clear();
                    for (DocumentSnapshot document : task.getResult()) {
                        Meeting meeting = document.toObject(Meeting.class);
                        list.add(meeting);
                    }
                    adapter = new MeetingAdapter(list, getContext());
                    recyclerView.setAdapter(adapter);
//                    adapter.notifyDataSetChanged();
                    lastVisible = task.getResult().getDocuments().get(task.getResult().size() - 1);
                    Toast.makeText(getContext(), "Обновление завершено. lastVisible = " + lastVisible.get("id")
                            + " / " + isScrolling
                            + " / " + isLastItemReached, Toast.LENGTH_SHORT).show();
                    recyclerView.addOnScrollListener(onScrollListener);
                }
            }
        });
    }

    private RecyclerView.OnScrollListener onScrollListener = new RecyclerView.OnScrollListener() {
        @Override
        public void onScrollStateChanged(@NonNull RecyclerView recyclerView, int newState) {
            super.onScrollStateChanged(recyclerView, newState);
            if (newState == AbsListView.OnScrollListener.SCROLL_STATE_TOUCH_SCROLL) {
                isScrolling = true;
//                Toast.makeText(getContext(), "Крутим", Toast.LENGTH_SHORT).show();
            }
        }
        @Override
        public void onScrolled(@NonNull RecyclerView recyclerView, int dx, int dy) {
            super.onScrolled(recyclerView, dx, dy);
            int firstVisibleItem = linearLayoutManager.findFirstVisibleItemPosition();
            int visibleItemCount = linearLayoutManager.getChildCount();
            int totalItemCount = linearLayoutManager.getItemCount();
            Log.d("Ok","firstVisibleItem = " + firstVisibleItem);
            Log.d("Ok","visibleItemCount = " + visibleItemCount);
            Log.d("Ok","totalItemCount = " + totalItemCount);
            if (isScrolling && (firstVisibleItem + visibleItemCount == totalItemCount) && !isLastItemReached) {
                isScrolling = false;
                Query nextQuery = FirebaseFirestore.getInstance()
                        .collection("meetings")
                        .orderBy("id", Query.Direction.DESCENDING)
                        .startAfter(lastVisible)
                        .limit(LIMIT_ITEM_LOAD);
                nextQuery.get().addOnCompleteListener(new OnCompleteListener<QuerySnapshot>() {
                    @Override
                    public void onComplete(@NonNull Task<QuerySnapshot> task) {
                        for (DocumentSnapshot document : task.getResult()) {
                            Meeting meeting = document.toObject(Meeting.class);
                            list.add(meeting);
                        }
                        adapter.notifyDataSetChanged();
                        if (task.getResult().size() < LIMIT_ITEM_LOAD) {
                            isLastItemReached = true;
                            Toast.makeText(getContext(), "Конец списка. lastVisible = " + lastVisible.get("id"), Toast.LENGTH_SHORT).show();
                        } else {
                            lastVisible = task.getResult().getDocuments().get(task.getResult().size() - 1);
                            Toast.makeText(getContext(), "Подгрузка завершена. lastVisible = " + lastVisible.get("id"), Toast.LENGTH_SHORT).show();
                        }

                    }
                });
            }
        }
    };

    @Override
    public boolean onOptionsItemSelected(MenuItem item) {
        switch (item.getItemId()) {
            case R.id.action_filtration:
                //
                break;
            default:
                break;
        }
        return true;
    }

    public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
        inflater.inflate(R.menu.toolbar_home, menu);
        super.onCreateOptionsMenu(menu, inflater);
    }

    public void setBorderItemSelected(View view) {
        item_1.setBackgroundColor(getResources().getColor(android.R.color.transparent));
        item_2.setBackgroundColor(getResources().getColor(android.R.color.transparent));
        item_3.setBackgroundColor(getResources().getColor(android.R.color.transparent));
        item_4.setBackgroundColor(getResources().getColor(android.R.color.transparent));
        item_5.setBackgroundColor(getResources().getColor(android.R.color.transparent));
        view.setBackgroundColor(getResources().getColor(R.color.white));
    }
}
READ ALSO
jQuery load + Spring + Thymeleaf. Подгрузка файлов

jQuery load + Spring + Thymeleaf. Подгрузка файлов

Есть файл, допустим, generalhtml:

161
как найти значение в хеш таблице(словаре)?

как найти значение в хеш таблице(словаре)?

Сначала я ввожу словами числаЗатем на вход программе подаётся значение N — количество записей, которые необходимо обработать Следующие...

120
Изменение имени класса java [закрыт]

Изменение имени класса java [закрыт]

Как можно изменить имя класса из главного метода?

171
отсутствует, не заполняется flowExecutionUrl

отсутствует, не заполняется flowExecutionUrl

Делаю приложение используя Spring MVC и Spring Web Flow, сделав некий flow я могу попасть на него используя ${flowExecutionUrl} в JSP файле, но из-за некой, невиданной...

120