0

So im working on project which shows memes and it loads em from an API, so now theres a main menu to select categories so when i click on a particular category, the fragment transactions to a new fragment and then it loads memes by a method written in ExploreFragment -

package com.example.memeit;

import static com.android.volley.VolleyLog.TAG;

import android.content.Context;
import android.os.Bundle;

import androidx.annotation.NonNull;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;
import androidx.fragment.app.FragmentTransaction;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;

import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.AbsListView;
import android.widget.Adapter;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast;

import com.android.volley.Request;
import com.android.volley.RequestQueue;
import com.android.volley.Response;
import com.android.volley.VolleyError;
import com.android.volley.toolbox.JsonObjectRequest;
import com.android.volley.toolbox.Volley;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.util.ArrayList;
import java.util.List;

/**
 * A simple {@link Fragment} subclass.
 * Use the {@link ExploreFragment#newInstance} factory method to
 * create an instance of this fragment.
 */
public class ExploreFragment extends Fragment{

    // TODO: Rename parameter arguments, choose names that match
    // the fragment initialization parameters, e.g. ARG_ITEM_NUMBER
    private static final String ARG_PARAM1 = "param1";
    private static final String ARG_PARAM2 = "param2";

    // TODO: Rename and change types of parameters
    private String mParam1;
    private String mParam2;
    public String BASEURL = "https://meme-api.herokuapp.com/gimme/30";
    public TextView tv1_likes;
    public RecyclerView rcv1_explore;
    public Context context;
    public ArrayList<exploreclass> list;
    public boolean isScrolling = false;
    public LinearLayoutManager manager;
    public explore_adapter adapter;
    int currentItems, totalItems, scrolledOutItems;

    public ExploreFragment() {
        // Required empty public constructor
    }

    /**
     * Use this factory method to create a new instance of
     * this fragment using the provided parameters.
     *
     * @param param1 Parameter 1.
     * @param param2 Parameter 2.
     * @return A new instance of fragment ExploreFragment.
     */
    // TODO: Rename and change types and number of parameters
    public static ExploreFragment newInstance(String param1, String param2) {
        ExploreFragment fragment = new ExploreFragment();
        Bundle args = new Bundle();
        args.putString(ARG_PARAM1, param1);
        args.putString(ARG_PARAM2, param2);
        fragment.setArguments(args);
        return fragment;
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        if (getArguments() != null) {
            mParam1 = getArguments().getString(ARG_PARAM1);
            mParam2 = getArguments().getString(ARG_PARAM2);
        }
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container,
                             Bundle savedInstanceState) {
        // Inflate the layout for this fragment
        View view = inflater.inflate(R.layout.fragment_explore, container, false);
        tv1_likes =(TextView) view.findViewById(R.id.tv1_explore);
        list = new ArrayList<>();
        manager = new LinearLayoutManager(getContext());
        adapter = new explore_adapter(list, getContext());
        rcv1_explore =(RecyclerView) view.findViewById(R.id.rcv_explore);
        rcv1_explore.setHasFixedSize(true);
        rcv1_explore.addOnScrollListener(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;
                }
            }

