Today's MVP Monday post comes from French Surface: Development MVP Nicolas Calvi and is provided in both French and English.
Bases de la programmation tactile avec WPF4 et le SDK
- Gestuelles
- Programmation tactile avec WPF 4
- Extension de la programmation avec le SDK Surface 2.0
- Intégration avec MVVM
Dans cet article on va aborder quelques approches basiques pour bien débuter avec la programmation tactile sous Windows 7. Que ce soit avec WPF 4 ou avec le SDK Surface 2.0, il faut bien comprendre en quoi ces deux technologies nous servent pour créer des interfaces tactiles intuitives.
Les Gestuelles:
Avant toute chose, il faut déjà bien comprendre qu’en programmation tactile on ne parle pas de clavier et de souris. Faire du tactile c’est faire des interfaces naturelles (NUI pour Natural User Interface). Dans ce cas, on parle de gestuelles. Cela va de la plus simple avec le contact basique (figure A) jusqu’à des choses plus complexes comme le zoom (figure D et E).
Dans la figure 1, on peut voir le contact (Figure 1-A), la rotation (Figure 1-B), le déplacement (Figure 1-C) et le zoom (Figure 1-D et 1-E). Ce sont les gestuelles les plus couramment utilisées, elles couvrent une utilisation largement suffisante pour la grande majorité des applications tactiles.
Il faut donc, quand on réalise une application de ce type, résonner avec ces gestuelles et oublier les interfaces GUI (Graphic User Interface) qu’on utilise habituellement. Fini donc les menus ou les fenêtres modales, on doit penser que c’est le doigt qui contrôle l’interface. Il est important de bien penser nos applications pour que les zones de contacts soient suffisamment grandes, que les objets manipulés soit cohérents et intuitifs. Il est généralement fortement recommandé de faire appel à un Designer Industriel et Interactif afin de réaliser le Design de l’application pour ensuite mettre en image celle-ci avec l’aide d’un graphiste. Ces métiers bien différents ne sont pas à négliger si vous voulez une application cohérente et intuitive.
Il est donc important de comprendre qu'une application tactile reste une application NUI et doit répondre à des normes en termes d'expérience utilisateur. Le fait de faire une application intuitive et ludique est toujours le fruit d'une profonde réflexion en début de projet. Il ne faut pas perdre de vue qu'un périphérique tactile s'utilise d'une certaine façon et qu'il faut nécessairement revoir le Design d'une application quand on la porte d'une tablette vers une table Microsoft® Surface® 2.0 par exemple.
Programmation avec WPF 4 :
Pour le développement on utilise WPF 4 sous Visual Studio 2010 qui permet la réalisation d’applications tactiles sous Windows 7. La gestion du tactile fonctionne à première vue comme la gestion de la souris, il suffit de remplacer le pointeur de la souris par un doigt qui fait contact avec une surface tactile. Pour cela, chaque « UIElement » possède une série d’événements sur lesquels on peut se brancher : TouchDown, TouchUp, TouchMove, TouchLeave et TouchEnter.
Ces événements s’utilisent comme ceux de la souris, à savoir quand un contact se produit (TouchDown), quand ce contact bouge (TouchMove), quand il disparait de la surface tactile (TouchUp), mais aussi quand il entre ou sort d’un élément graphique (ToucheEnter, TouchLeave). Jusque-là rien de bien compliqué, il suffit sur le callback de l’événement de récupérer dans l’argument les coordonnées du contact pour pouvoir le traiter.
Ceci est pour l’accès bas niveau des contacts. Si on devait par exemple essayer de savoir si un utilisateur fait un zoom dans notre application, il faudrait donc commencer à créer une classe qui permettrait de gérer cette
gestuelle : à savoir traquer les contacts sur l’élément, faire un historique de leurs déplacements pour ensuite les analyser et déterminer si la gestuelle a eu lieu. Fort heureusement pour nous, Microsoft nous épargne ce dur labeur en intégrant dans chaque « UIElement », une classe qui permet de scruter les gestuelles de la figure 1.
Cette classe est la classe « Manipulation ». Chaque « UIElement » possède une instance de cette classe et il suffit de mettre la propriété « IsManipulationEnabled » à vraie pour activer cette fonctionnalité. Une fois ceci fait, on a accès à d’autres événements : ManipulationStarting, ManipulationStarted, ManipulationDelta et ManipulationCompleted.
Quand des contacts sont détectés (TouchDown) sur l’élément, la manipulation est initialisée et l’événement « ManipulationStarting » est levé. Dans le callback de cet évènement, on va indiquer quelle gestuelle on va suivre (une translation, un zoom, une rotation), quel élément graphique va nous servir de référentiel pour la manipulation ou encore le point de pivot pour la rotation. Une fois ces informations traitées l’événement « ManipulationStarted » est levé pour indiquer que les manipulations sont sous surveillance avec les paramètres indiqués précédemment.
Une fois cette initialisation terminée, un événement va être levé régulièrement tout au long de la manipulation, il s’agit de « ManipulationDelta ». Celui-ci va nous notifier de tous les changements liés aux gestuelles en cours de reconnaissances. Les informations fournies sont complètes car elles tracent autant le changement depuis le dernier « ManipulationDelta » levé que les changements globaux depuis le début de la manipulation. Le plus intéressant est que si des contacts s’ajoutent ou se retirent pendant la manipulation, ils seront traités et les informations de la manipulation seront mises à jour également.
Pour finir, quand plus aucun contact ne sera sur l’élément, on considèrera que c’est la fin de la manipulation, l’événement « ManipulationCompleted » sera donc levé. A ce moment-là, il sera possible de gérer de l’inertie avec l’objet manipulé en fonction de sa dernière position. Pour cela, il suffit d’implémenter l’événement « ManipulationInertiaStarting ». Dans celui-ci il suffira de renseigner les « Behaviors » pour le traitement de l’inertie.
Prenons pour exemple un rectangle dans un « Canvas » :
Voici le code pour faire en sorte que si on touche au rectangle il se comporte dans un « ScatterView » (contrôle qui permet de manipuler des objets naturellement sur une surface tactile).
Voici donc une première approche des possibilités tactile de WPF 4 sous Windows 7 à savoir la gestion des contacts mais aussi des manipulations les plus courantes. Pour étendre ce modèle, Microsoft a mis à disposition le SDK Surface 2.0 qui ajoute des APIs pour la gestion des contacts, c’est le point que nous allons aborder maintenant.
Programmation avec le SDK Surface 2.0 :
Tout d’abord, il faut bien comprendre la philosophie de ce SDK que l’on peut résumer par « Write once - touch anywhere ». En effet, comme son nom ne l’indique pas, ce SDK peut être utilisé par tous les périphériques tactiles compatibles Windows 7. C’est une chose importante car tout code écrit avec ce SDK sera portable à l’identique (en terme d’exécution) sur les autres supports compatibles : Tablette, écrans tactile, Microsoft® Surface® 2.0.
Dans un second temps, ce SDK apporte des contrôles complémentaires pour la gestion des applications tactiles, ces contrôles sont préfixés par « Surface ». Il y a donc des contrôles retravaillés (SurfaceButton, SurfaceScrollViewer, SurfaceListBox, SurfaceWindow, etc.) qui viennent en remplacement des contrôles WPF 4, mais aussi de nouveaux contrôles (ScatterView, TagVisualizer, etc.) qui traduisent les nouveaux usages liés à ce type de périphérique.
Dans les faits, le SDK Surface 2.0 va étendre les possibilités de WPF 4. Par exemple, sur les événements de contact (TouchDown, TouchUp, etc.) l’argument contiendra de nouvelles API sous formes d’actions et d’informations. Pour cela, un peu comme pour les extensions « Linq » on doit ajouter à notre classe la référence de l’assembly « Microsoft.Surface.Presentation.Input » ce qui va permettre d’étendre l’une des propriétés de « TouchEventArgs » à savoir le « TouchDevice ».
Une fois étendu, il sera possible de savoir de quoi est capable le périphérique tactile. En effet un écran tactile simple (qui ne peut reconnaitre qu’un seul contact) n’a pas les mêmes possibilités qu’une table Microsoft® Surface® 2.0 (reconnaissance des tags, orientation des contacts). Par exemple, la nouvelle classe « InteractiveSurface.PrimarySurfaceDevice » permet de connaître ces fameuses capacités :
IsFingerRecognitionSupported: Permet de savoir si le périphérique est capable d’identifier la différence entre un doigt posé sur celle-ci ou un objet quelconque. La table Microsoft® Surface® 2.0 par exemple en est capable, mais si d’autres périphériques peuvent le faire, ils peuvent le signaler par cette fonction.
IsTagRecognitionSupported: Permet de savoir si le périphérique à la possibilité de reconnaitre des « Tags » (comme Microsoft® Surface® 2.0).
IsTiltSupported: Permet de savoir si le périphérique est inclinable (comme Microsoft® Surface® 2.0).
IsTouchOrientationSupported: Permet de savoir si le périphérique peut tracer l’orientation d’un contact sur celui-ci (comme Microsoft® Surface® 2.0), à savoir l’angle qu’il forme avec le point zéro de la zone tactile.
IsTouchBoundsSupported: Permet de savoir si le périphérique peut connaitre la surface de contact (comme Microsoft® Surface® 2.0), c’est-à-dire la forme et l’aire de ce qui touche le périphérique.
Il suffit juste donc d’interroger cette classe pour savoir si certaines actions sont réalisables. De même, on peut, sur chaque contact, via la classe d’argument des événements de contact (TouchUp, TouchDown, etc.), savoir si le contact est d’un type particulier (doigt, tag, etc.) et en récupérer les informations. Par défaut, il faut tester les capacités avant de les invoquer car votre code peut être exécuté sur des périphériques complétement différents.
Le développement est ensuite assez similaire par rapport à WPF 4. Il existe cependant des extensions pour gérer des gestuelles simples comme le « Tap » ou le « Hold » et qui sont fournies dans le SDK de cette façon :
Cela permet de se brancher facilement sur ces gestuelles courantes, ce que ne permettait pas WPF 4.
Il faut donc voir ce SDK comme un complément très utile qui fournit tout ce qu’il manquait à WPF4, tout en préparant l’arrivé de la table Microsoft® Surface® 2.0.
Information Importante :
Il faut savoir qu’avec WPF 4, si l’on active la manipulation sur un élément (« IsManipulationEnabled »), ses enfants ne recevront plus l’événement « TouchUp », ce qui peut être problématique notamment avec le SDK Surface 2.0. Si on place des éléments dans un « SurfaceScrollViewer » par exemple, il n’est plus possible d’intercepter le « TouchUp » dans les éléments qu’il contient, et ce car il implémente la manipulation. De ce fait, le « Behavior » « s:TouchExtensions.TapGesture » ne fonctionnera pas.
Intégration avec le pattern MVVM :
Une problématique importante est la gestion des gestuelles avec un pattern de type MVVM, à savoir comment lié l’interface (Vue) avec son ViewModel. La solution est très simple : un « Behavior » (ajouter l’assembly « System.Windows.Interactivity »). Pour cela il suffit d’en créer un très simple :
La commande étant un mécanisme courant de gestion des informations entre la « View » et le « ViewModel », en créant ce « Behavior », il devient très simple de faire le pont. Dans la méthode « OnAttached », il suffit de se brancher sur les événements de manipulations grâce à la propriété « AssociatedObject ».
Quand on a fini de traiter la gestuelle, il suffit d’invoquer la commande avec la fonction « ManipulationDetected ». C’est aussi simple que ça. Pour déclarer le « Behavior » sur son objet il suffit de faire comme ceci :
En conclusion, la programmation tactile via WPF 4 ou le SDK Surface 2.0 est très accessible. Elle repose sur les mêmes fondements que la programmation GUI classique avec l’adaptation des interactions (ici plus de souris ni de clavier, mais nos doigts). Le but restant, au final, de concevoir les applications pour qu’elles soient intuitives et accessibles.
English Translation:
Basis of tactile programming with WPF4 and Surface 2.0 SDK
- Gestures
- Tactile programming with WPF 4
- Programing extension with Surface 2.0 SDK
- Integrating with MVVM
In this article we will discuss some basic approaches to get started with tactile programming under Windows 7. Whether it is with WPF 4 or Surface SDK 2.0, it is important to understand how these two technologies are used to create intuitive touch interfaces.
Gestures:
First of all, we must understand that in touch programming we don’t talk about keyboards, mouse clicks or other interactions with these two devices. Programming in "tactile" is creating natural interfaces (NUI for Natural User Interface). In this case we talk about gestures, this goes from simple contact “tap” (figure A) to more complex things such as zooms (Figure D and E).
In figure 1, we can see the simple contact named “tap” (Figure 1-A), rotation (Figure 1-B), move (Figure 1-C), zoom in (Figure 1-D), zoom out (Figure 1-E). These gestures are the most commonly used, they are sufficient for the great majority of touch applications.
Therefore, when you create this type of application you must use those gestures and forget the menus and modal windows usually used on GUI (Graphic User Interface). You must think for finger interactions and not for mouse interactions. It’s important to create big enough contacts areas so that the objects are easily movable with a finger. Objects must be intuitive so that the understanding of the object induces the required gesture. So it is generally recommended to hire an Industrial & Interaction Designer for the concept, gestures and interaction and a Graphic Designer to create the visual (color and layout). These two different skills are determinative if you want to produce an intuitive and consistent application.
It is important to understand that in the case of touch technology, we are concerned with NUI applications. This leads to an adherence to standards and the inclusion of constraints in terms of user experience. To make an application intuitive and fun, a reflection period at the beginning of the project is fundamental. We must not forget that a touch device is used in a precise way. It is above all, necessary to review the design of an application when one converts it from a tactile tablet to Microsoft Surface 2.0 for instance.
Programming with WPF 4 :
The basis of this programming uses a WPF 4 project, which allows the developement of touch application on Windows 7. Tactile handling works in the same way as mouse handling, you just need to replace the mouse pointer with a finger on a tactile surface. So each “UIElement” has a set of events to which you can subscribe: TouchDown, TouchUp, TouchMove, TouchLeave and TouchEnter.
These events behave like mouse events: when a contact occurs (TouchDown), when this contact moves (TouchMove), when it disappears from the tactile surface (TouchUp), also when it enters or leaves a graphical element (TouchEnter, TouchLeave). Nothing to complex here, you just need to get the contact coordinates in the argument of the event callback to handle it.
This is for the low-level contact access. But if, for instance, you want to know if a user is zooming, you would have to create a new class to handle this gesture. This class should look for all contacts on the element, back up and analyze all theirs moves to then find out if the gesture occurred. Fortunately, Microsoft spares us this hard work by building a class in each “UIElement” to examine all the gestures you have seen in figure 1.
This class is the “Manipulation” class. Each “UIElement” owns an instance of this class and you just need to set the “IsManipulationEnabled” property to true to get this functionality. Once done, you have access to more events: ManipulationStarting, ManipulationStarted, ManipulationDelta and ManipulationCompleted.
When contacts are detected (TouchDown) on an element, the manipulation is initiated and the event “ManipulationStarting” is raised. In the event callback, you have to tell the object which gesture you are expecting (translation, zoom or rotation), which graphical element is the referential for the manipulation or what is the rotation pivot point. Once that information handled the “ManipulationStarted” event is raised to notify that the manipulation are monitored with the parameter previously set.
Once this initialization done, the “ManipulationDelta” event is regularly raised during the manipulation. This one will notify every change about currently monitored gestures. The information provided are complete because it provides all changes from the beginning of the manipulation and from the last ManipulationDelta raised. The most interesting is if new contact are made or removed during the manipulation, they are handled and information is updated.
Finally when no contact remains on the element, the manipulation is considered completed and the “ManipulationCompleted” event is raised. From this moment, it’s possible to handle inertia with the manipulated object depending on its last position. To do so, you just need to handle the “ManipulationInertiaStarting” event. In this handler, you need to give information about the inertia behavior.
Let’s take a rectangle in a “Canvas” as example:
Here is the code to make sure that the rectangle behaves like it was in a “ScatterView” (control allowing natural object manipulation on a tactile surface).
Here is a first approach of WPF 4 tactile possibilities on Windows 7, that is to say contacts but also widely used manipulation handling. To extend this model, Microsoft released the Surface SDK 2.0 which adds APIs for contact handling, that’s the next topic.
Programming with Surface SDK 2.0:
First of all, you have to understand the SDK philosophy that can be summarized with “Write once – touch anywhere”. Indeed, as its name doesn’t tell, this SDL can be used by all tactile devices Windows 7 compatible. That’s important because all the code written with this SDK can be identically executed on any compatible support: tablet, tactile screen, Microsoft® Surface® 2.0.
Secondly, this SDK bring complementary controls for tactile application management, those controls are prefixed with “Surface”. There are reworked controls (SurfaceButton, SurfaceScrollViewer, SurfaceListBox, SurfaceWindow, etc.) which replace WPF 4 usual controls, but also new controls (ScatterView, TagVisualizer, etc.) which translate new usages for those devices.
In facts, Surface SDK 2.0 is extending WPF 4 possibilities. For example, on contact events (TouchDown, TouchUp, etc.), the argument provides new API as actions and information. Like “linq” extensions, you have to add the “Microsoft.Surface.Presentation.Input” referenced assembly to your class. This will extend a “TouchEventArgs” property called “TouchDevice”.
Once extended, it will be possible to know what the tactile device supports. Indeed a simple tactile screen (which can only recognize one finger) won’t have the same possibilities as a Microsoft® Surface® 2.0 (tag recognition, contact orientation). For example, the new “InteractiveSurface.PrimarySurfaceDevice” class lets you know those capabilities:
IsFingerRecognitionSupported: Lets you know if the device can make the difference between a finger and any object. The Microsoft® Surface® 2.0 table can do this for example. But if another device can, it can report it with this function.
IsTagRecognitionSupported: Lets you know if the device can recognize « Tags » (like Microsoft® Surface® 2.0).
IsTiltSupported: Lets you know if the device support tilt (like Microsoft® Surface® 2.0).
IsTouchOrientationSupported: Lets you know if the device can define the contact orientation (like Microsoft® Surface® 2.0), that is to say the angle it forms with the zero point of the touch area.
IsTouchBoundsSupported: Lets you know if the device can know the contact area surface (like Microsoft® Surface® 2.0), ie the form and area of what touches the device.
You just need to ask this class to know if some actions are feasible. The same, via the contact event argument class (TouchUp, TouchDown, etc.), you can know for each contact if it’s a particular type (finger, tag, etc.) and get information about it. By default, you have to test every capability before using it because your code can be executed on any device.
The development is then similar to WPF 4. However, you can use some extensions provided by the SDK to handle simple gestures like “Tap” or “Hold” like that:
This lets you handle simple, commonly used gestures, which you couldn’t do with WPF 4.
So, this SDK can be seen as a useful WPF 4 complement which provides every feature needed while preparing Microsoft® Surface® 2.0 table release.
Important information:
You need to know that with WPF 4, if the manipulation is enabled on an Element (“IsManipulationEnabled”), its children won’t receive the “TouchUp” event, which can be problematic especially with the Surface SDK 2.0. If you have some element inside a “SurfaceScrollViewer” for example, it’s not possible to catch the “TouchUp” event on those elements, and this because its implements the manipulation. Thus, the “s:TouchExtensions.TapGesture” behavior won’t work.
MVVM pattern integration:
A big problematic is gesture handling using an MVVM pattern, that is to say, how to link the interface (View) with its ViewModel. The solution is easy: a Behavior (adding “System.Windows.Interactivity” assembly). For that, you just need to create a new simple behavior:
The mechanism command being a common handler for information between the View and the ViewModel, by creating this Behavior, it becomes easy. In the “OnAttached” method, you need to subscribe to the manipulation events thanks to the “AssociatedObject” property.
When the gesture is done treated, you just need to invoke the command with the “ManipulationDetected” function. It's that simple. To declare the behavior on its object, you need to do like that:
To conclude, tactile programming with WPF 4 and Surface SDK 2.0 is really accessible. It remains on the same foundations as classical GUI programming with interaction adaptation (here no more mouse or keyboard, only fingers). The goal remains, ultimately, to design applications so that they are intuitive and accessible.
Author's Bio
Nicolas Calvi is a consultant and trainer for Winwise. Winwise is a French company specialized in Microsoft technologies. His fields of expertise are the natural interfaces such as Microsoft® Surfaces® or Kinect® and the multidisciplinary Agile methodologies. He brings his expertise to companies in order to create rich intuitive interfaces. For this, he places the user in the center of all the concerns during conception. He shares his experience within his "Black Blog" (http: // blog.nicolascalvi.com) as well as on Twitter via @nicolascalvi.
Nicolas Calvi est Consultant / Formateur pour Winwise une société Française spécialisé dans les technologies Microsoft. Ses domaines d’expertises sont les interfaces naturelles comme Microsoft® Surface® ou Kinect® et les méthodologies Agile pluridisciplinaires. Il apporte son expertise aux entreprises pour créer des interfaces riches intuitive et replace l’utilisateur au centre des préoccupations de conception. Il partage son expérience au sein de son « Black Blog » (http://blog.nicolascalvi.com) ainsi que sur Twitter via @nicolascalvi.
MVP Mondays
The MVP Monday Series is created by Melissa Travers. In this series we work to provide readers with a guest post from an MVP every Monday. Melissa is a Community Program Manager for Dynamics, Excel, Office 365, Platforms and SharePoint in the United States. She has been working with MVPs since her early days as Microsoft Exchange Support Engineer when MVPs would answer all the questions in the old newsgroups before she could get to them.