-1

I have the app set up so when I hit a view on the Recycler View the movie image transitions properly to Activity B. Now when I try to populate The information about the object in Activity B (Like plot etc) I get an error saying the what i have in the onBindViewHolder is null. I must be missing Something because The way I had app set up before (All the information on one card) everything was being queried correctly and displayed. It all started happening when i decided to change and send the information to Activity B.

Here is the adapter

public class MoviesAdapter extends RecyclerView.Adapter<MoviesAdapter.MyViewHolder> {

private List<MovieData> moviesList;
private Context context;
private ClickListener clickListener;
ImageLoader imageLoader = AppController.getInstance().getImageLoader();

public MoviesAdapter(Context context, List<MovieData> moviesList) {
    this.moviesList = moviesList;
    this.context = context;
}

public class MyViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
    public TextView title, plot, releaseDate, rating;
    public ImageView thumb;
    public NetworkImageView moviePic;

    public MyViewHolder(View view) {
        super(view);
        view.setOnClickListener(this);
        title = (TextView) view.findViewById(R.id.name);
        plot = (TextView) view.findViewById(R.id.plot);
        releaseDate = (TextView) view.findViewById(R.id.releaseDate);
        rating = (TextView) view.findViewById(R.id.rating);
        thumb = (ImageView) view.findViewById(R.id.thumb);
        moviePic = (NetworkImageView) view.findViewById(R.id.profilePic);
    }

    @Override
    public void onClick(View v) {

        //context.startActivity(new Intent(context,DisplayActivity.class));
        if (clickListener != null) {
            clickListener.itemClicked(v, getAdapterPosition());

            }
        }
    }


@Override
public MyViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
    View itemView = LayoutInflater.from(parent.getContext())
            .inflate(R.layout.movie_row, parent, false);

    return new MyViewHolder(itemView);
}

@Override
public void onBindViewHolder(MyViewHolder holder, int position) {
    MovieData movie = moviesList.get(position);
   holder.title.setText(movie.getTitle());
    holder.plot.setText(movie.getPlot());
    holder.releaseDate.setText(movie.getReleaseDate());

    holder.rating.setText(movie.getRating());
    Float nRating = Float.parseFloat(holder.rating.getText().toString());

    if (nRating > 6.5) {
        holder.thumb.setImageResource(R.drawable.ic_thumbs_up);
    } else {
        holder.thumb.setImageResource(R.drawable.ic_thumbdown);
    }



    holder.moviePic.setImageUrl(movie.getImage(), imageLoader);

}



@Override
public int getItemCount() {
    return moviesList.size();
}


//Interface and method to help with clicks
public interface ClickListener {

    void itemClicked(View view, int position);
}

public void setClickListener(ClickListener clickListener) {
    this.clickListener = clickListener;
}

Here is the mainActivity

public class MainActivity extends AppCompatActivity implements MoviesAdapter.ClickListener {

private static final String TAG = MainActivity.class.getSimpleName();

static final int SETTINGS_INTENT_REPLY = 1;

private MoviesAdapter mAdapter;
private List<MovieData> mData = new ArrayList<>();
private RecyclerView recyclerView;
private GridLayoutManager gridLayoutManager;



@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    //check Sdk Level
    setContentView(R.layout.activity_main);

    recyclerView = (RecyclerView) findViewById(R.id.recycler_view);

    mAdapter = new MoviesAdapter(this, mData);
    mAdapter.setClickListener(this);
    gridLayoutManager = new GridLayoutManager(this,2);
    recyclerView.setLayoutManager(gridLayoutManager);
    recyclerView.setItemAnimator(new DefaultItemAnimator());
    recyclerView.setAdapter(mAdapter);

    refreshMovie();

}



@Override
public void onActivityResult(int settingsRequestCode, int settingsResultcode, Intent resultData) {
    super.onActivityResult(settingsRequestCode, settingsResultcode, resultData);

    if (settingsRequestCode == SETTINGS_INTENT_REPLY) {
        refreshMovie();
    }
}

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    MenuInflater inflater = getMenuInflater();
    inflater.inflate(R.menu.main, menu);
    return true;
}

@Override
public boolean onOptionsItemSelected(MenuItem item) {
    // Handle action bar item clicks here. The action bar will
    // automatically handle clicks on the Home/Up button, so long
    // as you specify a parent activity in AndroidManifest.xml.
    int id = item.getItemId();

    if (id == R.id.action_settings) {
        Intent settingsIntent = new Intent(this, SettingsActivity.class);
        startActivityForResult(settingsIntent, SETTINGS_INTENT_REPLY);
        return true;
    }

    return super.onOptionsItemSelected(item);
}





public void refreshMovie() {

    // Get a reference to the ConnectivityManager to check state of network connectivity
    ConnectivityManager connMgr = (ConnectivityManager)
            this.getSystemService(Context.CONNECTIVITY_SERVICE);

    // Get details on the currently active default data network
    NetworkInfo networkInfo = connMgr.getActiveNetworkInfo();

    // If there is a network connection, fetch data
    if (networkInfo != null && networkInfo.isConnected()) {


        mData.clear();

        networkCall();

    } else {

        mData.clear();

        Snackbar snackbar = Snackbar
                .make(recyclerView, "Network Error", Snackbar.LENGTH_INDEFINITE)
                .setAction("Retry", new View.OnClickListener() {
                    @Override
                    public void onClick(View view) {
                        refreshMovie();
                    }
                });

        snackbar.show();
    }
}

/**
 * Parsing json reponse and passing the data to feed view list adapter
 */
public void parseJsonFeed(JSONObject response) {

    final String POSTER_BEGIN_URL = "http://image.tmdb.org/t/p/w500/";
    try {
        JSONArray feedArray = response.getJSONArray("results");

        for (int i = 0; i < feedArray.length(); i++) {
            JSONObject feedObj = (JSONObject) feedArray.get(i);

            MovieData item = new MovieData();

            item.setTitle(feedObj.getString("original_title"));

            // Image might be null sometimes
            String image = feedObj.isNull("poster_path") ? null : feedObj
                    .getString("poster_path");
            String POSTER_URL = POSTER_BEGIN_URL + image;
            item.setImage(POSTER_URL);
            item.setPlot(feedObj.getString("overview"));
            item.setRating(feedObj.getString("vote_average"));
            item.setReleaseDate(feedObj.getString("release_date"));

            mData.add(item);
        }

        // notify data changes to list adapater
        mAdapter.notifyDataSetChanged();
    } catch (JSONException e) {
        e.printStackTrace();
    }
}

public void networkCall() {

    // We first check for cached request
    Cache cache = AppController.getInstance().getRequestQueue().getCache();

    String order;

    SharedPreferences sharedPrefs =
            PreferenceManager.getDefaultSharedPreferences(this);
    String orderType = sharedPrefs.getString(
            getString(R.string.pref_order_key),
            getString(R.string.pref_most_popular));

    if (orderType.equals(getString(R.string.pref_top_rated))) {
        order = "top_rated";
    } else {
        order = "popular";
    }

    String URL_FEED = "https://api.themoviedb.org/3/movie/" + order + "?api_key=" + BuildConfig.OPEN_MOVIE_API_KEY;

    Cache.Entry entry = cache.get(URL_FEED);
    if (entry != null) {
        // fetch the data from cache
        try {
            String data = new String(entry.data, "UTF-8");
            try {
                parseJsonFeed(new JSONObject(data));
            } catch (JSONException e) {
                e.printStackTrace();
            }
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        }

    } else {
        // making fresh volley request and getting json
        JsonObjectRequest jsonReq = new JsonObjectRequest(Request.Method.GET,
                URL_FEED, null, new Response.Listener<JSONObject>() {

            @Override
            public void onResponse(JSONObject response) {
                VolleyLog.d(TAG, "Response: " + response.toString());
                if (response != null) {
                    parseJsonFeed(response);
                }
            }
        }, new Response.ErrorListener() {

            @Override
            public void onErrorResponse(VolleyError error) {
                VolleyLog.d(TAG, "Error: " + error.getMessage());
            }
        });

        // Adding request to volley request queue
        AppController.getInstance().addToRequestQueue(jsonReq);

    }

}

@Override
public void itemClicked(View view, int position) {

    view.setTransitionName("mImage");

    MovieData movie = mData.get(position);


    Intent intent = new Intent(this, DisplayActivity.class);

    intent.putExtra("MoviePoster", movie.getImage());
    intent.putExtra("Title", movie.getTitle());
    intent.putExtra("rDate", movie.getReleaseDate());
    intent.putExtra("plot", movie.getPlot());
    intent.putExtra("rating", movie.getRating());


    ActivityOptionsCompat optionsCompat = ActivityOptionsCompat.makeSceneTransitionAnimation(this,view, view.getTransitionName());



    getApplicationContext().startActivity(intent,optionsCompat.toBundle());

}

}

Here is the Activity B

