vendredi 7 octobre 2016

[Unity3D][Guide] Une minimap pas trop compliquée

Depuis quelque jours je touche pas mal à Unity3D, ce moteur de jeu gratuit et assez complet qui permet de faire pas mal de choses même pour un néophyte en matière de développement de jeux-vidéo. Ma dernière lubie, faire un système de minimap pour n'importe quel type de jeu.

Après plusieurs recherches et essai, j'ai fini par parvenir à réaliser quelque chose de plutôt simple, mais mine de rien assez efficace, qui nous donne quelque chose comme ça à la fin:


Rendu final


Si vous êtes intéressés et voulez en faire une vous même et n'avez aucune idée de comment faire, je vais vous exposer ici la méthode que j'ai employée, d'abord dans les grandes lignes pour vous expliquer l'idée puis de manière plus poussée. Gardez cependant en tête que ce n'est peut être pas la méthode parfaite et que plus tard vous voudrez peut être passer à quelque chose de plus poussé.
En attendant, prenez vos plus beaux habits de développeurs, remontez vos manches, attachez vos  bretelles, rentrez les chevaux, et suivez le guide! ;)




Explications:


Avant de se lancer dans le développement en lui même, laissez moi donc vous expliquer la manière de procéder. Nous voulons ici réaliser une minimap, à savoir donc un morceau d'interface à l'écran qui permet de voir une fraction de la map et nous indiquant clairement où notre personnage se trouve.
La manière la plus simple vient intuitivement: placer une caméra au dessus du personnage à suivre, et afficher ce qu'elle voit dans un coin de l'écran.
C'est grosso modo ce que nous allons faire, mais il faut garder deux choses en tête:
- Chaque caméra va faire un rendu en temps réel ce qu'elle voit, ainsi si la map comporte beaucoup de choses, les performances pourraient être sévèrement affectées
- On ne veut pas forcément tout afficher sur la minimap (par exemple on pourrait ne vouloir afficher que le terrain et la position du personnage principal, mais pas les autres personnages, ni les effets météorologiques, ou quoi que ce soit d'autre).


En sachant cela, comment procéder ?

Après mûres réflexions (et surtout pas mal de tutos sur internet ainsi qu'une bonne grosse dose de coca dans les veines), j'ai imaginé le procédé suivant:
- Placer une caméra au dessus du terrain, bien centrée
- N'afficher que le terrain et les objets de décor que je veux voir sur la map
- Prendre une photo de ce que voit ainsi la caméra (dans la meilleure qualité possible)
- La retoucher un peu si besoin est
- Créer une surface (plan) sous le terrain de la même taille que le terrain
- Lui donner comme texture la photo prise précédemment
- Dire à Unity de ne montrer que ce plan avec la nouvelle caméra
- Lier cette caméra au joueur pour qu'elle suive ses déplacements

Ainsi donc on a une caméra qui suit le joueur, et qui n'affiche que le plan, sans rendre une nouvelle fois tout le terrain. La photo ayant été prise en haute qualité on obtient une map assez jolie. On a bien ce que l'on voulait avec un coût en performances réduit.




En détails


Si vous avez compris le principe mais ne voyez pas comment faire cela, lisez ce qui suit.

  1. Prérequis Pour pouvoir réaliser ceci il vous faut avant de commencer:
    - Un terrain dont vous voulez réaliser la minimap
    - Un personnage à suivre (regardez les standards Assets d'Unity si vous n'en avez pas un à vous ça fera très bien l'affaire)


  2. Prise de la photo
    Là encore il y a plusieurs manières de le faire, mais pour ma part j'ai procédé ainsi:
    - Désactiver tous les objets que je ne voulais pas voir sur la map
    - Créer une caméra
    - La placer au dessus du terrain, au centre
    - La mettre en mode orthographique (pour enlever le relief qui ne ferai pas beau sur la map)(non ce n'est pas un mode de grammar nazi bande de fripoux)
    Mode Orthographique

    - Faire en sorte de ne voir que le terrain à l'écran, rien de plus ni moins (le meilleur moyen que j'ai trouvé étant de paramétrer les dimensions de sortie dans les même proportions que celles du terrain)
    Remplacer Standalone par vos proportions

    - Prendre une photo, soit comme ça soit directement depuis la caméra. (vous pouvez attacher ce script à la caméra, qui fera très bien le boulot)
    Mon screen perso

    - Si vous avez changé les proportions d'affichage, vous pouvez les remettre comme à l'origine.



  3. Plan et texture 

    Maintenant que l'on a notre belle image de notre map, il nous faut l'afficher à l'écran. Pour cela:
    - Créer un plan, appelez le minimap par exemple
    - Le mettre aux dimensions du terrain
    - Le glisser sous le terrain
    - Ajouter la texture sur le plan (un cliqué glissé suffit)
    La map (a gauche) et le terrain (à droite)

    - Si besoin, effectuer une rotation du plan si la texture n'est pas dans le même sens que l'image originale
    - Superposer parfaitement le terrain à la map
    - Quand on est bon, dans l'onglet hiérarchie glissez le plan dans votre terrain, ainsi si vous déplacez votre terrain la map bougera en meme temps!

    Et voilà, on a notre minimap, simple non ? En fait non, on n'a pas tout à fait terminé, on veut que notre caméra n'affiche QUE le plan, et que la caméra du joueur au contraire ne l'affiche pas. Comment dire à Unity de faire cela ? C'est très simple, en utilisant les Layers !



  4. Les Layers
     
    Si vous sélectionnez n'importe quel objet dans Unity, vous pourrez voir dans l'inspecteur, en dessous de son nom, un onglet Tag ainsi qu'un onglet Layer. Par défaut le Layer est "Default". Sélectionnez donc la minimap, cliquez sur Layer et sélectionnez "Add Layer". Une liste apparaitra, et dans la première case disponible, entrez un nom, par exemple "Minimap". Resélectionnez ensuite votre map, et vérifiez que son Layer est bien celui que vous venez de créer.


    A quoi cela nous sert-il ? 
    Hé bien en fait, cette séparation nous permettra de dire à notre caméra de n'afficher que les objets de ce Layer là. Il est aussi possible, par exemple pour l'eau, de lui dire de ne réfléchir que les objets d'un certain Layer, c'est un composant bien pratique qui nous permet de "séparer" nos objets sans pour autant avoir à faire deux choses différentes.

    Comment faire ?
    Reprenez votre caméra de tout à l'heure, et dans l'onglet "Culling Mask", déselectionnez tout sauf le layer minimap. Si vous lancez la scène, vous ne verrez alors bien que la minimap.
    A l'inverse, lorsque vous allez ensuite réactiver votre joueur, n'oubliez pas de désélectionner le layer minimap de sa caméra, et faite de même pour tout ce qui utilise des layers (réflexion de l'eau etc).



  5. Afficher la position du joueur

    Maintenant que nous avons notre minimap, il serait bien de pouvoir afficher le joueur non ? C'était un peu le but de la manoeuvre en même temps ;)
    Il vous suffit de créer un sprite représentant votre position (vous pouvez le créer avec unity sinon en importer) et l'attacher à votre personnage. Mettez le sur le layer minimap, lancez et TADAAAAAAA!...
    Vous voyez la vue du joueur et plus du tout la minimap. Hm. Problématique. Nous allons résoudre ça plus tard, mais pour l'instant si vous désactivez la caméra du personnage, vous pourrez bien revoir votre minimap et votre marqueur qui bouge quand vous déplacez votre personnage !
    Et vous pourrez utiliser cette technique de layer pour tous les points que vous voudrez faire apparaitre sur votre minimap (noms de lieux, ennemis...).


  6. Render Texture

    Ca y est nous touchons au but, il ne nous reste plus qu'à faire en sorte d'avoir notre minimap à l'écran. Pour cela commencez par réactiver la caméra du joueur que nous avons coupée précédemment.
    Ensuite la procédure est un peu technique à expliquer.
    Unity propose une feature appelé "Render texture", c'est une texture qui se met à jour en temps réel à l'aide d'une caméra. C'est donc ce que nous allons utiliser.
    Dans l'explorateur, cliquez droit, et créez une nouvelle Render texture, nommez là comme vous le souhaitez.
    Cliquez ensuite sur la caméra et dans Target Texture déposez la texture dernièrement créée.
    Vous pourrez voir qu'elle ressemble bien à ce que la caméra voit actuellement.
    Lier la caméra à la texture



  7. UI 
    La dernière étape est de créer l'UI (User Interface) qui va afficher notre carte.
    Dans l'onglet Hiérarchie, cliquez droit et sélectionnez "UI > Raw Image". Les raw images permettent d'afficher des render textures.
    Prenez donc cette Raw image nouvellement créée, et glissez y dans "texture" la render texture de votre minimap. Positionnez là ensuite ou vous voulez, et magie, vous avez en temps réel votre minimap qui s'actualise quand vous avancez !

  8. Pour aller plus loin

    Ici nous avons un système de minimap statique et qui n'affiche que le joueur. Pour un vrai jeu, il peut être utile de faire en sorte que cette map soit moins grande et suive le joueur, mais aussi qu'elle affiche les ennemis repérés, les lieux proches, etc.
    Pour faire suivre le joueur, il suffit simplement d'attacher la caméra au joueur et de réduire son champ de vision ;)
    Pour le reste, un peu de code sera surement nécessaire, mais ce n'était pas le sujet de ce guide. N'hésitez pas à chercher de votre côté comment faire ! :)



Conclusion


En réalisant ceci j'ai appris pas mal de choses sur Unity, notamment l'utilisation des Layers, des Render Textures et des caméras. Et vous l'aurez vu tout cela a été fait sans une ligne de code, imaginez ce que ça peut donner après! :D

En tout cas j'espère que ce retour d'expérience vous aura plu et aidé, n'hésitez pas à me faire des retours sur ce que vous en avez pensé, ou même proposer vos implémentations du système de minimap ou encore vos possibles améliorations! Si vous avez des question je me ferai un plaisir d'y répondre. A très vite pour de nouvelles aventures informatiques :)

Aucun commentaire:

Enregistrer un commentaire