Physicalisation de statistiques au hockey sur glace

De EduTech Wiki
Aller à la navigation Aller à la recherche
Heatmap imprimée en 3D.jpg
Auteur-e-s Utilisateur:Kevin Oulevey
Année de fabrication 2018
Technologie utilisée Impression 3D
Type Physicalisation de données, Autre
Domaine d’enseignement Sport
Niveau d’enseignement Enseignement facultatif
Public cible Experts / Spécialistes
Public cible (Age)
Mots clés statistique
Lien vers le cours STIC https://edutechwiki.unige.ch/fr/STIC:STIC III (2018)
Fichier source
STIC portaillogo.png


DESCRIPTION (objectif pédagogique)

Ce projet créé dans le cadre du cours STIC III a pour but de proposer des visualisations évocatrices des statistiques de hockey sur glace. Elle se reposera sur un parser XML écrit en php, qui produira une heatmap qui sera déclinée sur divers supports.

Heatmap générée avec pHpOCKEY

Ce projet est terminé dans le cadre du cours mais il sera poursuivi afin d'arriver à un projet plus abouti.

La compréhension de données statistiques est une tâche difficile, surtout lorsqu'elles sont présentées dans un tableau (la situation actuelle). Il existe actuellement des représentations visuelles assez basiques qui consistent à indiquer l'emplacement d'une action de jeu à l'endroit où elle a eu lieu. Bien que ces représentations graphiques en deux dimensions possèdent une certaine affordance, elles ont comme faiblesse de ne pas fournir d'indications quant à la concentration des actions qui peuvent se superposer. Ce problème s'amplifie lorsque le nombre d'actions augmente, comme on peut le voir sur l'illustration jointe.

FABRICATION (réalisation technique)

Il s'agit là d'une méthode centrée utilisateur, puisque tout a commencé par un entretien avec les utilisateurs. Ce projet va essayer de répondre du mieux possible à leurs besoins. On est en droit de se demander pourquoi ne pas utiliser une heatmap traditionnelle ? Toutes les heatmaps ont une échelle de couleurs pour pouvoir les lire. En remplaçant l'information de couleur par un ajout d'une information de hauteur physique, on contourne ce problème et on y rend plus simple à lire. De même, on peut opérer des comparaisons plus facilement. Par exemple, sur une heatmap classique les valeurs en orange seront deux fois plus élevées que les valeurs en vert, sans lire la légende c'est impossible à déterminer, en revanche si vous comparez des hauteurs physiques, cela devient trivial.

Après s'être entretenu avec les utilisateurs, il reste encore des défis à relever :

  • En premier lieu, il faudra récupérer les données saisies sous un format utilisable par l'ordinateur (actuellement elles sont sous une forme visuelle).
  • Dans un deuxième temps, il faudra développer un algorithme d'interprétation des données.
  • Ensuite, il faudra développer un algorithme permettant de produire des objets tangibles à partir de ces données.
Sur cette image on a un exemple de visualisation bidimensionnelle que l'on utilise en hockey sur glace. Elle illustre bien le problème de la précision lorsque des évènements se superposent.
Sur cette image, on a un exemple de visualisation bidimensionnelle que l'on utilise en hockey sur glace. Elle illustre bien le problème de la précision lorsque des évènements se superposent.


Dans ce projet, je vais imprimer en 3D une réplique de patinoire dont la topographie indiquera l'emplacement et la quantité de tirs cadrés.

Les données statistiques sont exportées au format XML. Le fichier obtenu ressemble à ce qui suit.
<GAMEACTION>
			<TEAM>Flaming Eagles HC</TEAM>
			<TIME>3756</TIME>
			<TYPE>SHOT</TYPE>
			<DETAIL>SOG</DETAIL>
			<SS>5-5</SS>
			<SCORER>24</SCORER>
			<PLUS1>3</PLUS1>
			<PLUS2>11</PLUS2>
			<PLUS3>16</PLUS3>
			<PLUS4>25</PLUS4>
			<PLUS5>24</PLUS5>
			<PLUS6>14</PLUS6>
			<GK>14</GK>
			<GK_OPPONENT>149</GK_OPPONENT>
			<DATETIME>1541271623</DATETIME>
			<PERIOD>1</PERIOD>
			<POSITION_X>4.691489</POSITION_X>
			<POSITION_Y>20.90425</POSITION_Y>
			<POSITION>L-POINT</POSITION>
			<ZONE>OFFENSIVE</ZONE>
		</GAMEACTION>
Pour réaliser ma heatmap je vais avoir besoin des éléments suivants :
  • <DETAIL> pour identifier s'il s'agit d'un tir cadré.
  • <POSITION_X> et <POSITION_Y> pour pouvoir y situer sur la surface de jeu.

