Crear una Windows 10 UWP App y utilizar YoloV2 para reconocer objetos
- Introduccion a YoloV2 como modelo de reconocimiento de objetos
- Como crear una UWP App y analizar los frames de la webcam utilizando YoloV2
- Convirtiendo el resultado de YoloV2 a clases C# y mostrarlas en modo Frames
- Redimensionar el output para trabajar con diferentes resoluciones y mostrar los Frames procesados por segundo con YoloV2
Buenas!
Ahora que ya tenemos el archivo Yolo.ONNX es momento de crear una app en la que utilicemos el mismo. He aquí el paso a paso y algunos comentarios
1. Creamos una nueva Windows 10 UWP App. Como siempre el nombre es super original
2. Como vamos a utilizar la cámara como feed de imágenes para procesarlas con YoloV2. Hay muchos ejemplos sobre como realizar esto. En este caso utilizaremos un control de Windows Community Toolkit V 3.0 (como ya escribí en un post anterior). Agregamos los siguientes packages vía NuGet
- Microsoft.Toolkit.Uwp.UI
- Microsoft.Toolkit.Uwp.UI.Controls
3. Agregamos un control CameraPreview en nuestro Xaml y ya estamos a 2 lineas de tener la cámara funcionando.
4. Habilitamos los permisos necesarios para utilizar la camera en el manifiesto con con las siguientes líneas nuestra app ya tiene una camera funcional.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using Windows.UI.Xaml.Controls; | |
using Windows.UI.Xaml.Navigation; | |
namespace UwpAppYolo01 | |
{ | |
public sealed partial class MainPage : Page | |
{ | |
public MainPage() | |
{ | |
InitializeComponent(); | |
} | |
protected override async void OnNavigatedTo(NavigationEventArgs e) | |
{ | |
await CameraPreview.StartAsync(); | |
CameraPreview.CameraHelper.FrameArrived += CameraHelper_FrameArrived; | |
} | |
private void CameraHelper_FrameArrived(object sender, Microsoft.Toolkit.Uwp.Helpers.FrameEventArgs e) | |
{ | |
} | |
} | |
} |
5. Llega el momento de comenzar a utilizar YoloV2. Las últimas versiones de Visual Studio 2017 nos permiten importar un modelo ONNX en un proyecto y se crearan las clases necesarias para trabajar con el mismo. Agregamos como un archivo existente al archivo [Tiny-YOLOv2.onnx].
Nuestra solución debería quedar similar a la siguiente
6. La clase que se genera en VS para trabajar con el modelo es bastante “fea”.
7. Mi sugerencia, reemplazar [8d4d0fa662b14686b1865e0e6d3c598e] por [TinyYoloV2]
8. Ahora si ya podemos ver la clase generada y dentro de la misma podremos encontrar 3 clases
- Una clase de Input para el model
- Una clase de Output para el model
- Una clase para trabajar con el model
Es momento de cargar el modelo en nuestra app. Esto lo hacemos antes de inicializar la camera como muestra el siguiente codigo
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using Windows.UI.Xaml.Controls; | |
using Windows.UI.Xaml.Navigation; | |
namespace UwpAppYolo01 | |
{ | |
public sealed partial class MainPage : Page | |
{ | |
private TinyYoloV2Model _model; | |
public MainPage() | |
{ | |
InitializeComponent(); | |
} | |
protected override async void OnNavigatedTo(NavigationEventArgs e) | |
{ | |
LoadYoloOnnxModel(); | |
await CameraPreview.StartAsync(); | |
CameraPreview.CameraHelper.FrameArrived += CameraHelper_FrameArrived; | |
} | |
private async void LoadYoloOnnxModel() | |
{ | |
var file = await Windows.Storage.StorageFile.GetFileFromApplicationUriAsync(new Uri("ms-appx:///Tiny-YOLOv2.onnx")); | |
_model = await TinyYoloV2Model.CreateTinyYoloV2Model(file); //, | |
} | |
private void CameraHelper_FrameArrived(object sender, Microsoft.Toolkit.Uwp.Helpers.FrameEventArgs e) | |
{ | |
} | |
} | |
} |
9. Como utilizaremos el modelo como parte de nuestra app, tenemos que definir que el mismo sea tratado como un Content en el proceso de Build
10. El siguiente paso es evaluar un frame de la cámara con el modelo YoloV2. Aquí el código nos muestra como utilizamos las clases que creamos cuando importamos el modelo.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
private async void CameraHelper_FrameArrived(object sender, Microsoft.Toolkit.Uwp.Helpers.FrameEventArgs e) | |
{ | |
if (e?.VideoFrame?.SoftwareBitmap == null) return; | |
var input = new TinyYoloV2ModelInput {image = e.VideoFrame}; | |
var output = await _model.EvaluateAsync(input); | |
Debug.WriteLine(output.grid.ToString()); | |
} |
11. Finalmente un BreakPoint nos puestra como el output del modelo tiene [información], que deberemos procesar luego.
Importante: En algún momento debería escribir sobre las capacidades de conversión de modelos que nos trae Visual Studio Tools for AI. Si estas interesado puedes ver las referencias.
Pues bien, en este punto ya estamos utilizando el modelo YoloV2 para analizar los frames de la cámara. En los siguientes posts comentare como trabajar con el output del modelo para interpretar el mismo.
Happy Coding!
Saludos @ Toronto
El Bruno
References
- YOLO: Real-time object detection
- YOLO9000: Better, Faster, Stronger by Joseph Redmon and Ali Farhadi (2016)
- ONNX Tools
- Azure AI Gallery, Tiny YOLO V2
- El Bruno, Windows Community Toolkit V 3.0 makes life incredibly easy if you need working with the camera in a UWP App
- Visual Studio Marketplace, Visual Studio Tools for AI
5 comments