B4A Library [B4X] [XUI] AS Swipe Card - a tinder like swipeable card view

Hello Community,

This library is not free, because, it cost a lot of time and gray hair to create such views.
Donations from 5€ or 6$ are valid. (You can donate any amount you want :))
Please write SwipeCard in the order description, thanks.

Thanks for your understanding. :)

This library is compatible and tested with B4A,B4I and B4J!
If you have bugs or a wish then tell me it in the comments.

Features
  • cross-platform compatible
  • enable or disable events
  • add and remove cards
  • scroll to cards
  • animations
  • swipe with fingers
  • and more...
sc_1.gif
sc_2.gif
Bildschirmaufnahme 2020-05-06 um 19.47.082.gif


On B4J and B4I you need a base panel, only this way the events can be triggered by your other control elements, see the example projects to learn more.

ASSwipeCard
Author: Alexander Stolte
Version: 1.06

  • ASSwipeCard
    • Events:
      • BaseResize (Width As Double, Height As Double)
      • IndexChanged (index As Int)
      • ReachEnd
      • SwipeStateChange (state As Int)
      • SwipeStateChanged (state As Int)
    • Functions:
      • AddCard (xpnl As B4XView, Tag As Object) As String
      • Class_Globals As String
      • Clear As String
        Clears all cards
      • DesignerCreateView (Base As Object, Lbl As Label, Props As Map) As String
        Base type must be Object
      • getBase As B4XView
      • GetCard (Index As Int) As B4XView
      • getCardBackground As B4XView
      • getSize As Int
      • getTag (Index As Int) As Object
      • IniParent (parent As B4XView) As String
      • Initialize (Callback As Object, EventName As String) As String
      • IsInitialized As Boolean
        Tests whether the object has been initialized.
      • NextCard (swipe_state As Int)
      • PreviousCard (swipe_state As Int)
      • RemoveCard (Index As Int) As String
      • setCurrentIndex (index As Int) As String
      • SwipeState_BOTTOM As Int
      • SwipeState_LEFT As Int
      • SwipeState_NEUTRAL As Int
      • SwipeState_RIGHT As Int
      • SwipeState_TOP As Int
      • SwipeStateRandom As Int
    • Properties:
      • Base As B4XView [read only]
      • CardBackground As B4XView [read only]
      • CurrentIndex
      • Size As Int [read only]
  • SwipeCardItems
    • Fields:
      • IsInitialized As Boolean
        Tests whether the object has been initialized.
      • Tag As Object
      • xpnl_cardbase As B4XView
    • Functions:
      • Initialize
        Initializes the fields to their default value.
Changelog
  • 1.00
    • Release
  • 1.01
    • Add Designer Property: EnableLeftRightSwipe -Enabled or Disabled the swipe gesture for left and right swiping
    • Add Designer Property: EnableTopBottomSwipe -Enabled or Disabled the swipe gesture for top and bottom swiping
  • 1.02
    • Add Event "SwipeStateChange" - Triggers when the card is moved with the finger in one direction e.g. LEFT,RIGHT,TOP,BOTTOM or NEUTRAL
    • Event "SwipeStateChanged" - Triggers now only when the user has released the card
    • Add Clear - clears all cards
  • 1.03
    • get CurrentIndex is now readable
  • 1.04
    • Add Designer Properties - If true then the previous card is shown as next card if you swipe in the right direction
      • SwipeLeft2Previous
      • SwipeRight2Previous
      • SwipeTop2Previous
      • SwipeBottom2Previous
  • 1.05
    • BugFixes for the Features of V1.04
  • 1.06
    • BugFix
  • 1.07
    • BugFix
Have Fun :)
@Alexander Stolte
 

Attachments

  • B4A Example.zip
    4.3 KB · Views: 335
  • B4I Example.zip
    6.7 KB · Views: 182
  • B4J Example.zip
    3.6 KB · Views: 195
  • ASSwipeCard.zip
    4.2 KB · Views: 25
Last edited:

Alexander Stolte

Expert
Licensed User
Update
  • 1.04
    • Add Designer Properties - If true then the previous card is shown as next card if you swipe in the right direction
      • SwipeLeft2Previous
      • SwipeRight2Previous
      • SwipeTop2Previous
      • SwipeBottom2Previous
Now, only issue which I see is when I slide to right (so I go one card back), then first is shown next card for a split of a second, and then it's replaced with previous one.
Any idea how to handle that?
I added this as an internal function, just set the designer property to "true" in the direction you want to show the previous card.
 

Drago Bratko

Member
Licensed User
Great, thank you.
I appreciate your support, and I have initiate second donation.

There is one more issue ... in my case, I would like that if one came to first card and swipe one more to right, that it goes to last one. And also if one goes to last card, and swipe left, that it goes to first card. So it would be like a loop.

I have done it in this way which is fine:
B4X:
Sub ASSwipeCard1_SwipeStateChanged(state As Int)
    If state = ASSwipeCard1.SwipeState_NEUTRAL Then
        Log("SwipeStateChanged: Neutral")
    else If state = ASSwipeCard1.SwipeState_TOP Then
        Log("SwipeStateChanged: Top")
        ASSwipeCard1.CurrentIndex = nCurrentIndex
        ToastMessageShow("LIKE", False)
    else If state = ASSwipeCard1.SwipeState_BOTTOM Then
        Log("SwipeStateChanged: Bottom")
        ASSwipeCard1.CurrentIndex = nCurrentIndex
        ToastMessageShow("DISLIKE", False)
    else If state = ASSwipeCard1.SwipeState_LEFT Then
        nCurrentIndex = CurIndexCalc(1)
        ASSwipeCard1.CurrentIndex = nCurrentIndex
    else If state = ASSwipeCard1.SwipeState_RIGHT Then
        nCurrentIndex = CurIndexCalc(-1)
        ASSwipeCard1.CurrentIndex = nCurrentIndex
    End If
End Sub

Sub CurIndexCalc(nValue As Int) As Int
    Dim nNewIndex As Int
    nNewIndex = nCurrentIndex + (nValue)
    If nNewIndex < 0 Then
        nNewIndex = ASSwipeCard1.Size -1
    Else If nNewIndex = ASSwipeCard1.Size Then
        nNewIndex = 0
    End If
    Return nNewIndex
End Sub

But, error happened in that edged cases
B4X:
Error occurred on line: 440 (ASSwipeCard)
java.lang.ArrayIndexOutOfBoundsException: length=33; index=-1
    at java.util.ArrayList.get(ArrayList.java:439)
    at anywheresoftware.b4a.objects.collections.List.Get(List.java:117)
    at softwise.swipe.example.asswipecard$ResumableSub_TouchHandler.resume(asswipecard.java:1887)
    at softwise.swipe.example.asswipecard._touchhandler(asswipecard.java:1267)
    at softwise.swipe.example.asswipecard._xpnl_cardbase_touch2(asswipecard.java:1993)
    at java.lang.reflect.Method.invoke(Native Method)
    at anywheresoftware.b4a.shell.Shell.runMethod(Shell.java:732)
    at anywheresoftware.b4a.shell.Shell.raiseEventImpl(Shell.java:351)
    at anywheresoftware.b4a.shell.Shell.raiseEvent(Shell.java:255)
    at java.lang.reflect.Method.invoke(Native Method)
    at anywheresoftware.b4a.ShellBA.raiseEvent2(ShellBA.java:144)
    at anywheresoftware.b4a.BA.raiseEvent(BA.java:176)
    at anywheresoftware.b4a.agraham.reflection.Reflection$7.onTouch(Reflection.java:1118)
    at android.view.View.dispatchTouchEvent(View.java:15195)
    ....

Thanks for checking it. :)
 

Drago Bratko

Member
Licensed User
you dont need this code, just check the following Designer Property: "Swipe Right 2 Previous"

Heh, you are right. Swipe works perfectly in both directions. :)

Now, only when I came to last card and try to go to next one that it goes to first one (like in circle).
And also, when I came to first card and try to go to previous one that it goes to last one (like in circle).

How do you suggest to implement it?
 

Drago Bratko

Member
Licensed User
Update
  • 1.05
    • BugFixes for the Features of V1.04

try it now.

Thank you.
Now I got this error :

B4X:
Error description: Undeclared variable 'swipecarditems' is used before it was assigned any value.
Error occurred on line: 334 (ASSwipeCard)
SwipeCardIemsList.Get(i).As(SwipeCardItems).xpnl_cardbase.Visible = False
 

Drago Bratko

Member
Licensed User
I don't have this error.
Do you have the latest version of the IDE?

☺️ You were right ... I didn't have latest IDE ... that solved issue with compiling.


But edge cases are still behaving same as before. (when I came to last card and try to go to next one and when I came to first card and try to go to previous one ... in both cases screen with no card is shown and no movements are possible any more).
 

Alexander Stolte

Expert
Licensed User
But edge cases are still behaving same as before. (when I came to last card and try to go to next one and when I came to first card and try to go to previous one ... in both cases screen with no card is shown and no movements are possible any more).
After all, that's the way it's meant to be. When this happens, you must decide what happens, you can then automatically display the 1st card or do something else.
No other card comes before the 1st card and the same after the last card. You have to decide what happens, the events work.
 

Drago Bratko

Member
Licensed User
After all, that's the way it's meant to be. When this happens, you must decide what happens, you can then automatically display the 1st card or do something else.
No other card comes before the 1st card and the same after the last card. You have to decide what happens, the events work.
OK, got it. I have implemented it in that way. Thank you.

Funny problem (still one) is that without problem I can reference to first card, but not to last card. Any idea why?

B4X:
    If state = ASSwipeCard1.SwipeState_LEFT Then
        If ASSwipeCard1.CurrentIndex = ASSwipeCard1.Size Then
            ASSwipeCard1.CurrentIndex = 0 ' that works
        End If
    else If state = ASSwipeCard1.SwipeState_RIGHT Then
        If ASSwipeCard1.CurrentIndex = -1 Then
            ASSwipeCard1.CurrentIndex = ASSwipeCard1.Size -2 ' that works
            'ASSwipeCard1.CurrentIndex = ASSwipeCard1.Size -1 ' that is not working
        End If
    End If
 

Drago Bratko

Member
Licensed User
looks like you reach the last card. I dont see a issue.

There are 25 cards in the deck.
I have swipe left 3 cards and then swipe one card right (back) ... and it went to that state.

If I swipe slowly (cca 1 sec per swipe) it's fine. But if I swipe faster like on the video, I can replicate it all the time.
Maybe it's related with that ...
 
Top