            @Override
            public void onScrolled(@NonNull RecyclerView recyclerView, int dx, int dy) {
                super.onScrolled(recyclerView, dx, dy);

                totalItems = manager.getItemCount();
                currentItems = manager.getChildCount();
                scrolledOutItems = manager.findFirstVisibleItemPosition();


                if(isScrolling && (totalItems == currentItems + scrolledOutItems)) {
                    isScrolling = false;
                    fetchMoreData();
                }
            }
        });

        return view;
    }


    public void ExtractMemes(Context context, String url) {
        RequestQueue queue = Volley.newRequestQueue(context);
        JsonObjectRequest response = new JsonObjectRequest(Request.Method.GET, url, null, new Response.Listener<JSONObject>() {
            @Override
            public void onResponse(JSONObject response) {
                try {
                    JSONArray memes_array = response.getJSONArray("memes");
                    for(int i=0; i<memes_array.length(); i++) {
                        JSONObject memes_object = memes_array.getJSONObject(i);

                        exploreclass class_object = new exploreclass();
                        class_object.setUps(memes_object.getInt("ups"));
                        class_object.setUrl(memes_object.getString("url"));
                        class_object.setPostLink(memes_object.getString("postLink"));
                        list.add(class_object);
                    }
                } catch (JSONException e) {
                    e.printStackTrace();
                }
                rcv1_explore.setLayoutManager(manager);
                rcv1_explore.setAdapter(adapter);
            }
        }, new Response.ErrorListener() {
            @Override
            public void onErrorResponse(VolleyError error) {
                Toast.makeText(getContext(), error.getLocalizedMessage(), Toast.LENGTH_SHORT).show();
            }
        });

        queue.add(response);

    }



    private void fetchMoreData() {

        RequestQueue queue = Volley.newRequestQueue(getContext());
        JsonObjectRequest response = new JsonObjectRequest(Request.Method.GET, BASEURL, null, new Response.Listener<JSONObject>() {
            @Override
            public void onResponse(JSONObject response) {

                try {
                    JSONArray memes_array = response.getJSONArray("memes");
                    for(int i=0; i<memes_array.length(); i++) {
                        JSONObject memes_object = memes_array.getJSONObject(i);

                        exploreclass class_object = new exploreclass();
                        class_object.setUps(memes_object.getInt("ups"));
                        class_object.setUrl(memes_object.getString("url"));
                        class_object.setPostLink(memes_object.getString("postLink"));
                        list.add(class_object);
                        adapter.notifyDataSetChanged();
                        Toast.makeText(getContext(), "Success", Toast.LENGTH_SHORT).show();
                    }
                } catch (JSONException e) {
                    e.printStackTrace();
                }

            }
        }, new Response.ErrorListener() {
            @Override
            public void onErrorResponse(VolleyError error) {
                Toast.makeText(getContext(), error.getLocalizedMessage(), Toast.LENGTH_SHORT).show();
            }
        });

        queue.add(response);

    }

}

so now when i call this method ExtractMemes in another class to load memes after transaction it says -

java.lang.NullPointerException: Attempt to invoke virtual method 'void androidx.recyclerview.widget.RecyclerView.setLayoutManager(androidx.recyclerview.widget.RecyclerView$LayoutManager)' on a null object reference
        at com.example.memeit.ExploreFragment$2.onResponse(ExploreFragment.java:154)
        at com.example.memeit.ExploreFragment$2.onResponse(ExploreFragment.java:137)

this is how i access the method -

if(position == 0){
            FragmentTransaction transaction = getChildFragmentManager().beginTransaction();
            ExploreFragment exploreFragment = new ExploreFragment();
            exploreFragment.list = new ArrayList<>();
            exploreFragment.manager = new LinearLayoutManager(getContext());
            transaction.replace(R.id.framelayout, exploreFragment);
            exploreFragment.ExtractMemes(getContext(), "https://meme-api.herokuapp.com/gimme/HistoryMemes/50");

        }
James Z
  • 12,209
  • 10
  • 24
  • 44
  • You have misread the message. It says you are calling `setLayoutManager()` on a `null` object. This means that the `RecyclerView` is null. Where do you initialize `rcv1_explore`? – Code-Apprentice Dec 08 '21 at 15:56
  • I have initialized the rcv1_explore in the explore fragment after onCreateView, I'm still stuck and can't find what's wrong – Jeet Saluja Dec 09 '21 at 10:51
  • It is difficult for me to give any suggestions because your question is missing information needed to debug this. I suggest setting a break point at the line in Android Studio and debug your code. If you are unfamiliar with the Android Studio debugger, now is a perfect time to learn. – Code-Apprentice Dec 09 '21 at 18:29

0 Answers0