Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
125 views
in Technique[技术] by (71.8m points)

java - Snapshot listener returning empty snapshot when I open the fragment again

I have a fragment in an activity that uses Firestore snapshot listener. When I first start the fragment, it works fine. But then if I navigate to another fragment and return, I get an empty snapshot. How do I get it to fetch the snapshot properly again?

Here is the query with the listener registration:

private void setupRecyclerView() {
    if (mealplanRecycler == null) {
        mealplanRecycler = mealplanView.findViewById(R.id.mealplan_recycler);
        LinearLayoutManager linearLayoutManager = new LinearLayoutManager(mealplanContext);
        linearLayoutManager.setOrientation(LinearLayoutManager.VERTICAL);
        mealplanRecycler.setHasFixedSize(true);
        mealplanRecycler.setLayoutManager(linearLayoutManager);
    }
    getMealplans();
}

private void getMealplans() {
        String userId = (bundle != null && bundle.containsKey("userId")) ? bundle.getString("userId") : "";
        Query mealplanQuery = firebaseFirestore.collection("Meal_Plans").whereEqualTo("userId", userId).orderBy("timeOfCreation", Query.Direction.DESCENDING);
        registration = mealplanQuery.addSnapshotListener((value, error) -> {
            toolbarProgressbar.setVisibility(View.GONE);
            mealplanArrayList = new ArrayList<>();
            if (error == null && value != null) {
                for (QueryDocumentSnapshot document : value) {
                    Mealplan mealplan = document.toObject(Mealplan.class);
                    Mealplan updatedmealplan = updateTime(mealplan);
                    mealplanArrayList.add(updatedmealplan);
                    if (mealplanArrayList.size() > 0) {
                        tvAddMealplan.setVisibility(View.GONE);
                        ivAddmealplan.setVisibility(View.GONE);
                    }
                }
                if (mealPlanAdapter != null) {
                    mealPlanAdapter.setItems(mealplanArrayList);
                    mealPlanAdapter.notifyDataSetChanged();
                } else {
                    String planId = (bundle != null && bundle.containsKey("planId")) ? bundle.getString("planId") : "none";
                    mealPlanAdapter = new MealPlanAdapter(mealplanContext, mealplanArrayList, planId);
                    mealplanRecycler.setAdapter(mealPlanAdapter);
                }
                mealPlanAdapter.setEditMealplanListener(this::onButtonPressed);
            } else {
                Log.d(TAG, "error is not null: " + Objects.requireNonNull(error).getLocalizedMessage());
                toolbarProgressbar.setVisibility(View.GONE);
                tvAddMealplan.setVisibility(View.GONE);
            }
        });
    }

And this is how I am creating the fragment in Main Activity:

MealplanFragment fragment = new MealplanFragment();
FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction().setCustomAnimations(R.anim.enter_from_right, R.anim.exit_to_right, R.anim.enter_from_right, R.anim.exit_to_right).replace(R.id.frame_container, fragment, null);
            fragmentTransaction.commit();
question from:https://stackoverflow.com/questions/65648505/snapshot-listener-returning-empty-snapshot-when-i-open-the-fragment-again

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

A fragment's onCreateView is called only once when the fragment's view is being created. From then on it will be called again only if the view is destroyed and needs to be recreated. It is what function onCreate is for an Activity.

So, when you switch between fragments it is not called. The solution is to place the listener registration code in a function that will be called when switching fragments.

You can try onHiddenChanged function:

@Override
public void onHiddenChanged(boolean hidden) {
    super.onHiddenChanged(hidden);
    if (hidden) {    
    
    } 
    else {

    }
}

or

@Override
public void setUserVisibleHint(boolean isVisibleToUser) {
    super.setUserVisibleHint(isVisibleToUser);
    if (isVisibleToUser) {
    
    } else {
     
    }
}

The above are deprecated in API level 28. So, you can also try setMenuVisibility:

 @Override
 public void setMenuVisibility(boolean isvisible) {
    super.setMenuVisibility(isvisible);
    if (isvisible){
        Log.d("Viewpager", "fragment is visible ");
    }else {
        Log.d("Viewpager", "fragment is not visible ");
    }
}

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...