[#LEAPMOTION] HowTo: Show the number of fingers ever the Leap

Hello!

Today is going to be a quick post, I’ll change the console app for a WPF app to work with the Leap Motion. In this app, I’ll show how a gesture is detected by the sensor in addition to the amount of active fingers over the sensor. For this example I’ve used some information from in this post of the great Iris Classon to create the following listener

   1: using System;

   2: using System.Threading.Tasks;

   3: using Leap;

   4:  

   5: namespace LeapWpf01

   6: {

   7:     public class ElBrunoListener : Listener

   8:     {

   9:         public void Sample(){}

  10:         public event Action<FingerList> OnFingersRegistered;

  11:         public event Action<GestureList> OnGestureMade;

  12:         private long _now;

  13:         private long _previous;

  14:         private long _timeDifference;

  15:  

  16:         public override void OnInit(Controller controller) { }

  17:  

  18:         public override void OnConnect(Controller controller)

  19:         {

  20:             controller.EnableGesture(Gesture.GestureType.TYPECIRCLE);

  21:             controller.EnableGesture(Gesture.GestureType.TYPEKEYTAP);

  22:             controller.EnableGesture(Gesture.GestureType.TYPESCREENTAP);

  23:             controller.EnableGesture(Gesture.GestureType.TYPESWIPE);

  24:         }

  25:  

  26:         public override void OnDisconnect(Controller controller) { }

  27:  

  28:         public override void OnExit(Controller controller) { }

  29:  

  30:         public override void OnFrame(Controller controller)

  31:         {

  32:             var frame = controller.Frame();

  33:             _now = frame.Timestamp;

  34:             _timeDifference = _now - _previous;

  35:  

  36:             if (frame.Hands.IsEmpty) return;

  37:  

  38:             _previous = frame.Timestamp;

  39:             if (_timeDifference < 1000) return;

  40:  

  41:             // Run async

  42:             if (frame.Gestures().Count > 0)

  43:                 Task.Factory.StartNew(() => OnGestureMade(frame.Gestures()));

  44:             if (frame.Fingers.Count > 0)

  45:                 Task.Factory.StartNew(() => OnFingersRegistered(frame.Fingers));

  46:         }

  47:     }

  48: }

The listener is quite simple, public an event with the information captured by the LEAP every 1 second.

In the MainWindow of my WPF app, I have the following code. The only thing that must be taken into consideration, is that the best sensor initialization in the Loaded() event, and always with care for closing the View close the controller and the listener with the sensor.

   1: using System;

   2: using System.ComponentModel;

   3: using System.Diagnostics;

   4: using System.Runtime.CompilerServices;

   5: using System.Windows;

   6: using Leap;

   7: using LeapWpf01.Annotations;

   8:  

   9: namespace LeapWpf01

  10: {

  11:     public partial class MainWindow : INotifyPropertyChanged

  12:     {

  13:         private string _gesturesText;

  14:         private Controller _controller;

  15:         private ElBrunoListener _listener;

  16:         private string _fingersText;

  17:  

  18:         public MainWindow()

  19:         {

  20:             DataContext = this;

  21:             Loaded += MainWindow_Loaded;

  22:             Closing += MainWindow_Closing;

  23:             InitializeComponent();

  24:         }

  25:  

  26:         void MainWindow_Closing(object sender, CancelEventArgs e)

  27:         {

  28:             _controller.RemoveListener(_listener);

  29:             _controller.Dispose();

  30:         }

  31:  

  32:         void MainWindow_Loaded(object sender, RoutedEventArgs e)

  33:         {

  34:             _listener = new ElBrunoListener();

  35:             _controller = new Controller();

  36:             _controller.AddListener(_listener);

  37:             _listener.OnFingersRegistered += OnFingersRegistered;

  38:             _listener.OnGestureMade += OnGestureMade;

  39:         }

  40:  

  41:         void OnGestureMade(GestureList gestures)

  42:         {

  43:             var gesturesData = string.Empty;

  44:             foreach (var gesture in gestures)

  45:             {

  46:                 gesturesData += gesture.Type + Environment.NewLine;

  47:             }

  48:             GesturesText = gesturesData;

  49:         }

  50:  

  51:         void OnFingersRegistered(FingerList fingers)

  52:         {

  53:             FingersText = "Active Fingers:" + fingers.Count;

  54:         }

  55:     }

  56: }

Then, the functionality of the app is pretty straigh forward,

 

The sensor is OK, but in order to have something up and running, you have to work a lot. The SDK gives you raw information , so you have to work with this information to get cool results

Saludos @ Home

El Bruno

image image image Google

[#LEAPMOTION] HowTo: Mostrar la cantidad de dedos sobre el Leap

Hola!

Hoy vamos con un post de esos rápidos, en el que cambio una app de Consola por una app WPF y en la misma, muestro el gesto detectado por el sensor además de la cantidad de dedos activos. Para este ejemplo me he basado en este post de la crack Iris Classon para crear el siguiente listener

   1: using System;

   2: using System.Threading.Tasks;

   3: using Leap;

   4:  

   5: namespace LeapWpf01

   6: {

   7:     public class ElBrunoListener : Listener

   8:     {

   9:         public void Sample(){}

  10:         public event Action<FingerList> OnFingersRegistered;

  11:         public event Action<GestureList> OnGestureMade;

  12:         private long _now;

  13:         private long _previous;

  14:         private long _timeDifference;

  15:  

  16:         public override void OnInit(Controller controller) { }

  17:  

  18:         public override void OnConnect(Controller controller)

  19:         {

  20:             controller.EnableGesture(Gesture.GestureType.TYPECIRCLE);

  21:             controller.EnableGesture(Gesture.GestureType.TYPEKEYTAP);

  22:             controller.EnableGesture(Gesture.GestureType.TYPESCREENTAP);

  23:             controller.EnableGesture(Gesture.GestureType.TYPESWIPE);

  24:         }

  25:  

  26:         public override void OnDisconnect(Controller controller) { }

  27:  

  28:         public override void OnExit(Controller controller) { }

  29:  

  30:         public override void OnFrame(Controller controller)

  31:         {

  32:             var frame = controller.Frame();

  33:             _now = frame.Timestamp;

  34:             _timeDifference = _now - _previous;

  35:  

  36:             if (frame.Hands.IsEmpty) return;

  37:  

  38:             _previous = frame.Timestamp;

  39:             if (_timeDifference < 1000) return;

  40:  

  41:             // Run async

  42:             if (frame.Gestures().Count > 0)

  43:                 Task.Factory.StartNew(() => OnGestureMade(frame.Gestures()));

  44:             if (frame.Fingers.Count > 0)

  45:                 Task.Factory.StartNew(() => OnFingersRegistered(frame.Fingers));

  46:         }

  47:     }

  48: }

El listener es bastante simple, publica en modo evento toda la información capturada por el LEAP cada 1 segundo.

Luego en la MainWindow de mi app WPF poseo el código del siguiente párrafo. Lo único que hay que tener en cuenta en este caso, es que en la inicialización del sensor mejor hacerla en el evento Loaded(), y siempre con cuidado en el closing de la View de cerrar el controller y el listener con el sensor.

   1: public partial class MainWindow : INotifyPropertyChanged

   2: {

   3:     private string _gesturesText;

   4:     private Controller _controller;

   5:     private ElBrunoListener _listener;

   6:     private string _fingersText;

   7:  

   8:     public MainWindow()

   9:     {

  10:         DataContext = this;

  11:         Loaded += MainWindow_Loaded;

  12:         Closing += MainWindow_Closing;

  13:         InitializeComponent();

  14:     }

  15:  

  16:     void MainWindow_Closing(object sender, CancelEventArgs e)

  17:     {

  18:         _controller.RemoveListener(_listener);

  19:         _controller.Dispose();

  20:     }

  21:  

  22:     void MainWindow_Loaded(object sender, RoutedEventArgs e)

  23:     {

  24:         _listener = new ElBrunoListener();

  25:         _controller = new Controller();

  26:         _controller.AddListener(_listener);

  27:         _listener.OnFingersRegistered += OnFingersRegistered;

  28:         _listener.OnGestureMade += OnGestureMade;

  29:     }

  30:  

  31:     void OnGestureMade(GestureList gestures)

  32:     {

  33:         var gesturesData = string.Empty;

  34:         foreach (var gesture in gestures)

  35:         {

  36:             gesturesData += gesture.Type + Environment.NewLine;

  37:         }

  38:         GesturesText = gesturesData;

  39:     }

  40:  

  41:     void OnFingersRegistered(FingerList fingers)

  42:     {

  43:         FingersText = "Active Fingers:" + fingers.Count;

  44:     }

  45: }

Luego, la funcionalidad de la app es bastante straigh forward,

 

La verdad es que como sensor está bien, ahora para poder tener algo up and running, hay que trabajar bastante. No por las capacidades, sino más bien porque el SDK te deja TODA la información en bruto, lo demás … pues a trabajarserlo

Saludos @ Home

El Bruno

image image image Google

[#MICROSOFT] Empowering us (amazing way to tell how we can use new technologies!)

Hello!

After the Super Bowl and the brand-new new CEO of Microsoft, today my office with a great video presented Sunday, and also behind the stories that accompany it

I recommend to see the detail of each story, they are impressive.

Source: http://msft.it/Empowering

Greetings @ Home

El Bruno

imageimageimageGoogle

[#MICROSOFT] Empowering us (impresionante forma de presentar como podemos usar las new technologies!)

Hola!

Después del Super Bowl y del flamante nuevo CEO de Microsoft, hoy me despacho con un video genial presentado el domingo, y además detrás las historias que lo acompañan

Recomiendo ver el detalle de cada historia, son impresionantes.

Fuente: http://msft.it/Empowering

Saludos @ Home

El Bruno

image image image Google

[#LEAP] Welcome Leap Motion! (think in axis now > XYZ!)

Hello!

People usually say that someone is mature enough when you start to be more concerned by the nobey to be spend in the dentist rather the minutes of pain and suffering. In our profession mature usually is associated to set aside the lines of code and start doing more management tasks. To many people this seems an aberration, when in reality don’t realize that it is an excellent opportunity to work with friends, learn on how to work as a team and try to have a good time with one common goal. This is team management Winking smile

Well, when you spend traveling from here to there, and you don’t open Visual Studio in a week, you have to get back the lost time in the weekend (also with family and friends!). Why is that today, already with several ideas and personal projects in my head, I start with a new one: Leap Motion time.

image

The truth is that the device is €99 , but personally I think it worth more than this amout: is a great device!. I will not explain what does the Leap do, thinks in Minority Report, or better to watch this video of Engadget.

I what I will do is to download the SDK and then:

1 Open Visual Studio 2013

2. Create a console application

3. Add the following references to the application

  • \LeapDeveloperKit\LeapSDK\lib\LeapCSharp.NET4.0.dll

4 I can now start to put some code to see the really power of the Leap Motion sensor! As always with these devices, I have to configure the app to be compiled for a specific target, in this case X86.

image

5, In the Main add the following code and already have something running. In this section, what we do is create a listener for events that Leap Motion sends and initialize it with a Controller.

   1: using System;

   2: using Leap;

   3:  

   4: namespace LeapConsole1

   5: {

   6:     class Program

   7:     {

   8:         static void Main(string[] args)

   9:         {

  10:             var listener = new ElBrunoListener();

  11:             var controller = new Controller();

  12:             controller.AddListener(listener);

  13:             Console.WriteLine("Press Enter to quit...");

  14:             Console.ReadLine();

  15:             controller.RemoveListener(listener);

  16:             controller.Dispose();

  17:         }

  18:     }

  19: }

6. The ElBrunoListener class has a little more code, since it is that is responsible for processing information that sends us the Leap. We see that you have inside

   1: using System;

   2: using System.Linq;

   3: using Leap;

   4:  

   5: namespace LeapConsole1

   6: {

   7:     class ElBrunoListener : Listener

   8:     {

   9:         private readonly Object _thisLock = new Object();

  10:  

  11:         private void SafeWriteLine(String line)

  12:         {

  13:             lock (_thisLock)

  14:             {

  15:                 Console.WriteLine(line);

  16:             }

  17:         }

  18:  

  19:         public override void OnInit(Controller controller)

  20:         {

  21:             SafeWriteLine("Initialized");

  22:         }

  23:  

  24:         public override void OnConnect(Controller controller)

  25:         {

  26:             SafeWriteLine("Connected");

  27:             controller.EnableGesture(Gesture.GestureType.TYPESWIPE);

  28:         }

  29:  

  30:         public override void OnDisconnect(Controller controller)

  31:         {

  32:             SafeWriteLine("Disconnected");

  33:         }

  34:  

  35:         public override void OnExit(Controller controller)

  36:         {

  37:             SafeWriteLine("Exited");

  38:         }

  39:  

  40:         public override void OnFrame(Controller controller)

  41:         {

  42:             var frame = controller.Frame();

  43:             var gestures = frame.Gestures();

  44:             foreach (var swipe in from gesture in gestures where gesture.Type == Gesture.GestureType.TYPESWIPE select new SwipeGesture(gesture))

  45:             {

  46:                 var gestureName = GetGestureNameFromSwipe(swipe);

  47:                 SafeWriteLine(string.Format("Swipe id: {0}, name: {1}", swipe.Id, gestureName));

  48:                 break;

  49:             }

  50:         }

  51:  

  52:         private string GetGestureNameFromSwipe(SwipeGesture swipe)

  53:         {

  54:             var gestureName = "undefined";

  55:             var direction = swipe.Direction;

  56:             if (direction.Yaw > 0)

  57:             {

  58:                 gestureName = "left to right";

  59:             }

  60:             if (direction.Yaw < 0)

  61:             {

  62:                 gestureName = "right to left";

  63:             }

  64:             return gestureName;

  65:         }

  66:     }

  67: }

7. In the first place, we can see that we can do an override of OnInit, OnConnect, OnDisconnect and OnExit to initialize the sensor. In this case, I just want that the sensor registers the SWIPE gesture.

8 Then the OnFrame method, we can process the information that returns us a FRAME. The truth is that it is impressive what has this object. In this example, we access the collection of gestures and in it, we get SWYPE type.

9. Then we have to process all the information from this SWIPE. On the one hand we know that it is a SWIPE, but we need to find out the direction of the same. To do this, I’ll work with the SwipeGesture object and I’ll try to identify if the swipe has been left to right processing the Direction property.

image

Note: Direction is a vector. A vector has a lot of information, such as the start position and end, always associated with the axes, X, and y Z. With this information and thinking of the vector in the 3 axes, we could identify swipes from left to right, top to bottom, bottom-left, etc.

In this case, and to summarize much we can do with the LEAP, I’ve decided to process the YAW property. It gives us an integer value with the difference in angles from the negative Z axis and the positive X axis.

api/../../../images/Math_Yaw_Angle.png

Thus if the angle is greater that 90 degrees will be a SWIPE LEFT TO RIGHT and if it is less than 90 degrees is a RIGHT TO LEFT SWIPE.

Note: This always thinking that you’re not Terminator and make gestures of swipe in a direction straight unchanged.

10 As well, now already we can launch the app and see how the console shows the gestures that we are doing on the Leap Motion!

By the way, I will have to get some Google Glases or a sports camera because the film stock in 1st person with the mobile phone… because it is not well Open-mouthed smile

Greetings @ Home

El Bruno

imageimageimageGoogle

[#LEAP] Welcome Leap Motion !!! (empezando a pensar en XYZ!)

Hola!

Dicen que madurar es preocuparse más por lo que te va a cobrar el dentista que por los minutos de dolor y sufrimiento. En nuestra profesión madurar se asocia a dejar de lado las líneas de código y comenzar a hacer tareas más de gestión. A muchas personas esto les parece una aberracion, cuando en realidad no se dan cuenta de que es una excelente oportunidad para poder programar con amigos, trabajar en equipo e intentar pasar un buen rato con un objetivo en común entre varios. Esto es gestión de equipos Winking smile

Ahora bien, cuando te pasas viajando de aqui y no abres el Visual Studio en una semana, pues te queda el mono para el fin de semana. Por eso es que hoy, ya con varias ideas en la cabeza, me pongo de lleno con el juguetito nuevo de estos días: un Leap Motion.

image

La verdad es que por los €99 que cuesta, vale la pena con creces. No me voy a enrollar explicando lo que hace, piensa en Minority Report, o mejor mira este video de Engadget.

Yo lo que haré es descargar el SDK y después:

1. Abrir Visual Studio 2013

2. Crear una applicación de consola

3. Agregar las siguientes referencias a la applicación

  • \LeapDeveloperKit\LeapSDK\lib\LeapCSharp.NET4.0.dll

4. Listo! ya puedo empezar a meter código para ver que nos da el Leap Motion! Antes como siempre con estos devices, tengo que configurar la app para que se compile para un target específico, en este caso X86.

image

5,  En el Main agrego el siguiente código y ya tebgo algo funcionando. En esta sección, lo que hacemos es crear un listener para los eventos que envía el Leap Motion e inicializarlo con un Controller.

   1: using System;

   2: using Leap;

   3:  

   4: namespace LeapConsole1

   5: {

   6:     class Program

   7:     {

   8:         static void Main(string[] args)

   9:         {

  10:             var listener = new ElBrunoListener();

  11:             var controller = new Controller();

  12:             controller.AddListener(listener);

  13:             Console.WriteLine("Press Enter to quit...");

  14:             Console.ReadLine();

  15:             controller.RemoveListener(listener);

  16:             controller.Dispose();

  17:         }

  18:     }

  19: }

6. La clase ElBrunoListener tiene un poco más de código, ya que es la que se encarga de procesar la información que nos envía el Leap. Veamos que tiene dentro

   1: class ElBrunoListener : Listener

   2: {

   3:     private readonly Object _thisLock = new Object();

   4:  

   5:     private void SafeWriteLine(String line)

   6:     {

   7:         lock (_thisLock)

   8:         {

   9:             Console.WriteLine(line);

  10:         }

  11:     }

  12:  

  13:     public override void OnInit(Controller controller)

  14:     {

  15:         SafeWriteLine("Initialized");

  16:     }

  17:  

  18:     public override void OnConnect(Controller controller)

  19:     {

  20:         SafeWriteLine("Connected");

  21:         controller.EnableGesture(Gesture.GestureType.TYPESWIPE);

  22:     }

  23:  

  24:     public override void OnDisconnect(Controller controller)

  25:     {

  26:         SafeWriteLine("Disconnected");

  27:     }

  28:  

  29:     public override void OnExit(Controller controller)

  30:     {

  31:         SafeWriteLine("Exited");

  32:     }

  33:  

  34:     public override void OnFrame(Controller controller)

  35:     {

  36:         var frame = controller.Frame();

  37:         var gestures = frame.Gestures();

  38:         foreach (var swipe in from gesture in gestures where gesture.Type == Gesture.GestureType.TYPESWIPE select new SwipeGesture(gesture))

  39:         {

  40:             var gestureName = GetGestureNameFromSwipe(swipe);

  41:             SafeWriteLine(string.Format("Swipe id: {0}, name: {1}", swipe.Id, gestureName));

  42:             break;

  43:         }

  44:     }

  45:  

  46:     private string GetGestureNameFromSwipe(SwipeGesture swipe)

  47:     {

  48:         var gestureName = "undefined";

  49:         var direction = swipe.Direction;

  50:         if (direction.Yaw > 0)

  51:         {

  52:             gestureName = "left to right";

  53:         }

  54:         if (direction.Yaw < 0)

  55:         {

  56:             gestureName = "right to left";

  57:         }

  58:         return gestureName;

  59:     }

  60: }

7. En primer lugar podemos ver que podemos hacer un override de OnInit, OnConnect, OnDisconnect y OnExit para inicializar el sensor. En este caso, solo quiero que el sensor registre el gesto SWIPE.

8. Luego en el OnFrame, podemos procesar la información que nos retorna un FRAME. La verdad es que es impresionante todo lo que tiene este objeto. En este ejemplo, accedemos a la colección de gestos y en la misma, obtenemos los de tipo SWYPE.

9. Luego tenemos que procesar toda la información de este SWIPE. Por un lado sabemos que es un SWIPE, pero necesitamos averiguar la dirección del mismo. Para esto trabajamos con el objeto SwipeGesture y resumiendo un poco el tema, dentro del mismo identifico si el swipe ha sido de izquierda a derecha procesando la propiedad Direction.

image

Direction es un vector. Un vector tiene mucha información, como la posición inicial y final, siempre asociado a los ejes, X, Y y Z. Con esta información y pensando en el vector en los 3 ejess, podríamos identificar swipes de izquierda a derecha, de arriba hacia abajo, de abajo a izquierda, etc.

En este caso, y para resumir mucho lo que podemos hacer con el LEAP, he decido procesar la propiedad YAW. La misma nos da un valor entero con la diferencia en ángulos desde el eje Z negativo y el eje X positivo.

api/../../../images/Math_Yaw_Angle.png

De esta forma si el ángulo es mayor que 90º será un SWIPE LEFT TO RIGHT y si es menor que 90º será un SWIPE RIGHT TO LEFT.

Nota: Esto siempre pensando en que no seas Terminator y hagas los gestos de swipe en una dirección recta sin variaciones.

10. Pues bien, ahora ya podemos lanzar la app y ver como la consola nos muestra los gestos que vamos realizando sobre el Leap Motion!

Por cierto, me tendré que conseguir unas Google Glases o una cámara deportiva porque lo de filmar acciones en 1ra persona con el mobile phone … pues no queda bien Open-mouthed smile

Saludos @ Home

El Bruno

image image image Google

[#KINECTSDK] Camp:Introduccion development with Kinect (sold out!)

Hello!!!

Thanks to Cristina (my MVP Lead) and to Rafa Ansino, I’ve the cnace to participate and lead a DevCamp with focus in the development with Kinect for Windows SDK. the date for this Camp is March 8, from 09:00 to 14:00. In this session I’ll share an overview of what we can do with Kinect for Windows and the SDK V1. The sad part is … we sold out! I’ve a have full House. The good news is that you have the chance to request a Second Edition, so if we get enough quota we’ll probably do another.

And we’re very freak, so I’ll also share some of the capabilities of the new Kinect for Windows V2 (which is simply amazing!) and why not, some that another development environment not Microsoft to create games with Kinect and C#.

By the way if you want to see the posts of Kinect SDK V2, them can be found here.

Registration (or almost) http://www.eventbrite.es/e/entradas-campintroduccion-al-desarrollo-con-kinect-10100142799

Greetings @ Home

El Bruno

imageimageimageGoogle

[#VS2013] VsAnywhere web workspace (impresionante es poco para describirlo!)

Hola!

Cuando veo que entra un mensaje de Jesus a las 0300 AM por Skype, sé que son buenas noticias. Algún día me dirá que se ha ganado la lotería o alguna de este tipo, sin embargo lo que me muestra cada tanto me deja con la boca abierta y me rompe los esquemas sobre lo que podemos hacer en el mundo del desarrollo de software.

Y es que después de un tiempo donde lograron una integración natural con GitHub, hoy toca lo mismo con las funcionalidades que nos presenta Visual Studio Online, en este caso para Vs Anywhere.

Gracias a esta nueva funcionalidad, puedes compartir un proyecto en el que estes trabajando con otra persona. Hasta aquí es VSAnywhere en estado puro, sin embargo esto le da una vuelta más. Imagina que la persona con la que queires hacer una revisión de código, no tiene acceso a un ordenador, solo tiene en sus manos una tablet de esas de la manzanita … pues aquí esta nueva funcionalidad te da una solución.

Simplemente compartes un link! y desde el otro lado pueden abrir el proyecto para colaborar con el mismo desde una interfaz web !!!

Un video que lo explica mejor que 1000 palabras

Great work VSAnywhere team !!!

Saludos @ Home

El Bruno

image image image Google

[#RESHARPER] R # and INotifyPropertyChanged, really cool!

Hello!

Since a couple of days ago I have this post in draft mode so I’m going to give out today. And the first first thing, a small, an image/video with really cool of ReSharper functionality

VS2013 RSharper NotifiyPropChanged

Although I’ve already written recently about the ability of R # to implement this interface, as you can see in the image above, when we add the INotifyPropertyChanged interface in a class, ReSharper offers 2 options in your context menu

  • First add the “System.ComponentModel” Namespace, something you already know and which also makes the own Visual Studio
  • Second R# offers us to implement the interface, and also to be able to correctly use the same offers us the possibility to add a class Annotations

This class is pre-defined in R# and we can configure the same options of ReSharper. The operation includes grants for the completion and validation of the names of the props in the definition of OnPropertyChanged.

image

And now if, when we generate a property, we can define directly a prop with OnPropertyChanged with ReSharper

VS2013 RSharper prop

I’m saving tons of minutes !

Resources

Greetings @ Córdoba

El Bruno

imageimageimageGoogle