Il y a là un premier problème, je ne sais pas à quoi correspondent ces valeurs. Où se trouve le 0 ? Quel est le maximum ? Après avoir placé des données dans les coins de la patinoire j'ai pu déterminer que les positions vont de 0 à 30 sur l'axe des X (petit côté de la patinoire) et de 0 à 60 pour l'axe des Y (long côté). C'est assez logique puisque une patinoire européenne fait 30m*60m.

L'algorithme que je vais mettre en place devra donc extraire les positions X et Y de tous les tirs cadrés (SOG).

La première étape est la collecte de données, ces données ayant déjà été collectées, je peux passer à l'étape suivante qui consiste à extraire les données pertinentes. Pour ce faire je vais coder un algorithme utilisant XPath qui me permettra de cibler les GAMEACTION correspondant à un tir cadré, puis à en récupérer la position.

  • Scanner le dossier dans lequel se trouve les fichiers XML, placer leurs noms dans un array et les passer au parser.
  • Repérer tous les tirs cadrés d'une équipe dans le XML avec XPath et les placer dans un array (ces paramètres seront des arguments, utiles si on veut travailler sur d'autres équipes ou d'autres actions de jeu).
  • L'array créé par SimpleXML contient des objets, il faut donc récupérer les valeurs contenues dans les objets, les arrondir et les push dans un autre array.
  • Ensuite, on crée un tableau (multidimensional array) que l'on remplit de 0.
  • Pour remplir les cases correspondantes à chaque tir, on récupère chaque paire de coordonnées (un x et un y), et ensuite on incrémente la case du tableau correspondant.
  • On répète l'opération pour tous les fichiers présents dans le dossier.
  • On exporte le tableau dans le dossier de travail.

Le code s'exécute en ligne de commande mais on pourrait imaginer lui donner une interface utilisateur dans le navigateur. L'avantage de l'exécution en ligne de commande est de s'affranchir de la durée d'exécution maximale. On peut augmenter cette valeur en modifiant php.ini cependant cela ne devrait pas être nécessaire.

Afin de respecter les bonnes pratiques, l'utilisateur n'appelle pas directement le parser mais un script unique qui s'occupe lui d'appeler les autres fonctions.

Le code est disponible sur GitHub : https://github.com/oulevey/pHpOCKEY.

Pour info : les informations qui vont suivre sont complémentaires à la lecture du README. On lance l'application en exécutant php index.php dossier_d'entrée dossier_de_sortie [options] les options que l'on peut entrer sont --scad pour créer une heatmap au format OpenSCAD ou --png pour créer une heatmap qui est une image PNG. On peut également solliciter l'aide et la version avec, respectivement, --help et --version.

Dans le dossier d'entrée, on place les fichiers XML respectant la grammaire mentionnée auparavant. Dans le dossier de sortie, on trouvera nos heatmaps (si le dossier n'existe pas, il sera créé).

Le parser va ensuite procéder à l'analyse syntaxique et créer la matrice qui sera soit convertie en fichier SCAD (génération d'un fichier heatmap.scad par le parser) ou alors la matrice est transmise à une nouvelle fonction qui va créer la heatmap en PNG (création d'un fichier heatmap.dat). Les deux options ne sont pas mutuellement exclusives.

Une fois le script exécuté, on trouve dans le dossier de sortie 3 fichiers au format SCAD :

  • config.scad qui contient divers paramètres que l'on peut ajuster (notamment la taille des lignes, et des pucks qui vont servir à représenter les tirs)
  • heatmap.scad qui contient la matrice qui sert à produire notre heatmap en 3D
  • build.scad qui, à partir des deux fichiers précédents, va créer la représentation 3D

L'utilisateur doit donc ouvrir le fichier build.scad pour avoir sa heatmap en 3D.

Rendu 3D représentant une patinoire avec des pucks de tailles différentes dessus symbolisant l'emplacement et le nombre de tirs.
Rendu en 3D de pHpOCKEY

La difficulté principale résidait dans le codage de l'algorithme en PHP car il s'agi d'un langage que je ne maîtrise pas franchement, cependant j'ai pu trouver de l'aide auprès de Sébastien Mischler (énormément) ainsi que Nicolas Hürzeler et Stéphane Morand que je remercie tous.

C'était également assez compliqué de choisir comment représenter les évènements en impression 3D, l'idée de base était de faire des pics, mais c'était impossible de les imprimer. Je me suis donc tourné vers des formes plus basiques, en l'occurence des cylindres qui rappellent les pucks (brillante idée de Sébastien).

Finalement, ce n'est pas une difficulté à proprement parler mais plus une perte de temps considérable : la génération des fichiers XML doit se faire manuellement à l'heure actuelle et ils sont envoyés par email. C'était une tâche particulièrement chronophage.

Heatmap imprimée en 3D
Heatmap imprimée en 3D
SPECIFICATIONS TECHNIQUES


UTILISATIONS (scénario pédagogique, règles du jeu)