Implementing Swipe Gestures for WaveMaker Widgets

OVERVIEW & PURPOSE

When you are building a web responsive or mobile app, the components used in your app could respond to gestures and render their states accordingly. For example, if you use tabs in your app, on swipe left  from one tab you could allow the user to navigate to the subsequent tab. To implement this functionality, as a developer you need to integrate the touch events and based upon the swipe direction, distance and speed, you would write the rendering logic for the component.

In an endeavour to providing a native gesture experience in your hybrid mobile apps, WaveMaker has come up with a framework for integrating gestures with HTML5/JS components. The gesture-based interactions for widgets can be easily built as a layer on top of the existing component by using this framework.

In this article we will give an overview of this framework and how it can be applied to a WaveMaker widget - Carousel.

SWIPEY Plugin

Swipey is a jQuery plugin for swipe gestures. The plugin can be included in any project and swipe can be applied on any element. This plugin exposes a swipey method to add swipe functionality on the element. The swipey method accepts an object as shown below:

$ele.swipey({
   'direction': $.fn.swipey.DIRECTIONS.HORIZONTAL,
   'threshold': 5,
   'onSwipeStart': function () {},
   'onSwipe': function () {},
   'onSwipeEnd': function () {},
}];

Once the finger touch is moved beyond the threshold value, touch event is recognised as a swipe event and swipeStart is triggered. When the finger touch leaves the screen it is recognised as end of swipe triggering the swipEnd.

To add swipe functionality, invoke swipeAnimation() on the jQuery element. This method accepts an object, with each property defined for specific purpose such as bounds, context used for animation etc.

$ele.swipeAnimation({
   'threshold': 5,
   'bounds': function () {},
   'context': function () {},
   'animation': {},
   'onLower': function () {},
   'onUpper': function () {},
}];

Element can be swiped between the upper or lower positions from the center. These positions are called as bounds. Lower bound is the relative distance the element can be moved from the its current position (i.e. center) in the left or lower direction. Similarly, Upper bound is also the relative distance the element can be moved from the its current position. (i.e. center) towards the right or upper direction. Through the Swipey plugin we can specify an animation for multiple target elements, by having an array of objects passed to animation property.

SWIPEY with Carousel Component

Let us use Swipey to build Carousel component. Carousel with set of images can be swiped to animate to next or previous carousel content.

The active carousel that is on the screen is at center: 0, whereas the previous carousel content is at left: -100% (left item) and next carousel content is at 100% (right item). On swipe, these three carousel content areas have to be translated using CSS transform. Hence, animation applied on the elements will be:

'animation': [{
   'target': function() {
         //To return the carousel content elements
   },
   'css': {
       'transform': 'translate3d(${{ (($D + $d) / w) * 100 + \'%\'}}, 0, 0)'
   }
}]

Where the function() returns the jQuery element having three carousel contents, as the CSS animation has to be applied on all the three carousel content areas.

In the above snippet, CSS property in animation is using “w”, “$D”, “$d” where w is the width of a single carousel content. $D, $d are the values which determine the current position and distance moved from the center, computed by the plugin and can be used during animation.

'context': function () {
   return {
       'w': state.width
   };
}

Setting the bounds for Carousel:

1. Let us consider the Carousel at centre position 0 i.e center: 0

wavemaker widgets

2. It can be either moved towards right or left with a distance equivalent to Carousel’s width in order to navigate to previous or next item as shown in the figure.

Implementing Swipe gestures

3. Current Carousel item has to be swiped to distance equivalent to width i.e. from left to right to navigate to previous content. Hence current position is centre i.e. center: 0 and this can be swiped till upper value (i.e. width) so upper bound value is width.

swipe gestures for wavemaker widgets

4. Similarly, Carousel can be swiped from right to left to navigate to next carousel item. Hence to navigate to next carousel item, carousel item can be moved from the center to lower value with distance equivalent to its width in the negative scale. Lower bound value is -width.

implementing swipe gestures

5. Hence, bounds for the carousel item can be written as

 {
“lower” : -width,
“center”: 0,
“upper”: width
                }

'bounds': function () {
   var items = this.find('.app-carousel-item');

    if (!state.width) {
       state.width = items.width();
   }

   // bounds: element can be swiped up to its width.
   return {
       'lower': -state.width,
       'center' : 0,
       'upper': state.width
   };
}

Callbacks when lower or upper bound is reached

These can be used to define the behavior of the Carousel when the bounds are reached.

 'onLower': function () {
       //Lower bound is reached
   },
   'onUpper': function () {
       //Upper bound is reached
   }

Conclusion

Thus, without having to modify the underlying component swipe gestures can be applied using the Swipey animation framework. This can be extended to widgets like Carousel, Tabs, List etc.