Cover image preview Cover image

Adding gesture-based interaction to your website

by Gene — posted on 31 August 2018
Though the topic covered on this post might still be actual, this content referrers to an older version of zuix.js library. See zuix.js website for up-to-date documentation.

One of the common problems with desktop and mobile development is that, except for the 'click' event, mouse events will not work on mobile and since they are touch-based devices, a different set of events must be used.

Common mouse events

Common touch events

So, to implement custom interaction in a website that works both on desktop and mobile, it will require taking care of both mouse and touch events.

And this can get even worse if we consider that the mouse and touch screen are not the only methods available for interacting within the digital world.

Mouse, touch-screen, your hand, your eyes or your whole body could all be considered a possible interaction medium.

This is where the abstraction to a gesture-based model can come in handy and create a common way to interact with user interfaces regardless of the device being used.

The Gesture Helper

To add gesture interaction to a web page we will be using the gesture_helper component. This can be used on any HTML element to detect gestures over it.

Recognized gestures

Since this component is implemented using zuix.js, first we need to include the library:

<script src="https://cdn.jsdelivr.net/npm/zuix-dist@1.0.0/js/zuix.min.js"></script>

Next we can load the gesture_helper component over the element either by using just HTML (data-ui-load attribute) or with JavaScript. Since JavaScript is required to handle the events anyway, let's load the component using the zuix.load(..) method:

HTML element

<div data-ui-field="surface"></div>

JavaScript

let surface = zuix.field('surface');
zuix.load('@lib/controllers/gesture_helper', {
  view: surface, // <- detect gestures over the given element
  on: {
    'gesture:touch': function(e, tp) {
      // handle gesture ...
    },
    'gesture:tap': function(e, tp) {
      // handle gesture ...
    },
    'gesture:pan': function(e, tp) {
      // handle gesture ...
    },
    'gesture:swipe': function(e, tp) {
      // handle gesture ...
    },
    'gesture:release': function(e, tp) {
      // handle gesture ...
    }
  }
});

With this little snippet of code, we are ready to handle gesture events over the element. Each event will pass to the handler function (callback) a tp (touch pointer) object that contains a handful of data that can be used to animate the target element:

tp = {
  // time frame
  startTime,
  endTime,
  // initial touch position
  startX,
  startY,
  // relative movement
  shiftX,
  shiftY,
  // actual direction, speed, position
  direction, // 'left' | 'right' | 'up' | 'down'
  velocity, // pixels per milliseconds
  x: x,
  y: y,
  // guessed scrolling direction
  scrollIntent(),  // false | 'horizontal' | 'vertical'
  // original event + cancel method
  event,
  cancel()
};

You can see a full example in the codepen below:

See the Pen Gesture Helper by g-labs (@genielabs) on CodePen.

In this example there are two instances of the gesture_helper being loaded.

The first one is loaded on the main surface, and it is used to detect pan gestures. Pan gesture is when you touch and drag the pointer over the surface.

The second one is loaded on the ball object, and it is used to detect touch and tap gesture. When the ball object is touched a .touched class is added to it. So the function that handles the pan gesture on the surface will start shifting the ball if the .touched class is present on it. Tapping the ball will make it bounce. Tap gesture is when you touch and then release right after.

Conclusions

Yes I called this gesture_helper a "component", but to be accurate it is a controller.

The difference between a component and a controller, is that the first one also ships with its piece of user interface (the HTML view), while the latter it's a JavaScript code only component that can be loaded over any HTML element.

For this reason a controller can be considered as framework-agnostic (despite someone may not agree with this definition). For example, you can use a zuix.js controller on a React or Vue component or a Bootstrap based website.

Another feature of zuix.js controllers is that you can load as many controllers as you want on the same element. So not only can you add the gesture_helper, but you can also add a controller implementing some physics based reaction or any other interaction logic (e.g. even simple things like validation of an input field). You can bring elements to life without interferences on the UI side.

-~=(glabs.it)=~- Home | Posts | About |