嵌套的 RecyclerView 处理 onClick
Nested RecyclerView handling onClick
我有一个片段,它有一个嵌套的 RecyclerView 来显示产品列表。我根据 mmlooloo 的解决方案实现了这一点:How to create scrollable page of carousels in Android?
这是我的片段,我在其中调用了 MainRecyclerProductAdapter
public class CashSaleFragment 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";
private static final String TAG = "MainActivity";
private UserPreference userPreference = new UserPreference();
int numOfRows = 11;
int numOfColumns = 8;
public int layout = 1; // 0-list_icon 1-list 2-grid_icon 3-grid
public List<Product> listProduct, listProductFilter;
private DatabaseHelper db;
private RecyclerView mRecyclerView;
private LinearLayoutManager mLayoutManager;
View view;
Activity activity;
// TODO: Rename and change types of parameters
private String mParam1;
private String mParam2;
private OnFragmentInteractionListener mListener;
public CashSaleFragment() {
// 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 CashSaleFragment_old.
*/
// TODO: Rename and change types and number of parameters
public static CashSaleFragment newInstance(String param1, String param2) {
CashSaleFragment fragment = new CashSaleFragment();
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, final ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
view = inflater.inflate(R.layout.fragment_cash_sale, container, false);
activity = getActivity();
userPreference.init(activity);
db = DatabaseHelper.getInstance(activity);
// Get layout setting value
layout = Integer.parseInt(userPreference.getStringShared(SysPara.POS_LAYOUT));
changeViewProductAll();
return view;
}
public void onButtonPressed(Uri uri) {
if (mListener != null) {
mListener.onFragmentInteraction(uri);
}
}
@Override
public void onAttach(Context context) {
super.onAttach(context);
}
@Override
public void onDetach() {
super.onDetach();
mListener = null;
}
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
inflater.inflate(R.menu.cash_sale, menu);
super.onCreateOptionsMenu(menu,inflater);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
return super.onOptionsItemSelected(item);
}
/**
* This interface must be implemented by activities that contain this
* fragment to allow an interaction in this fragment to be communicated
* to the activity and potentially other fragments contained in that
* activity.
* <p>
* See the Android Training lesson <a href=
* "http://developer.android.com/training/basics/fragments/communicating.html"
* >Communicating with Other Fragments</a> for more information.
*/
public interface OnFragmentInteractionListener {
// TODO: Update argument type and name
void onFragmentInteraction(Uri uri);
}
// Get all products
private List<Product> getProducts(String tms_id, String user_co_id) {
return db.getAllProduct(tms_id, user_co_id);
}
// Convert to ListofListofProduct
private List<List<Product>> toListofListProduct(List<Product> product, int listSize, int row, int col) {
List<List<Product>> listOfListOfProducts = new ArrayList<List<Product>>();
int index = 0;
// if listing, change layout to contain only 1 column in each row
if (layout == 0 || layout == 1) {
row = product.size();
col = 1;
}
for(int i = 0 ; i<row ; i++){
List<Product> listOfProducts = new ArrayList<Product>();
for(int j = 0 ; j<col ; j++){
if (listSize == index) {
listOfListOfProducts.add(listOfProducts);
return listOfListOfProducts;
}
listOfProducts.add(product.get(index));
index++;
}
listOfListOfProducts.add(listOfProducts);
}
return listOfListOfProducts;
}
// Change the viewing display of product: list, listIcon, grid, gridIcon
public void changeViewProductAll() {
mRecyclerView = (RecyclerView) view.findViewById(R.id.rv_product);
mRecyclerView.addItemDecoration(new SimpleDividerItemDecoration(activity));
mLayoutManager = new LinearLayoutManager(activity,LinearLayoutManager.VERTICAL,false);
mRecyclerView.setLayoutManager(mLayoutManager);
mRecyclerView.setHasFixedSize(true);
//creation of the products for the grid/list
listProduct = new ArrayList<Product>();
listProductFilter = new ArrayList<Product>();
listProduct = getProducts(userPreference.getStringShared(SysPara.TMS_ID), userPreference.getStringShared(SysPara.USER_CO_ID));
List<List<Product>> ListofListofProducts = toListofListProduct(listProduct, listProduct.size(), numOfRows, numOfColumns);
Fragment fragment = new CashSaleFragment();
MainRecyclerProductAdapter mainRecyclerProductAdapter = new MainRecyclerProductAdapter(ListofListofProducts,activity,fragment);
mRecyclerView.setAdapter(mainRecyclerProductAdapter);
}
这是MainRecyclerProductAdapter
public class MainRecyclerProductAdapter extends RecyclerView.Adapter<MainRecyclerProductAdapter.ViewHolder> {
public static final String LOGTAG ="MainRecyclerProductAdapter";
private List<List<Product>> mRows;
Context mContext;
Fragment mFragment = new CashSaleFragment();
public MainRecyclerProductAdapter(List<List<Product>> objects, Context context, Fragment fragment) {
mContext = context;
mRows = objects;
mFragment = fragment;
}
static class ViewHolder extends RecyclerView.ViewHolder{
public RecyclerView mRecyclerViewRow;
public ViewHolder(View itemView) {
super(itemView);
mRecyclerViewRow =(RecyclerView)itemView.findViewById(R.id.recyclerView_row);
}
}
@Override
public int getItemCount() {
return mRows.size();
}
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
List<Product> RowItems = mRows.get(position);
LinearLayoutManager layoutManager = new LinearLayoutManager(mContext,LinearLayoutManager.HORIZONTAL,false);
holder.mRecyclerViewRow.setLayoutManager(layoutManager);
holder.mRecyclerViewRow.setHasFixedSize(true);
RowRecyclerProductAdapter rowsRecyclerAdapter = new RowRecyclerProductAdapter(mContext,RowItems,mFragment);
holder.mRecyclerViewRow.setAdapter(rowsRecyclerAdapter);
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int arg1) {
LayoutInflater inflater =
(LayoutInflater) mContext.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
View convertView = inflater.inflate(R.layout.recyclerview_row, parent, false);
return new ViewHolder(convertView);
}
RowRecyclerProductAdapter
public class RowRecyclerProductAdapter extends RecyclerView.Adapter<RowRecyclerProductAdapter.ViewHolder> {
private OnItemClickListener onItemClickListener;
private List<Product> mItems, productClickList;
private UserPreference userPreference = new UserPreference();
private int layout;
Context mContext;
com.m3online.i3twpos.util.OnItemClickListener onItemClickListener;
Fragment mFragment = new CashSaleFragment();
final Handler handler = new Handler();
public RowRecyclerProductAdapter(Context context, List<Product> objects, Fragment fragment) {
mContext = context;
mItems = objects;
mFragment = fragment;
userPreference.init(mContext);
layout = Integer.parseInt(userPreference.getStringShared(SysPara.POS_LAYOUT));
}
static class ViewHolder extends RecyclerView.ViewHolder{
public ImageView mImageView;
public TextView mTextView, mSKU;
public View rootView;
public ViewHolder(View itemView) {
super(itemView);
rootView = itemView;
mImageView =(ImageView)itemView.findViewById(R.id.productIcon);
mTextView =(TextView)itemView.findViewById(R.id.productTitle);
mSKU =(TextView)itemView.findViewById(R.id.sku);
}
}
@Override
public int getItemCount() {
return mItems.size();
}
public RowRecyclerProductAdapter (com.m3online.i3twpos.util.OnItemClickListener onItemClickListener) {
this.onItemClickListener = onItemClickListener;
}
@Override
public void onBindViewHolder(final ViewHolder holder, int position) {
final ViewHolder vh = (ViewHolder) holder;
final Product product = mItems.get(position);
holder.mTextView.setText(product.getProduct_name());
holder.mSKU.setText(product.getProduct_sku());
vh.itemView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Toast.makeText(mContext, "Click "+holder.mTextView.getText().toString(), Toast.LENGTH_SHORT).show();
onItemClickListener.onItemClick(product);
}
});
}
public interface OnItemClickListener {
void onItemClick(Product product);
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int arg1) {
LayoutInflater inflater = (LayoutInflater) mContext.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
View convertView = inflater.inflate(R.layout.product_grid, parent, false);
return new ViewHolder(convertView);
}
使用此实现,我可以单击并访问每个 ViewHolder,但我无法将数据传递到我的片段。这是因为我想将点击的项目添加到另一个列表(productOrderList),并将其显示在 ListView 中。作为现在的解决方法,我将单击的 Product
放入 SharedPreferences,然后再次加载我的片段。
这样,我可以从 SharedPreferences
获取列表并显示我的 ListView
,但我想采取适当的方式来处理这种情况。我对编程真的很陌生,但每天仍在学习很多东西。真的希望你们能帮我解决这个问题。
抱歉,如果我的解释不够清楚,如果我还需要添加其他细节,请告诉我。
编辑:
Screenshot of my current app
橙色框是我的 MainRecyclerProductAdapter
,而绿色框是每行的 RowRecyclerProductAdapter
。我想要实现的是,一旦我单击 RecyclerView
中列出的任何 Product
,我希望将其添加到 productOrderList 中并在紫色框中生成一个 ListView
.
这将解决您的问题:但我无法将数据传递到我的片段
您可以添加一个以对象作为参数的接口,通过使用它,您现在可以将数据从适配器传递到片段并将其用于您的:并将其显示在 ListView 中 问题。
CashSaleFragment
MainRecyclerProductAdapter mainRecyclerProductAdapter = new MainRecyclerProductAdapter(ListofListofProducts,activity,fragment, new com.m3online.i3twpos.util.OnItemClickListener() {
@Override
public void onItemClick(Product product) {
//you can now handle the product that is clicked from here on fragment. yey!
}
});
MainRecyclerProductAdapter
public static final String LOGTAG ="MainRecyclerProductAdapter";
private List<List<Product>> mRows;
Context mContext;
Fragment mFragment = new CashSaleFragment();
om.m3online.i3twpos.util.OnItemClickListener onItemClickListener; //add this
//update your constructor, add your custom interface
public MainRecyclerProductAdapter(List<List<Product>> objects, Context context, Fragment fragment, com.m3online.i3twpos.util.OnItemClickListener onItemClickListener) {
mContext = context;
mRows = objects;
mFragment = fragment;
this.onItemClickListener = onItemClickListener; //add this
}
.....
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
List<Product> RowItems = mRows.get(position);
LinearLayoutManager layoutManager = new LinearLayoutManager(mContext,LinearLayoutManager.HORIZONTAL,false);
holder.mRecyclerViewRow.setLayoutManager(layoutManager);
holder.mRecyclerViewRow.setHasFixedSize(true);
RowRecyclerProductAdapter rowsRecyclerAdapter = new RowRecyclerProductAdapter(mContext, RowItems, mFragment, onItemClickListener);
holder.mRecyclerViewRow.setAdapter(rowsRecyclerAdapter);
}
RowRecyclerProductAdapter
public RowRecyclerProductAdapter(Context context, List<Product> objects, Fragment fragment, com.m3online.i3twpos.util.OnItemClickListener onItemClickListener) {
mContext = context;
mItems = objects;
mFragment = fragment;
userPreference.init(mContext);
layout = Integer.parseInt(userPreference.getStringShared(SysPara.POS_LAYOUT));
this.onItemClickListener = onItemClickListener; //add this, to get the interface passed from fragment to mainrecyclerproductadapter to here
}
首先,您需要一个界面来拦截内部 recyclerview 中的触摸事件,因此在内部像这样创建一个 class。它会将截获的任何触摸传回给调用 class 的父级。
public class ItemClickSupport {
private final RecyclerView mRecyclerView;
private OnItemClickListener mOnItemClickListener;
private OnItemLongClickListener mOnItemLongClickListener;
private View.OnClickListener mOnClickListener = new View.OnClickListener() {
@Override
public void onClick(View v) {
if (mOnItemClickListener != null) {
RecyclerView.ViewHolder holder = mRecyclerView.getChildViewHolder(v);
mOnItemClickListener.onItemClicked(mRecyclerView, holder.getAdapterPosition(), v);
}
}
};
private View.OnLongClickListener mOnLongClickListener = new View.OnLongClickListener() {
@Override
public boolean onLongClick(View v) {
if (mOnItemLongClickListener != null) {
RecyclerView.ViewHolder holder = mRecyclerView.getChildViewHolder(v);
return mOnItemLongClickListener.onItemLongClicked(mRecyclerView, holder.getAdapterPosition(), v);
}
return false;
}
};
private RecyclerView.OnChildAttachStateChangeListener mAttachListener =
new RecyclerView.OnChildAttachStateChangeListener() {
@Override
public void onChildViewAttachedToWindow(View view) {
if (mOnItemClickListener != null) {
view.setOnClickListener(mOnClickListener);
}
if (mOnItemLongClickListener != null) {
view.setOnLongClickListener(mOnLongClickListener);
}
}
@Override
public void onChildViewDetachedFromWindow(View view) {
}
};
private ItemClickSupport(RecyclerView recyclerView) {
mRecyclerView = recyclerView;
mRecyclerView.setTag(R.id.item_click_support, this);
mRecyclerView.addOnChildAttachStateChangeListener(mAttachListener);
}
public static ItemClickSupport addTo(RecyclerView view) {
ItemClickSupport support = (ItemClickSupport) view.getTag(R.id.item_click_support);
if (support == null) {
support = new ItemClickSupport(view);
}
return support;
}
public static ItemClickSupport removeFrom(RecyclerView view) {
ItemClickSupport support = (ItemClickSupport) view.getTag(R.id.item_click_support);
if (support != null) {
support.detach(view);
}
return support;
}
public ItemClickSupport setOnItemClickListener(OnItemClickListener listener) {
mOnItemClickListener = listener;
return this;
}
public ItemClickSupport setOnItemLongClickListener(OnItemLongClickListener listener) {
mOnItemLongClickListener = listener;
return this;
}
private void detach(RecyclerView view) {
view.removeOnChildAttachStateChangeListener(mAttachListener);
view.setTag(R.id.item_click_support, null);
}
public interface OnItemClickListener {
void onItemClicked(RecyclerView recyclerView, int position, View v);
void onItemClicked(int position);
}
public interface OnItemLongClickListener {
boolean onItemLongClicked(RecyclerView recyclerView, int position, View v);
}
public static class SimpleOnItemClickListener implements OnItemClickListener {
@Override
public void onItemClicked(int position) {
}
@Override
public void onItemClicked(RecyclerView recyclerView, int position, View v) {
}
}
}
现在,当您创建外部 recyclerview 适配器时,只需初始化它即可。
ItemClickSupport.addTo(mRecyclerView).setOnItemClickListener(this);
这时候你将拥有拦截你在外部适配器 class.
中作为 this
传递的内部触摸事件所需的所有方法
但我们也希望这些事件从外部适配器 class 传递到调用片段,设置一个像这样的侦听器。
rootAdapter.setOnItemClickListener(this);
现在在根适配器中,绑定项目和创建内部适配器时,将项目点击支持监听器传递给内部适配器,如下所示:
innerAdapter.setOnItemClickListener(new ItemClickSupport.SimpleOnItemClickListener() {
@Override
public void onItemClicked(int position) {
// Here we pass the click to the parent provided click listener.
// We modify the position with the one of the ViewHolder so that we don't get the
// position of the horizontal RecyclerView adapter - we are interested on the
// vertical item actually.
if (null != mItemClickListener) {
mItemClickListener.onItemClicked(holder.getAdapterPosition());
}
}
});
mItemClickListener
就是你上面通过fragment设置的。
在内部适配器中,创建视图时,在布局的根部设置一个点击监听器,并将该事件传回自定义点击监听器:
// Detect the click events and pass them to any listeners
itemView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (null != mOnItemClickListener) {
mOnItemClickListener.onItemClicked(position);
}
}
});
mOnItemClickListener
其实就是上面说的adapter传递过来的item点击支持
我有一个片段,它有一个嵌套的 RecyclerView 来显示产品列表。我根据 mmlooloo 的解决方案实现了这一点:How to create scrollable page of carousels in Android?
这是我的片段,我在其中调用了 MainRecyclerProductAdapter
public class CashSaleFragment 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";
private static final String TAG = "MainActivity";
private UserPreference userPreference = new UserPreference();
int numOfRows = 11;
int numOfColumns = 8;
public int layout = 1; // 0-list_icon 1-list 2-grid_icon 3-grid
public List<Product> listProduct, listProductFilter;
private DatabaseHelper db;
private RecyclerView mRecyclerView;
private LinearLayoutManager mLayoutManager;
View view;
Activity activity;
// TODO: Rename and change types of parameters
private String mParam1;
private String mParam2;
private OnFragmentInteractionListener mListener;
public CashSaleFragment() {
// 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 CashSaleFragment_old.
*/
// TODO: Rename and change types and number of parameters
public static CashSaleFragment newInstance(String param1, String param2) {
CashSaleFragment fragment = new CashSaleFragment();
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, final ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
view = inflater.inflate(R.layout.fragment_cash_sale, container, false);
activity = getActivity();
userPreference.init(activity);
db = DatabaseHelper.getInstance(activity);
// Get layout setting value
layout = Integer.parseInt(userPreference.getStringShared(SysPara.POS_LAYOUT));
changeViewProductAll();
return view;
}
public void onButtonPressed(Uri uri) {
if (mListener != null) {
mListener.onFragmentInteraction(uri);
}
}
@Override
public void onAttach(Context context) {
super.onAttach(context);
}
@Override
public void onDetach() {
super.onDetach();
mListener = null;
}
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
inflater.inflate(R.menu.cash_sale, menu);
super.onCreateOptionsMenu(menu,inflater);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
return super.onOptionsItemSelected(item);
}
/**
* This interface must be implemented by activities that contain this
* fragment to allow an interaction in this fragment to be communicated
* to the activity and potentially other fragments contained in that
* activity.
* <p>
* See the Android Training lesson <a href=
* "http://developer.android.com/training/basics/fragments/communicating.html"
* >Communicating with Other Fragments</a> for more information.
*/
public interface OnFragmentInteractionListener {
// TODO: Update argument type and name
void onFragmentInteraction(Uri uri);
}
// Get all products
private List<Product> getProducts(String tms_id, String user_co_id) {
return db.getAllProduct(tms_id, user_co_id);
}
// Convert to ListofListofProduct
private List<List<Product>> toListofListProduct(List<Product> product, int listSize, int row, int col) {
List<List<Product>> listOfListOfProducts = new ArrayList<List<Product>>();
int index = 0;
// if listing, change layout to contain only 1 column in each row
if (layout == 0 || layout == 1) {
row = product.size();
col = 1;
}
for(int i = 0 ; i<row ; i++){
List<Product> listOfProducts = new ArrayList<Product>();
for(int j = 0 ; j<col ; j++){
if (listSize == index) {
listOfListOfProducts.add(listOfProducts);
return listOfListOfProducts;
}
listOfProducts.add(product.get(index));
index++;
}
listOfListOfProducts.add(listOfProducts);
}
return listOfListOfProducts;
}
// Change the viewing display of product: list, listIcon, grid, gridIcon
public void changeViewProductAll() {
mRecyclerView = (RecyclerView) view.findViewById(R.id.rv_product);
mRecyclerView.addItemDecoration(new SimpleDividerItemDecoration(activity));
mLayoutManager = new LinearLayoutManager(activity,LinearLayoutManager.VERTICAL,false);
mRecyclerView.setLayoutManager(mLayoutManager);
mRecyclerView.setHasFixedSize(true);
//creation of the products for the grid/list
listProduct = new ArrayList<Product>();
listProductFilter = new ArrayList<Product>();
listProduct = getProducts(userPreference.getStringShared(SysPara.TMS_ID), userPreference.getStringShared(SysPara.USER_CO_ID));
List<List<Product>> ListofListofProducts = toListofListProduct(listProduct, listProduct.size(), numOfRows, numOfColumns);
Fragment fragment = new CashSaleFragment();
MainRecyclerProductAdapter mainRecyclerProductAdapter = new MainRecyclerProductAdapter(ListofListofProducts,activity,fragment);
mRecyclerView.setAdapter(mainRecyclerProductAdapter);
}
这是MainRecyclerProductAdapter
public class MainRecyclerProductAdapter extends RecyclerView.Adapter<MainRecyclerProductAdapter.ViewHolder> {
public static final String LOGTAG ="MainRecyclerProductAdapter";
private List<List<Product>> mRows;
Context mContext;
Fragment mFragment = new CashSaleFragment();
public MainRecyclerProductAdapter(List<List<Product>> objects, Context context, Fragment fragment) {
mContext = context;
mRows = objects;
mFragment = fragment;
}
static class ViewHolder extends RecyclerView.ViewHolder{
public RecyclerView mRecyclerViewRow;
public ViewHolder(View itemView) {
super(itemView);
mRecyclerViewRow =(RecyclerView)itemView.findViewById(R.id.recyclerView_row);
}
}
@Override
public int getItemCount() {
return mRows.size();
}
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
List<Product> RowItems = mRows.get(position);
LinearLayoutManager layoutManager = new LinearLayoutManager(mContext,LinearLayoutManager.HORIZONTAL,false);
holder.mRecyclerViewRow.setLayoutManager(layoutManager);
holder.mRecyclerViewRow.setHasFixedSize(true);
RowRecyclerProductAdapter rowsRecyclerAdapter = new RowRecyclerProductAdapter(mContext,RowItems,mFragment);
holder.mRecyclerViewRow.setAdapter(rowsRecyclerAdapter);
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int arg1) {
LayoutInflater inflater =
(LayoutInflater) mContext.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
View convertView = inflater.inflate(R.layout.recyclerview_row, parent, false);
return new ViewHolder(convertView);
}
RowRecyclerProductAdapter
public class RowRecyclerProductAdapter extends RecyclerView.Adapter<RowRecyclerProductAdapter.ViewHolder> {
private OnItemClickListener onItemClickListener;
private List<Product> mItems, productClickList;
private UserPreference userPreference = new UserPreference();
private int layout;
Context mContext;
com.m3online.i3twpos.util.OnItemClickListener onItemClickListener;
Fragment mFragment = new CashSaleFragment();
final Handler handler = new Handler();
public RowRecyclerProductAdapter(Context context, List<Product> objects, Fragment fragment) {
mContext = context;
mItems = objects;
mFragment = fragment;
userPreference.init(mContext);
layout = Integer.parseInt(userPreference.getStringShared(SysPara.POS_LAYOUT));
}
static class ViewHolder extends RecyclerView.ViewHolder{
public ImageView mImageView;
public TextView mTextView, mSKU;
public View rootView;
public ViewHolder(View itemView) {
super(itemView);
rootView = itemView;
mImageView =(ImageView)itemView.findViewById(R.id.productIcon);
mTextView =(TextView)itemView.findViewById(R.id.productTitle);
mSKU =(TextView)itemView.findViewById(R.id.sku);
}
}
@Override
public int getItemCount() {
return mItems.size();
}
public RowRecyclerProductAdapter (com.m3online.i3twpos.util.OnItemClickListener onItemClickListener) {
this.onItemClickListener = onItemClickListener;
}
@Override
public void onBindViewHolder(final ViewHolder holder, int position) {
final ViewHolder vh = (ViewHolder) holder;
final Product product = mItems.get(position);
holder.mTextView.setText(product.getProduct_name());
holder.mSKU.setText(product.getProduct_sku());
vh.itemView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Toast.makeText(mContext, "Click "+holder.mTextView.getText().toString(), Toast.LENGTH_SHORT).show();
onItemClickListener.onItemClick(product);
}
});
}
public interface OnItemClickListener {
void onItemClick(Product product);
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup parent, int arg1) {
LayoutInflater inflater = (LayoutInflater) mContext.getSystemService(Activity.LAYOUT_INFLATER_SERVICE);
View convertView = inflater.inflate(R.layout.product_grid, parent, false);
return new ViewHolder(convertView);
}
使用此实现,我可以单击并访问每个 ViewHolder,但我无法将数据传递到我的片段。这是因为我想将点击的项目添加到另一个列表(productOrderList),并将其显示在 ListView 中。作为现在的解决方法,我将单击的 Product
放入 SharedPreferences,然后再次加载我的片段。
这样,我可以从 SharedPreferences
获取列表并显示我的 ListView
,但我想采取适当的方式来处理这种情况。我对编程真的很陌生,但每天仍在学习很多东西。真的希望你们能帮我解决这个问题。
抱歉,如果我的解释不够清楚,如果我还需要添加其他细节,请告诉我。
编辑:
Screenshot of my current app
橙色框是我的 MainRecyclerProductAdapter
,而绿色框是每行的 RowRecyclerProductAdapter
。我想要实现的是,一旦我单击 RecyclerView
中列出的任何 Product
,我希望将其添加到 productOrderList 中并在紫色框中生成一个 ListView
.
这将解决您的问题:但我无法将数据传递到我的片段
您可以添加一个以对象作为参数的接口,通过使用它,您现在可以将数据从适配器传递到片段并将其用于您的:并将其显示在 ListView 中 问题。
CashSaleFragment
MainRecyclerProductAdapter mainRecyclerProductAdapter = new MainRecyclerProductAdapter(ListofListofProducts,activity,fragment, new com.m3online.i3twpos.util.OnItemClickListener() {
@Override
public void onItemClick(Product product) {
//you can now handle the product that is clicked from here on fragment. yey!
}
});
MainRecyclerProductAdapter
public static final String LOGTAG ="MainRecyclerProductAdapter";
private List<List<Product>> mRows;
Context mContext;
Fragment mFragment = new CashSaleFragment();
om.m3online.i3twpos.util.OnItemClickListener onItemClickListener; //add this
//update your constructor, add your custom interface
public MainRecyclerProductAdapter(List<List<Product>> objects, Context context, Fragment fragment, com.m3online.i3twpos.util.OnItemClickListener onItemClickListener) {
mContext = context;
mRows = objects;
mFragment = fragment;
this.onItemClickListener = onItemClickListener; //add this
}
.....
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
List<Product> RowItems = mRows.get(position);
LinearLayoutManager layoutManager = new LinearLayoutManager(mContext,LinearLayoutManager.HORIZONTAL,false);
holder.mRecyclerViewRow.setLayoutManager(layoutManager);
holder.mRecyclerViewRow.setHasFixedSize(true);
RowRecyclerProductAdapter rowsRecyclerAdapter = new RowRecyclerProductAdapter(mContext, RowItems, mFragment, onItemClickListener);
holder.mRecyclerViewRow.setAdapter(rowsRecyclerAdapter);
}
RowRecyclerProductAdapter
public RowRecyclerProductAdapter(Context context, List<Product> objects, Fragment fragment, com.m3online.i3twpos.util.OnItemClickListener onItemClickListener) {
mContext = context;
mItems = objects;
mFragment = fragment;
userPreference.init(mContext);
layout = Integer.parseInt(userPreference.getStringShared(SysPara.POS_LAYOUT));
this.onItemClickListener = onItemClickListener; //add this, to get the interface passed from fragment to mainrecyclerproductadapter to here
}
首先,您需要一个界面来拦截内部 recyclerview 中的触摸事件,因此在内部像这样创建一个 class。它会将截获的任何触摸传回给调用 class 的父级。
public class ItemClickSupport {
private final RecyclerView mRecyclerView;
private OnItemClickListener mOnItemClickListener;
private OnItemLongClickListener mOnItemLongClickListener;
private View.OnClickListener mOnClickListener = new View.OnClickListener() {
@Override
public void onClick(View v) {
if (mOnItemClickListener != null) {
RecyclerView.ViewHolder holder = mRecyclerView.getChildViewHolder(v);
mOnItemClickListener.onItemClicked(mRecyclerView, holder.getAdapterPosition(), v);
}
}
};
private View.OnLongClickListener mOnLongClickListener = new View.OnLongClickListener() {
@Override
public boolean onLongClick(View v) {
if (mOnItemLongClickListener != null) {
RecyclerView.ViewHolder holder = mRecyclerView.getChildViewHolder(v);
return mOnItemLongClickListener.onItemLongClicked(mRecyclerView, holder.getAdapterPosition(), v);
}
return false;
}
};
private RecyclerView.OnChildAttachStateChangeListener mAttachListener =
new RecyclerView.OnChildAttachStateChangeListener() {
@Override
public void onChildViewAttachedToWindow(View view) {
if (mOnItemClickListener != null) {
view.setOnClickListener(mOnClickListener);
}
if (mOnItemLongClickListener != null) {
view.setOnLongClickListener(mOnLongClickListener);
}
}
@Override
public void onChildViewDetachedFromWindow(View view) {
}
};
private ItemClickSupport(RecyclerView recyclerView) {
mRecyclerView = recyclerView;
mRecyclerView.setTag(R.id.item_click_support, this);
mRecyclerView.addOnChildAttachStateChangeListener(mAttachListener);
}
public static ItemClickSupport addTo(RecyclerView view) {
ItemClickSupport support = (ItemClickSupport) view.getTag(R.id.item_click_support);
if (support == null) {
support = new ItemClickSupport(view);
}
return support;
}
public static ItemClickSupport removeFrom(RecyclerView view) {
ItemClickSupport support = (ItemClickSupport) view.getTag(R.id.item_click_support);
if (support != null) {
support.detach(view);
}
return support;
}
public ItemClickSupport setOnItemClickListener(OnItemClickListener listener) {
mOnItemClickListener = listener;
return this;
}
public ItemClickSupport setOnItemLongClickListener(OnItemLongClickListener listener) {
mOnItemLongClickListener = listener;
return this;
}
private void detach(RecyclerView view) {
view.removeOnChildAttachStateChangeListener(mAttachListener);
view.setTag(R.id.item_click_support, null);
}
public interface OnItemClickListener {
void onItemClicked(RecyclerView recyclerView, int position, View v);
void onItemClicked(int position);
}
public interface OnItemLongClickListener {
boolean onItemLongClicked(RecyclerView recyclerView, int position, View v);
}
public static class SimpleOnItemClickListener implements OnItemClickListener {
@Override
public void onItemClicked(int position) {
}
@Override
public void onItemClicked(RecyclerView recyclerView, int position, View v) {
}
}
}
现在,当您创建外部 recyclerview 适配器时,只需初始化它即可。
ItemClickSupport.addTo(mRecyclerView).setOnItemClickListener(this);
这时候你将拥有拦截你在外部适配器 class.
中作为this
传递的内部触摸事件所需的所有方法
但我们也希望这些事件从外部适配器 class 传递到调用片段,设置一个像这样的侦听器。
rootAdapter.setOnItemClickListener(this);
现在在根适配器中,绑定项目和创建内部适配器时,将项目点击支持监听器传递给内部适配器,如下所示:
innerAdapter.setOnItemClickListener(new ItemClickSupport.SimpleOnItemClickListener() {
@Override
public void onItemClicked(int position) {
// Here we pass the click to the parent provided click listener.
// We modify the position with the one of the ViewHolder so that we don't get the
// position of the horizontal RecyclerView adapter - we are interested on the
// vertical item actually.
if (null != mItemClickListener) {
mItemClickListener.onItemClicked(holder.getAdapterPosition());
}
}
});
mItemClickListener
就是你上面通过fragment设置的。
在内部适配器中,创建视图时,在布局的根部设置一个点击监听器,并将该事件传回自定义点击监听器:
// Detect the click events and pass them to any listeners
itemView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
if (null != mOnItemClickListener) {
mOnItemClickListener.onItemClicked(position);
}
}
});
mOnItemClickListener
其实就是上面说的adapter传递过来的item点击支持