public class DisplayActivity extends AppCompatActivity {

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_display);

    ImageLoader imageLoader = AppController.getInstance().getImageLoader();

    TextView nTitle = (TextView) findViewById(R.id.name);

    TextView nDate = (TextView) findViewById(R.id.releaseDate);

    TextView nRating = (TextView) findViewById(R.id.rating);

    TextView nPlot = (TextView) findViewById(R.id.plot);


    NetworkImageView nProfilePic = (NetworkImageView) findViewById(R.id.profilePic);



    // The detail Activity called via intent.  Inspect the intent for data.
    Bundle bundle = getIntent().getExtras();

    if (bundle != null) {


        //intent
        String movieImage = bundle.getString("MoviePoster");

        //intent
        String movieName = bundle.getString("title");

        //intent
        String movieDate = bundle.getString("rDate");

        //intent
        String movieRating = bundle.getString("rating");

        //intent
        String moviePlot = bundle.getString("plot");

        //set views
        nProfilePic.setImageUrl(movieImage, imageLoader);

        nTitle.setText(movieName);

        nDate.setText(movieDate);

        nRating.setText(movieRating);

        nPlot.setText(moviePlot);


    }
}

}

Here is logcat

04-12 14:01:22.349 23413-23413/com.app.sparkimagination.moviesmoviesmovies E/AndroidRuntime: FATAL EXCEPTION: main
                                                                                         Process: com.app.sparkimagination.moviesmoviesmovies, PID: 23413
                                                                                         java.lang.NullPointerException: Attempt to invoke virtual method 'void android.widget.TextView.setText(java.lang.CharSequence)' on a null object reference
                                                                                             at adapter.MoviesAdapter.onBindViewHolder(MoviesAdapter.java:78)
                                                                                             at adapter.MoviesAdapter.onBindViewHolder(MoviesAdapter.java:27)
                                                                                             at android.support.v7.widget.RecyclerView$Adapter.onBindViewHolder(RecyclerView.java:6356)
                                                                                             at android.support.v7.widget.RecyclerView$Adapter.bindViewHolder(RecyclerView.java:6389)
                                                                                             at android.support.v7.widget.RecyclerView$Recycler.tryBindViewHolderByDeadline(RecyclerView.java:5335)
                                                                                             at android.support.v7.widget.RecyclerView$Recycler.tryGetViewHolderForPositionByDeadline(RecyclerView.java:5598)
                                                                                             at android.support.v7.widget.RecyclerView$Recycler.getViewForPosition(RecyclerView.java:5440)
                                                                                             at android.support.v7.widget.RecyclerView$Recycler.getViewForPosition(RecyclerView.java:5436)
                                                                                             at android.support.v7.widget.LinearLayoutManager$LayoutState.next(LinearLayoutManager.java:2224)
                                                                                             at android.support.v7.widget.GridLayoutManager.layoutChunk(GridLayoutManager.java:556)
                                                                                             at android.support.v7.widget.LinearLayoutManager.fill(LinearLayoutManager.java:1511)
                                                                                             at android.support.v7.widget.LinearLayoutManager.onLayoutChildren(LinearLayoutManager.java:595)
                                                                                             at android.support.v7.widget.GridLayoutManager.onLayoutChildren(GridLayoutManager.java:170)
                                                                                             at android.support.v7.widget.RecyclerView.dispatchLayoutStep2(RecyclerView.java:3583)
                                                                                             at android.support.v7.widget.RecyclerView.dispatchLayout(RecyclerView.java:3312)
                                                                                             at android.support.v7.widget.RecyclerView.onLayout(RecyclerView.java:3844)
                                                                                             at android.view.View.layout(View.java:16630)
                                                                                             at android.view.ViewGroup.layout(ViewGroup.java:5437)
                                                                                             at android.widget.FrameLayout.layoutChildren(FrameLayout.java:336)
                                                                                             at android.widget.FrameLayout.onLayout(FrameLayout.java:273)
                                                                                             at android.view.View.layout(View.java:16630)
                                                                                             at android.view.ViewGroup.layout(ViewGroup.java:5437)
                                                                                             at android.widget.FrameLayout.layoutChildren(FrameLayout.java:336)
                                                                                             at android.widget.FrameLayout.onLayout(FrameLayout.java:273)
                                                                                             at android.view.View.layout(View.java:16630)
                                                                                             at android.view.ViewGroup.layout(ViewGroup.java:5437)
                                                                                             at android.support.v7.widget.ActionBarOverlayLayout.onLayout(ActionBarOverlayLayout.java:437)
                                                                                             at android.view.View.layout(View.java:16630)
                                                                                             at android.view.ViewGroup.layout(ViewGroup.java:5437)
                                                                                             at android.widget.FrameLayout.layoutChildren(FrameLayout.java:336)
                                                                                             at android.widget.FrameLayout.onLayout(FrameLayout.java:273)
                                                                                             at android.view.View.layout(View.java:16630)
                                                                                             at android.view.ViewGroup.layout(ViewGroup.java:5437)
                                                                                             at android.widget.LinearLayout.setChildFrame(LinearLayout.java:1743)
                                                                                             at android.widget.LinearLayout.layoutVertical(LinearLayout.java:1586)
                                                                                             at android.widget.LinearLayout.onLayout(LinearLayout.java:1495)
                                                                                             at android.view.View.layout(View.java:16630)
                                                                                             at android.view.ViewGroup.layout(ViewGroup.java:5437)
                                                                                             at android.widget.FrameLayout.layoutChildren(FrameLayout.java:336)
                                                                                             at android.widget.FrameLayout.onLayout(FrameLayout.java:273)
                                                                                             at com.android.internal.policy.PhoneWindow$DecorView.onLayout(PhoneWindow.java:2678)
                                                                                             at android.view.View.layout(View.java:16630)
                                                                                             at android.view.ViewGroup.layout(ViewGroup.java:5437)
                                                                                             at android.view.ViewRootImpl.performLayout(ViewRootImpl.java:2171)
                                                                                             at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:1931)
                                                                                             at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1107)
                                                                                             at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:6013)
                                                                                             at android.view.Choreographer$CallbackRecord.run(Choreographer.java:858)
                                                                                             at android.view.Choreographer.doCallbacks(Choreographer.java:670)
                                                                                             at android.view.Choreographer.doFrame(Choreographer.java:606)
                                                                                             at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:844)
                                                                                             at android.os.Handler.handleCallback(Handler.java:739)
                                                                                             at android.os.Handler.dispatchMessage(Handler.java:95)
                                                                                             at android.os.Looper.loop(Looper.java:148)
                                                                                            at android.app.ActivityThread.main(ActivityThr

Thanks in advanced

movie_row note all the other views in the holder are in activity_display xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
xmlns:tools="http://schemas.android.com/tools"
android:orientation="vertical"
android:tag="cards main container">

<android.support.v7.widget.CardView
    android:id="@+id/card_view"
    xmlns:card_view="http://schemas.android.com/apk/res-auto"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    card_view:cardCornerRadius="2dp"
    card_view:cardElevation="5dp"
    card_view:cardUseCompatPadding="true">

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        >

        <com.android.volley.toolbox.NetworkImageView
            android:id="@+id/profilePic"
            android:transitionName="@string/transition_string"
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_margin="5dp"
            android:layout_weight="1"
            />

    </LinearLayout>

</android.support.v7.widget.CardView>

display xml where all the info is

ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:weightSum="1"
tools:context=".DisplayActivity">

<LinearLayout
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical">

    <com.android.volley.toolbox.NetworkImageView
        android:id="@+id/profilePic"
        android:layout_width="match_parent"
        android:layout_height="262dp"
        android:scaleType="fitCenter"
        android:transitionName="@string/transition_string" />

    <TextView
        android:id="@+id/name"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:orientation="horizontal"
        android:weightSum="2">

        <ImageView
            android:id="@+id/thumb"
            android:layout_width="0dp"
            android:layout_height="75dp"
            android:layout_weight="1"
            tools:src="@drawable/ic_thumbs_up"
            />

        <TextView
            android:id="@+id/rating"
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_gravity="center"
            android:textAlignment="center"
            android:textSize="30dp"
            android:layout_weight="1"
            tools:text="9.0"/>


    </LinearLayout>

    <TextView
        android:id="@+id/plot"
        android:layout_width="match_parent"
        android:layout_height="173dp" />

    <TextView
        android:id="@+id/releaseDate"
        android:layout_width="match_parent"
        android:layout_height="wrap_content" />


</LinearLayout>

Phantômaxx
  • 37,901
  • 21
  • 84
  • 115

1 Answers1

0

The problem here is that is that the MyViewHolder class and onBindViewHolder() method are referring to and calling methods on views which aren't in the movie_row xml. For example trying to find R.id.plot and then in onBindViewholder() trying to call holder.plot.setText(). There is no TextView with the id plot in your movie_row so you get a NullPointerException and crash.

Presumably you previously did have the other Views in there and then removed them when you created your second Activity.

The two main choices to fix this are either to include all the views you're trying to reference in movie_row.xml if you actually want them displayed in the RecyclerView, or if they're not meant to be there then remove them from the MyViewHolder class and the onBindViewHolder() method.

Lewis McGeary
  • 7,692
  • 2
  • 40
  • 46
  • Well the recycler view only handles the grid on Activity A with images only ...I only want those views to inflate and set on Activity B? how can i make that happen? – Jose Burgos Apr 12 '17 at 20:52
  • @JoseBurgos see the last paragraph of my answer; if the RecyclerView is only supposed to show the `NetworkImageView`, then go to your `MyViewHolder` class and `onBindViewHolder()` method and remove all the stuff about the thumb and TextViews which don't exist in the RecyclerView. – Lewis McGeary Apr 12 '17 at 21:03
  • got it to work Thank you so much – Jose Burgos Apr 12 '17 at 21:05