jeudi 9 février 2012

RayTracing temps réel... en Flash ! Partie 1


Le " RayTracing " (ou lancer de rayon, en français) est une des techniques informatiques les plus connues pour le calcul et l'affichage d'images en 3 dimensions. Elle ne date pas d'hier mais reste encore aujourd'hui cantonnée à un champ d'application assez restreint (expérimentation, travail purement artistique, court-métrage, …) à cause d'un temps de calcul (de chaque image) très important. Pour les applications nécessitant un affichage en temps réel ou ayant un important volume d'images à calculer (jeux, dessins-animés, visites virtuelles, …) d'autres techniques sont privilégiées.

Pourtant dans les années 80, le RayTracing était LA technique privilégiée pour la création d'images de synthèse de qualité et particulièrement impressionnantes (pour l'époque), avec des images (devenues aujourd'hui des classiques) de boules réfléchissantes, sols à damier, … (voir l'image juste au dessus). Tout cela au prix de nombreuses heures de calcul…
Depuis rien n'a vraiment changé... le RayTracing reste lent et la puissance des machines (personnelles) actuelles ne suffit toujours pas à un rendu en temps réel. Bref, typiquement le genre de projet à priori inadapté à la – relative – lenteur de Flash… Raison de plus pour le faire ! 

Mais avant de se lancer dans le développement, il convient de se poser quelques questions :
- quelle qualité de résultat puis-je espérer ? 
- que signifie pour moi "temps réel" ? 
- quels sacrifices (de qualité) suis-je prêt à accepter pour rester en "temps réel" ? 
- quelles applications utiles pourrai-je tirer d'un tel développement ? 
- un RayTracer, comment ça marche ? 
- ça n'existe pas déjà en fait ?... 

Avant de répondre point par point, petit retour en arrière… de 20 ans. Paraissait en février 1989 un article dans le magazine "Science & vie Micro" avec un listing… de RayTracer. Ecrit en GFA Basic (un langage très populaire sur les machines Atari 16 bits de l'époque) par Mustafa Suna, celui-ci m'a fait découvrir cette technique et m'a causé de nombreux mal de cranes à essayer de décortiquer le code. En effet un RayTracer fonctionne avant tout avec des formules mathématiques (de niveau lycée) que je ne maîtrisais pas du tout à l'époque… Il n'empêche, j'ai fini par écrire mon premier RayTracer (ultra simpliste) sur mon Amstrad CPC (oui vous avez bien lu), un ordinateur 8 bits à 4 Mhz (pas Ghz…) affichant 16 couleurs en 160x200 (j'utilisai un système de trames pour simuler les dégradés…) en BASIC. Bref j'aime les défis… Pour info, j'ai toujours ce magazine et je l'ai ré-ouvert pour démarrer ce projet. Si Mr Mustafa Suna me lit, qu'il sache que son listing restera à jamais dans ma bibliothèque (entre deux boîtes de Doliprane) …

Je sais donc déjà un peu à quoi m'attendre mais je suis curieux de voir si je m'en sors mieux 20 ans après… Je commence par faire quelques recherches sur Internet sur le développement des RayTracer en temps réel et/ou en Flash. Cette technique se prêtant bien à un découpage des calculs, de nombreuses expérimentations sur des machines "parallèles" (en général multi-cœurs ou multi-processeurs) permettent d'envisager le temps réel. En Flash quelques bons/beaux résultats (mais pas en temps réel). Je m'attarde quand même sur 2 essais :
- http://www.laserpirate.com/as3raytracer/ 
- http://strille.net/works/as3/raytracer/raytracer_f9.swf 

Flash AS3 RayTracer Les résultats du premier sont à relativiser. Le nombre élevé d'images par seconde est surtout du à la taille réelle de l'image (toute petite) qui est ensuite "zoomer" (d'où les gros pixels tout moches…). Mais les explications des tentatives de l'auteur et le code source disponible sont précieux. Je le modifie pour afficher une scène simple (3 sphères+ une lumière directionnelle), sans effet de zoom, qui me servira de référence. Le but étant de faire "mieux" et plus rapide. Et surtout plus souple, car l'auteur à volontairement fait abstraction de la POO (programmation orientée objet) que je tiens moi à conserver pour obtenir un code facilement réutilisable dans une vraie application.

Le second est nettement plus impressionnant… mais absolument pas documenté. Là aussi si on veut une "bonne" qualité d'image, le FrameRate s'effondre. Je décortique les sources… qui me donnent de nouveau mal à la tête (noms de variable incompéhensibles, …). J'y reviendrai…

Je laisse volontairement de coté les tentatives non 100% AS CPU (via Alchemy, PixelBender, …).

Je relis aussi la série d'articles de Matthieu Brucher sur le site developpez.com qui permet de bien clarifier les choses et d'aller à l'essentiel. Le site alrj.org permet aussi de se remettre dans le bain niveau mathématique utile pour ce projet. Il existe de nombreux autres sites, mais au final tous disent la même chose…

1ière conclusion : un tel projet a déjà été tenté (avec des résultats mitigés) et la documentation est nombreuse. Allez, on continue !

Flash AS3 RayTracer molecule 3D viewer Afin de me fixer des objectifs (en terme de résultats visuels surtout) j'envisage d'utiliser ce moteur de RayTracing pour la visualisation en temps réel (et en ligne) de molécules. Ce genre d'applications existe déjà, mais pas en RT à ma connaissance (il s'agit juste de sphères qui se déplacent en 3D, mais pas de gestion de l'illumination, des ombres portées, de la transparence, …). Je me fixe aussi un FrameRate minimum de 10 images par seconde (sur ma machine). A priori je n'ai besoin que de sphères, cylindres et plans. Le tout devant être orienté objet pour être facilement implémenté dans un projet Flash quelconque.

Bon, mais alors on commence ? Oui... mais dans le prochain article !

PS : la première image illustrant cet article est issue (avec autorisation de l'auteur) du Blog de David Catuhe , dans un article sur l'utilisation du parallélisme (sur machine non dédiée) pour le développement d'un RayTracer. Allez donc le lire… ou un autre de ses articles sur le développement d'un RayTracer via le Cloud de Microsoft : http://blogs.msdn.com/b/eternalcoding/archive/2011/12/15/utiliser-la-puissance-du-cloud-azure-pour-faire-votre-propre-raytracer.aspx