简体   繁体   中英

How can I get selected Item position and Item Details (Model) from RecyclerView?

I have used MVVM, Databinding and Retrofit to develop this app. I have loaded data to RecyclerView. When I will click on any item on RecyclerView, I need the position and details information of this position. Because I will show this information in different activity. How can I do that?

I need item information and position after click on this. It is under View Model.

public void onItemClick(View view){
    Intent innn=new Intent(view.getContext(),HomeActivity.class);
    view.getContext().startActivity(innn);

}

View Model:

package com.nitolniloygroup.operating.viewmodel;

import android.content.Context;
import android.content.Intent;
import android.databinding.BaseObservable;
import android.databinding.Bindable;
import android.view.View;
import android.widget.Toast;

import com.nitolniloygroup.operating.BR;
import com.nitolniloygroup.operating.model.Movie;
import com.nitolniloygroup.operating.view.activity.HomeActivity;
import com.nitolniloygroup.operating.view.activity.LoginActivity;

/**
 * Created by durloveit on 12-Mar-2017.
 */

public class MovieMVVMViewModel extends BaseObservable {

    private Movie mMovie;
    private Context mContext;

    public MovieMVVMViewModel(Movie mMovie, Context mContext) {
        this.mMovie = mMovie;
        this.mContext = mContext;
    }

    @Bindable
    public String getTitle() {
        return mMovie.getTitle();
    }

    public void setTitle(String title) {
        mMovie.setTitle(title);
        notifyPropertyChanged(BR.title);
    }

    @Bindable
    public String getSubtitle() {
        return mMovie.getReleaseDate();
    }

    public void setSubtitle(String subtitle) {
        mMovie.setReleaseDate(subtitle);
        notifyPropertyChanged(BR.subtitle);
    }

    @Bindable
    public String getDescription() {
        return mMovie.getOverview();
    }

    public void setDescription(String description) {
        mMovie.setReleaseDate(description);
        notifyPropertyChanged(BR.description);
    }

public View.OnClickListener onReadMoreClicked(){
    return new View.OnClickListener(){
        @Override
        public void onClick(View view){
            //Toast.makeText(view.getContext(), "Button Read More", Toast.LENGTH_SHORT).show();
            Intent innn=new Intent(view.getContext(),LoginActivity.class);
            view.getContext().startActivity(innn);
        }
    };
}


public void onItemClick(View view){
    Intent innn=new Intent(view.getContext(),HomeActivity.class);
    view.getContext().startActivity(innn);

}



}

Adapter:

package com.nitolniloygroup.operating.view.adapter;

import android.content.Context;
import android.databinding.DataBindingUtil;
import android.support.v7.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.ViewGroup;


import com.nitolniloygroup.operating.databinding.ListItemMoviemvvmBinding;
import com.nitolniloygroup.operating.model.Movie;
import com.nitolniloygroup.operating.viewmodel.MovieMVVMViewModel;

import com.nitolniloygroup.operating.R;

import java.util.List;

/**
 * Created by durloveit on 12-Mar-2017.
 */

public class MovieMVVMAdapter extends RecyclerView.Adapter<MovieMVVMAdapter.BindingHolder>{

    private List<Movie> mMovies;
    private Context mContext;

    public MovieMVVMAdapter(List<Movie> mMovies, Context mContext) {
        this.mMovies = mMovies;
        this.mContext = mContext;
    }

    @Override
    public BindingHolder onCreateViewHolder(ViewGroup parent,int viewType){
        ListItemMoviemvvmBinding binding= DataBindingUtil.inflate(
                LayoutInflater.from(parent.getContext()),
                R.layout.list_item_moviemvvm,parent,false);

        return new BindingHolder(binding);
    }

    @Override
    public void onBindViewHolder(BindingHolder holder,int position){
        ListItemMoviemvvmBinding binding=holder.binding;
        binding.setMoviemvvmVM(new MovieMVVMViewModel(mMovies.get(position),mContext));
    }


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

    public static class BindingHolder extends RecyclerView.ViewHolder{
        private ListItemMoviemvvmBinding binding;

        public BindingHolder(ListItemMoviemvvmBinding binding){
            super(binding.cardviewMovieitem);
            this.binding=binding;
        }
    }
}

XML:

<?xml version="1.0" encoding="utf-8"?>

<layout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto">
    <data>
        <variable
            name="moviemvvmVM"
            type="com.nitolniloygroup.operating.viewmodel.MovieMVVMViewModel"></variable>

    </data>
    <android.support.v7.widget.CardView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:onClick="@{moviemvvmVM::onItemClick}"
        android:id="@+id/cardview_movieitem">

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:gravity="center_vertical"
            android:minHeight="72dp"
            android:orientation="horizontal"

            android:padding="16dp">

        <LinearLayout
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="1"
            android:orientation="vertical">

            <TextView
                android:id="@+id/title"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_gravity="top"
                android:paddingRight="16dp"
                android:textStyle="bold"
                android:text="@{moviemvvmVM.title}"
                android:textSize="16sp" />


            <TextView
                android:id="@+id/subtitle"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:text="@{moviemvvmVM.subtitle}"
                android:paddingRight="16dp"
                />

            <TextView
                android:id="@+id/description"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:maxLines="3"
                android:text="@{moviemvvmVM.description}"
                android:paddingRight="16dp"
                />

        </LinearLayout>

            <Button
                android:id="@+id/button5"
                android:layout_width="0dp"
                android:layout_height="wrap_content"
                android:layout_weight="1"
                android:gravity="right"
                android:onClick="@{moviemvvmVM.onReadMoreClicked}"
                android:text="Read More" />
        </LinearLayout>

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

Here's what I do to pass data between Fragment, Activity or Adapters. I have created a separate ViewModel which is used for data passing.

/**
 * ViewModel used for passing data between different components
 */

public class DataPassingViewModel extends ViewModel {
  private MutableLiveData<Object> mutableLiveData = new MutableLiveData<>();

  public void setData(final Object mObject) {
    mutableLiveData.setValue(mObject);
  }

  public MutableLiveData<Object> getObservable() {
    return mutableLiveData;
  }
}

Initialize it in Activity or Fragment containing LifecycleOwner via

final DataPassingViewModel mDataPassingViewModel = ViewModelProviders.of(this).get(DataPassingViewModel.class);

Observer on the ViewModel

mDataPassingViewModel.getObservable().observe(this, object -> {
      if (object != null) {
        // Do whatever you want
      }
    });

In Adapter/Fragment, initialize the DataPassingViewModel with context of parent activity. For fragment you can get parent context via getActivity() but for adapters you can get parent by passing it via constructor. So, you can create a new instance via -

mDataPassingViewModel =
   ViewModelProviders.of(mActivity).get(DataPassingViewModel.class);

or

mDataPassingViewModel =
      ViewModelProviders.of(getActivity()).get(DataPassingViewModel.class);

To pass data back mDataPassingViewModel.setData(mFileOrFolderTypes.get(position)); . Since setData() accepts generic object, you can pass anything Integer , String or entire class.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM