简体   繁体   中英

Xamarin.Forms Gesture on Android

It's possible to swipe page like on SnapChat using Gesture? I have something like this, but it's not working. Of course I got Interface and class but i don't know how to implement it that everything works good. I want to swipe form left side page and right side page like on SnapChat and changing color background while swipe.

  SwipeListener swipeListener = new SwipeListener(przeglad, this);

  public void onLeftSwipe(View view)
    {
        if (view == przeglad)
        {
            Page ne = new SrchPage();
        }
    }

Interface:

public interface ISwipeCallBack
{
    void onLeftSwipe(View view);
    void onRightSwipe(View view);
    void onTopSwipe(View view);
    void onBottomSwipe(View view);
    void onNothingSwiped(View view);
}

Swipe Class:

 public class SwipeListener : PanGestureRecognizer
{

    private ISwipeCallBack mISwipeCallback;
    private double translatedX = 0, translatedY = 0;

    public SwipeListener(View view , ISwipeCallBack iSwipeCallBack)
    {

        mISwipeCallback = iSwipeCallBack;
        var panGesture = new PanGestureRecognizer();
        panGesture.PanUpdated += OnPanUpdated;
        view.GestureRecognizers.Add(panGesture);
    }

    void OnPanUpdated(object sender, PanUpdatedEventArgs e)
    {

        View Content = (View)sender;

        switch (e.StatusType)
        {

            case GestureStatus.Running:

                try
                {
                    translatedX = e.TotalX;
                    translatedY = e.TotalY;
                }
                catch (Exception err)
                {
                    System.Diagnostics.Debug.WriteLine("" + err.Message);
                }
                break;

            case GestureStatus.Completed:

                System.Diagnostics.Debug.WriteLine("translatedX : " + translatedX);
                System.Diagnostics.Debug.WriteLine("translatedY : " + translatedY);

                if (translatedX < 0 && Math.Abs(translatedX) > Math.Abs(translatedY))
                {
                    mISwipeCallback.onLeftSwipe(Content);
                }
                else if (translatedX > 0 && translatedX > Math.Abs(translatedY))
                {
                    mISwipeCallback.onRightSwipe(Content);
                }
                else if (translatedY < 0 && Math.Abs(translatedY) > Math.Abs(translatedX))
                {
                    mISwipeCallback.onTopSwipe(Content);
                }
                else if (translatedY > 0 && translatedY > Math.Abs(translatedX))
                {
                    mISwipeCallback.onBottomSwipe(Content);
                }
                else
                {
                    mISwipeCallback.onNothingSwiped(Content);
                }

                break;

        }
    }

}

XML:

<Grid RowSpacing="10" Padding="30" VerticalOptions="Center"  x:Name="przeglad">

            <Grid.RowDefinitions>
                <RowDefinition Height="Auto"/>

                <RowDefinition Height="Auto"/>
                <RowDefinition Height="Auto"/>

                <RowDefinition Height="Auto"/>
                <RowDefinition Height="Auto"/>
            </Grid.RowDefinitions>

             <Button  Grid.Row="2"  Text="{resource:TranslateExtension Szukaj}"
                BorderRadius="30"
                BackgroundColor="#80FFFFFF"

                FontSize="18"
                TextColor="#330025"
                BorderWidth="4"
                BorderColor="#ffdbdb"
                Clicked="Button_Clicked_1"
              FontAttributes="Bold"/>

             <Button  Grid.Row="3"  Text="{resource:TranslateExtension Mapa}"
                BorderRadius="30"
                BackgroundColor="#80FFFFFF"
                FontSize="18"
                TextColor="#330025"                    
                BorderWidth="4"
                BorderColor="#ffdbdb"
                Clicked="Button_Clicked"
               FontAttributes="Bold"/>

        </Grid>

I think what you need is a ViewPager which covers on your original view with transparent background.

For example create your layout like this:

<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
  <ImageView
      android:id="@+id/img"
      android:layout_height="match_parent"
      android:layout_width="match_parent"
      android:src="@drawable/BG" />
  <android.support.v4.view.ViewPager android:id="@+id/viewpager"
                                     android:layout_height="match_parent"
                                     android:layout_width="match_parent"
                                     android:background="@android:color/transparent" />
</FrameLayout>

In code behind create an adapter for ViewPager first:

public class MyVPAdapter : PagerAdapter
{
    private Context context;
    private List<PItemModel> list;

    public MyVPAdapter(Context _context, List<PItemModel> _list)
    {
        context = _context;
        list = _list;
    }

    public override int Count
    {
        get { return list.Count; }
    }

    public override bool IsViewFromObject(View view, Java.Lang.Object obj)
    {
        return view == obj;
    }

    public override void DestroyItem(View container, int position, Java.Lang.Object view)
    {
        var viewpager = container.JavaCast<ViewPager>();
        viewpager.RemoveView(view as View);
    }

    public override Java.Lang.Object InstantiateItem(View container, int position)
    {
        ImageView tile = new ImageView(context);
        tile.SetImageResource(list[position].TileId);
        var viewpager = container.JavaCast<ViewPager>();
        viewpager.AddView(tile);
        return tile;
    }
}

In Code behind:

protected override void OnCreate(Bundle savedInstanceState)
{
    base.OnCreate(savedInstanceState);

    // Create your application here
    SetContentView(Resource.Layout.layout2);

    ViewPager pager = FindViewById<ViewPager>(Resource.Id.viewpager);
    List<PItemModel> list = new List<PItemModel>();
    list.Add(new PItemModel() { TileId = Resource.Drawable.BackButton });
    list.Add(new PItemModel() { TileId = Resource.Drawable.solidimg });
    var adapter = new MyVPAdapter(this, list);
    pager.Adapter = adapter;
} 

The PItemModel is simple like this:

public class PItemModel
{
    public int TileId { get; set; }
}

Last problem, the link you provided in the comment of your last case likes adding tile on photo, the ViewPager should be placed over TextureView which is used for presenting the camera stream. Here I only used a ImageView for demo.

Update:

Sorry, I just realized that you're using XF for development, than you should be able to create Custom Renderer for a view, and implement the code above in Android client project, the code in OnCreate should be moved into the implementation of view renderer in client project.

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