ViewPagerでCardViewを使用してみましたが、CardViewを左右にスワイプするたびに次の画面に移動します。その時、カード自体を削除してほしい。現在、スタンドアロンとしては両方とも正常に機能していますが、組み合わせると、ビューページャーのみが機能し、カードワイプは閉じません。
以下のコードでViewPagerを無効にしようとしましたが、このコードはCardViewスワイプジェスチャも無効にします。 CardViewのみにジェスチャーを設定するにはどうすればよいですか。2枚のカード間をスワイプすると、カード要素に接続されていないため、ViewPagerが表示されます。
または、ViewPagerを完全に無効にしてボタンとして使用し、CardViewでスワイプを有効にします。私は本当にどんな助けにも感謝します。前もって感謝します。
参考:ViewPagerでAndroid_horizontal_listviewを試しましたが、これは問題なく動作し、まったく同じです。
ViewPagerの場合:
mPager.setOnTouchListener(new OnTouchListener()
{
@Override
public boolean onTouch(View v, MotionEvent event)
{
return true;
}
});
CardViewの場合:
SwipeableRecyclerViewTouchListener swipeTouchListener =
new SwipeableRecyclerViewTouchListener(mRecyclerView,
new SwipeableRecyclerViewTouchListener.SwipeListener() {
@Override
public boolean canSwipe(int position) {
return true;
}
@Override
public void onDismissedBySwipeLeft(RecyclerView recyclerView, int[] reverseSortedPositions) {
for (int position : reverseSortedPositions) {
mItems.remove(position);
mAdapter.notifyItemRemoved(position);
}
mAdapter.notifyDataSetChanged();
}
@Override
public void onDismissedBySwipeRight(RecyclerView recyclerView, int[] reverseSortedPositions) {
for (int position : reverseSortedPositions) {
mItems.remove(position);
mAdapter.notifyItemRemoved(position);
}
mAdapter.notifyDataSetChanged();
}
});
mRecyclerView.addOnItemTouchListener(swipeTouchListener);
Mainactivity.Java
public class MainActivity extends Activity implements ActionBar.TabListener {
ViewPager vp;
View viewpager_layout_1;
View viewpager_layout_2;
View viewpager_layout_3;
ActionBar.Tab tab_1;
ActionBar.Tab tab_2;
ActionBar.Tab tab_3;
ActionBar bar;
/////
String jsonstring1;
CardViewAdapter spinnerArray;
ImageLoader imageLoader = ImageLoader.getInstance();//
DisplayImageOptions options;
ArrayList<HashMap<String, String>> array_list1;
RecyclerView recyclerView;
RelativeLayout re1;
private Context mContext;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);
setContentView(R.layout.activity_main);
mContext = this;
viewpager_layout_1 = new View(mContext);
viewpager_layout_1 = getLayoutInflater().inflate(R.layout.sample1, null);
viewpager_layout_3 = new View(mContext);
viewpager_layout_3 = getLayoutInflater().inflate(R.layout.sample2, null);
viewpager_layout_2 = new View(mContext);
viewpager_layout_2 = getLayoutInflater().inflate(R.layout.sample3, null);
vp = (ViewPager) findViewById(R.id.vp);
bar = getActionBar();
bar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
bar.setDisplayShowTitleEnabled(false);
bar.setDisplayShowHomeEnabled(false);
Vector<View> pages = new Vector<View>();
pages.add(viewpager_layout_1);
pages.add(viewpager_layout_3);
pages.add(viewpager_layout_2);
CustomPagerAdapter adapter = new CustomPagerAdapter(mContext, pages);
vp.setAdapter(adapter);
vp.setOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener() {
@Override
public void onPageSelected(int position) {
bar.setSelectedNavigationItem(position);
}
});
tab_1 = bar.newTab();
tab_1.setCustomView(R.layout.tab_layout_1);
tab_1.setTabListener(this);
bar.addTab(tab_1);
tab_2 = bar.newTab();
tab_2.setCustomView(R.layout.tab_layout_2);
tab_2.setTabListener(this);
bar.addTab(tab_2);
tab_3 = bar.newTab();
tab_3.setCustomView(R.layout.tab_layout_3);
tab_3.setTabListener(this);
bar.addTab(tab_3);
////
imageLoader.init(ImageLoaderConfiguration.createDefault(MainActivity.this));
jsonstring1 = "[{\"category\":\"1\",\"no\":\"1\",\"image\":\"http://upload.wikimedia.org/wikipedia/commons/c/c3/Jordan_by_Lipofsky_16577.jpg\"},{\"category\":\"2\",\"no\":\"2\",\"image\":\"http://upload.wikimedia.org/wikipedia/commons/thumb/9/96/Basketball_World_Cup_2014.jpg/800px-Basketball_World_Cup_2014.jpg\"},{\"category\":\"3\",\"no\":\"3\",\"image\":\"http://upload.wikimedia.org/wikipedia/commons/4/4e/Basketball_Goal.jpg\"},{\"category\":\"4\",\"no\":\"4\",\"image\":\"http://upload.wikimedia.org/wikipedia/commons/1/10/Basketball_through_hoop.jpg\"}]";
//////////
array_list1 = new ArrayList<HashMap<String, String>>();
JSONArray arr = null;
try {
arr = new JSONArray(jsonstring1);
for (int i = 0; i < arr.length(); i++) {
JSONObject e1 = arr.getJSONObject(i);
String category = e1.getString("category").trim();
String no = e1.getString("no").trim();
String image = e1.getString("image").trim();
HashMap<String, String> map = new HashMap<String, String>();
map.put("category", category);
map.put("no", no);
map.put("image", image);
// adding HashList to ArrayList
array_list1.add(map);
}
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
OnItemTouchListener itemTouchListener = new OnItemTouchListener() {
@Override
public void onCardViewTap(View view, int position) {
Toast.makeText(MainActivity.this, "Tapped " + array_list1.get(position), Toast.LENGTH_SHORT).show();
}
@Override
public void onButton1Click(View view, int position) {
Toast.makeText(MainActivity.this, "Clicked Button1 in " + array_list1.get(position), Toast.LENGTH_SHORT).show();
}
@Override
public void onButton2Click(View view, int position) {
Toast.makeText(MainActivity.this, "Clicked Button2 in " + array_list1.get(position), Toast.LENGTH_SHORT).show();
}
};
spinnerArray = new CardViewAdapter(itemTouchListener, MainActivity.this, array_list1);
recyclerView = (RecyclerView) viewpager_layout_3.findViewById(R.id.recycler_view);
recyclerView.setLayoutManager(new LinearLayoutManager(this));
SlideInBottomAnimationAdapter alphaAdapter = new SlideInBottomAnimationAdapter(spinnerArray);
ScaleInAnimationAdapter alphaAdapter2 = new ScaleInAnimationAdapter(alphaAdapter);
final AlphaInAnimationAdapter alphaAdapter3 = new AlphaInAnimationAdapter(alphaAdapter2);
alphaAdapter3.setDuration(500);
alphaAdapter3.setFirstOnly(true);
recyclerView.setAdapter(alphaAdapter3);
final SwipeableRecyclerViewTouchListener swipeTouchListener =
new SwipeableRecyclerViewTouchListener(recyclerView,
new SwipeableRecyclerViewTouchListener.SwipeListener() {
@Override
public boolean canSwipe(int position) {
return true;
}
@Override
public void onDismissedBySwipeLeft(RecyclerView recyclerView, int[] reverseSortedPositions) {
for (int position : reverseSortedPositions) {
// mItems.remove(position);
Toast.makeText(MainActivity.this, array_list1.get(position) + " swiped left", Toast.LENGTH_SHORT).show();
array_list1.remove(position);
alphaAdapter3.notifyItemRemoved(position);
}
alphaAdapter3.notifyDataSetChanged();
}
@Override
public void onDismissedBySwipeRight(RecyclerView recyclerView, int[] reverseSortedPositions) {
for (int position : reverseSortedPositions) {
//
Toast.makeText(MainActivity.this, array_list1.get(position) + " swiped right", Toast.LENGTH_SHORT).show();
array_list1.remove(position);
alphaAdapter3.notifyItemRemoved(position);
}
alphaAdapter3.notifyDataSetChanged();
}
});
recyclerView.addOnItemTouchListener(swipeTouchListener);
}
@Override
public void onTabReselected(ActionBar.Tab tab, FragmentTransaction ft) {
// Toast.makeText(getBaseContext(), tab.toString(), 5).show();
}
@Override
public void onTabSelected(ActionBar.Tab tab, FragmentTransaction ft) {
// Toast.makeText(getBaseContext(), tab.toString(), 5).show();
vp.setCurrentItem(tab.getPosition());
if (tab.getPosition() == 2) {
tab_2.setCustomView(null);
tab_2.setCustomView(R.layout.tab_layout_2);
tab_1.setCustomView(null);
tab_1.setCustomView(R.layout.tab_layout_1);
tab_3.setCustomView(null);
tab_3.setCustomView(R.layout.tab_layout_33);
} else if (tab.getPosition() == 1) {
tab_2.setCustomView(null);
tab_2.setCustomView(R.layout.tab_layout_22);
tab_1.setCustomView(null);
tab_1.setCustomView(R.layout.tab_layout_1);
tab_3.setCustomView(null);
tab_3.setCustomView(R.layout.tab_layout_3);
} else if (tab.getPosition() == 0) {
tab_1.setCustomView(null);
tab_1.setCustomView(R.layout.tab_layout_11);
if (tab_2 != null) {
tab_2.setCustomView(null);
tab_2.setCustomView(R.layout.tab_layout_2);
}
if (tab_3 != null) {
tab_3.setCustomView(null);
tab_3.setCustomView(R.layout.tab_layout_3);
}
}
}
@Override
public void onTabUnselected(ActionBar.Tab tab, FragmentTransaction ft) {
// Toast.makeText(getBaseContext(), tab.toString(), 5).show();
}
public interface OnItemTouchListener {
// this will disallow the touch request for parent scroll on touch of child view
/**
* Callback invoked when the user Taps one of the RecyclerView items
*
* @param view the CardView touched
* @param position the index of the item touched in the RecyclerView
*/
public void onCardViewTap(View view, int position);
/**
* Callback invoked when the Button1 of an item is touched
*
* @param view the Button touched
* @param position the index of the item touched in the RecyclerView
*/
public void onButton1Click(View view, int position);
/**
* Callback invoked when the Button2 of an item is touched
*
* @param view the Button touched
* @param position the index of the item touched in the RecyclerView
*/
public void onButton2Click(View view, int position);
}
public class CustomPagerAdapter extends PagerAdapter {
private final Context mContext;
private final Vector<View> pages;
public CustomPagerAdapter(Context context, Vector<View> pages) {
this.mContext = context;
this.pages = pages;
}
@Override
public Object instantiateItem(ViewGroup container, int position) {
View page = pages.get(position);
container.addView(page);
return page;
}
@Override
public int getCount() {
return pages.size();
}
@Override
public boolean isViewFromObject(View view, Object object) {
return view.equals(object);
}
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
container.removeView((View) object);
}
}
public class CardViewAdapter extends RecyclerView.Adapter<CardViewAdapter.ViewHolder> {
ArrayList<HashMap<String, String>> d;
Activity a;
private List<String> cards;
private OnItemTouchListener onItemTouchListener2;
public CardViewAdapter(OnItemTouchListener onItemTouchListener, Activity a, ArrayList<HashMap<String, String>> d) {
// this.cards = cards;
this.onItemTouchListener2 = onItemTouchListener;
this.a = a;
this.d = d;
}
@Override
public ViewHolder onCreateViewHolder(ViewGroup viewGroup, int i) {
View v = LayoutInflater.from(viewGroup.getContext()).inflate(R.layout.card_view_layout, viewGroup, false);
return new ViewHolder(v);
}
@Override
public void onBindViewHolder(ViewHolder viewHolder, int i) {
// viewHolder.title.setText(cards.get(i));
HashMap<String, String> item = d.get(i);
viewHolder.title.setText(item.get("category"));
imageLoader.displayImage(item.get("image"), viewHolder.im2);
}
@Override
public int getItemCount() {
// return d == null ? 0 : d.size();
return (null != d ? d.size() : 0);
// return d.size();
}
public class ViewHolder extends RecyclerView.ViewHolder {
MotionEvent motionEvent;
private int mSlop;
private int mMinFlingVelocity;
private int mMaxFlingVelocity;
private long mAnimationTime;
// Fixed properties
// private RecyclerView mRecyclerView;
private SwipeableRecyclerViewTouchListener.SwipeListener mSwipeListener;
// Transient properties
private int mViewWidth = 1; // 1 and not 0 to prevent dividing by zero
private int mDismissAnimationRefCount = 0;
private float mAlpha;
private float mDownX;
private float mDownY;
private boolean mSwiping;
private int mSwipingSlop;
private VelocityTracker mVelocityTracker;
private int mDownPosition;
private int mAnimatingPosition = ListView.INVALID_POSITION;
private View mDownView;
private boolean mPaused;
private float mFinalDelta;
///
private TextView title;
private Button button1;
private Button button2;
private ImageView im2;
public ViewHolder(View itemView) {
super(itemView);
title = (TextView) itemView.findViewById(R.id.card_view_title);
im2 = (ImageView) itemView.findViewById(R.id.imageView);
}
}
}
}
activity_main.xml
<RelativeLayout xmlns:Android="http://schemas.Android.com/apk/res/Android"
Android:layout_width="match_parent"
Android:layout_height="match_parent"
Android:id="@+id/relativelayout_1">
<LinearLayout
Android:layout_width="fill_parent"
Android:layout_height="fill_parent"
Android:layout_alignParentBottom="true"
Android:layout_alignParentStart="true"
Android:id="@+id/linearlayout_1"
Android:orientation="vertical">
<Android.support.v4.view.ViewPager
Android:id="@+id/vp"
Android:layout_width="match_parent"
Android:layout_height="0dp"
Android:layout_weight="1"
/>
</LinearLayout>
</RelativeLayout>
sample2.xml
<RelativeLayout xmlns:Android="http://schemas.Android.com/apk/res/Android"
Android:id="@+id/re1"
Android:layout_width="match_parent"
Android:layout_height="match_parent">
<Android.support.v7.widget.RecyclerView
Android:id="@+id/recycler_view"
Android:layout_width="match_parent"
Android:layout_height="match_parent"
Android:scrollbars="vertical">
</Android.support.v7.widget.RecyclerView>
</RelativeLayout>
この問題を解決するために、ItemTouchHelper
が提供するAndroid
を使用して、RecyclerView
からアイテムを簡単にスワイプして削除しました。
以下の実装を参照してください。
MainActivity:
ここにViewPager
の実装があり、その子はFragments
です。
_package za.co.gadgetgirl.testcardpager;
import Android.os.Bundle;
import Android.support.v4.app.Fragment;
import Android.support.v4.app.FragmentManager;
import Android.support.v4.app.FragmentPagerAdapter;
import Android.support.v4.view.ViewPager;
import Android.support.v7.app.AppCompatActivity;
import Java.util.ArrayList;
import Java.util.List;
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ViewPager viewPager = (ViewPager) findViewById(R.id.viewpager);
setupViewPager(viewPager);
}
private void setupViewPager(ViewPager viewPager) {
Adapter adapter = new Adapter(getSupportFragmentManager());
Frag1 frag1 = new Frag1();
Frag2 frag2 = new Frag2();
Frag3 frag3 = new Frag3();
adapter.addFragment(frag1, "frag1");
adapter.addFragment(frag2, "frag2");
adapter.addFragment(frag3, "frag3");
viewPager.setAdapter(adapter);
}
static class Adapter extends FragmentPagerAdapter {
private final List<Fragment> mFragments = new ArrayList<>();
private final List<String> mFragmentTitles = new ArrayList<>();
public Adapter(FragmentManager fm) {
super(fm);
}
public void addFragment(Fragment fragment, String title) {
mFragments.add(fragment);
mFragmentTitles.add(title);
}
@Override
public Fragment getItem(int position) {
return mFragments.get(position);
}
@Override
public int getCount() {
return mFragments.size();
}
@Override
public CharSequence getPageTitle(int position) {
return mFragmentTitles.get(position);
}
}
}
_
Frag1:
このFragment
にはRecyclerView
が添付されたItemTouchHelper
があります。 ItemTouchHelper
はSimpleCallback
インターフェースで定義されているonSwiped(...)
メソッドをリッスンし、このメソッドでスワイプされたアイテムを削除します。
_package za.co.gadgetgirl.testcardpager;
import Android.os.Bundle;
import Android.support.annotation.Nullable;
import Android.support.v4.app.Fragment;
import Android.support.v7.widget.LinearLayoutManager;
import Android.support.v7.widget.RecyclerView;
import Android.support.v7.widget.helper.ItemTouchHelper;
import Android.view.LayoutInflater;
import Android.view.View;
import Android.view.ViewGroup;
public class Frag1 extends Fragment {
@Nullable
@Override
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.frag1, container, false);
final RecyclerView rv = (RecyclerView) v.findViewById(R.id.rv);
final LinearLayoutManager llm = new LinearLayoutManager(getActivity());
rv.setLayoutManager(llm);
final RVAdapter rvAdapter = new RVAdapter(Person.initializeData());
rv.setAdapter(rvAdapter);
ItemTouchHelper itemTouchHelper = new ItemTouchHelper(new ItemTouchHelper.SimpleCallback(0,ItemTouchHelper.LEFT|ItemTouchHelper.RIGHT) {
@Override
public boolean onMove(RecyclerView recyclerView, RecyclerView.ViewHolder viewHolder, RecyclerView.ViewHolder target) {
return false;
}
@Override
public void onSwiped(RecyclerView.ViewHolder viewHolder, int direction) {
rvAdapter.removeItem(viewHolder.getAdapterPosition());
}
});
itemTouchHelper.attachToRecyclerView(rv);
return v;
}
}
_
RVAdapter:
_public class RVAdapter extends RecyclerView.Adapter<RVAdapter.PersonViewHolder> {
//...implementation...
public void removeItem(int position) {
persons.remove(position);
notifyItemRemoved(position);
}
}
_
ItemTouchHelper
を使用するには、アプリのgradleファイルで定義されている_appcompat-v7:22.2.0
_以上の依存関係が必要です。
私はこれまでSwipeableRecyclerView
を使ったことがないので、あまり言えません。以前と同じ問題があります。フラグメントのベースコンテナ(onTouch
、LinearLayout
など)のRelativeLayout
イベントを処理することで解決し、うまくいきます。このソリューションを試して、私たちに戻ってみませんか
あなたが説明しているユースケースでは、ViewPagerがスワイプアクションを取得するために使用したいクラスではないと思います。 CoordinatorLayout と SwipeDismissBehavior の組み合わせの方が適切だと思います。
編集:以下の私の解決策を参照してください:
レイアウトXML:
<?xml version="1.0" encoding="utf-8"?>
<Android.support.design.widget.CoordinatorLayout
xmlns:Android="http://schemas.Android.com/apk/res/Android"
xmlns:app="http://schemas.Android.com/apk/res-auto"
Android:layout_width="match_parent"
Android:layout_height="match_parent">
<Android.support.v7.widget.CardView
Android:id="@+id/cardView"
Android:layout_width="match_parent"
Android:layout_height="match_parent">
</Android.support.v7.widget.CardView>
</Android.support.design.widget.CoordinatorLayout>
アクティビティ:
public class MainActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
CardView cardView = (CardView) findViewById(R.id.cardView);
SwipeDismissBehavior<CardView> behavior = new SwipeDismissBehavior();
behavior.setSwipeDirection(SwipeDismissBehavior.SWIPE_DIRECTION_START_TO_END);
behavior.setListener(new SwipeDismissBehavior.OnDismissListener() {
@Override
public void onDismiss(View view) {
finish(); // close activity if desired
}
@Override
public void onDragStateChanged(int state) {
}
});
((CoordinatorLayout.LayoutParams) cardView.getLayoutParams()).setBehavior(behavior);
}
}
また、 CoordinatorLayout の使用例をいくつか示します。
特に SwipeDismissBehavior を使用して多くの例を見つけることができませんでしたが、概念は上記のリンクに似ています。
または、同様の投稿の提案に従うこともできます。 Androidのスワイプレイアウトで閉じる 希望の結果を得ることができます。
お役に立てれば。