Création d'herbe interactive dans Unreal Engine


Jusqu'à récemment, l'herbe dans les jeux était généralement indiquée par une texture au sol, plutôt que par le rendu de tiges individuelles. Mais avec une augmentation de la puissance du fer, il est devenu possible de rendre l'herbe. De grands exemples de ce rendu peuvent être vus dans des jeux comme Horizon Zero Dawn et The Legend of Zelda: Breath of the Wild . Dans ces jeux, le joueur peut parcourir les prairies herbeuses et, plus important encore, l'herbe répond aux actions du joueur.

Heureusement, la création d'un tel système n'est pas très difficile. En fait, l'article vous apprendra exactement cela! Dans ce didacticiel, vous apprendrez ce qui suit:

  • Créer un champ vectoriel à l'aide d'un système de capture de scène et de particules
  • Pliez l'herbe d'un joueur en fonction d'un champ vectoriel
Remarque: ce didacticiel suppose que vous connaissez déjà les bases de l'utilisation d'Unreal Engine. Si vous débutez avec Unreal Engine, consultez notre série en dix parties de didacticiels Unreal Engine pour les débutants . En particulier, consultez le didacticiel Systèmes de particules pour savoir comment utiliser Cascade dans ce didacticiel.
Remarque: ce didacticiel fait partie d'une série de trois didacticiels sur l'utilisation des cibles de rendu:

Se rendre au travail


Commençons par télécharger le matériel de ce tutoriel (vous pouvez les télécharger ici ). Décompressez-les, accédez à InteractiveGrassStarter et ouvrez InteractiveGrass.uproject . Vous verrez un petit champ d'herbe qui sera le thème de ce tutoriel. J'ai également créé un widget pour afficher la cible de rendu de la capture de scène.



Avant de commencer, vous devez étudier le didacticiel sur la création d'empreintes de pas dans la neige , car je vais ignorer certaines informations. Il convient de noter que la capture et la projection sont également utilisées dans ce didacticiel. Pour gagner du temps, j'ai préparé une capture de plan, similaire au plan du didacticiel sur les pistes dans la neige.

Pour commencer, examinons une autre façon de créer du gazon interactif. La manière la plus courante consiste à transférer les coordonnées du joueur sur le matériau de l'herbe et à utiliser un masque sphérique pour plier l'herbe dans un certain rayon par rapport au joueur.

Bien que cette approche soit assez bonne, elle ne s’adapte pas bien lorsque nous voulons ajouter plus d’acteurs à l’herbe. Pour chaque acteur que vous ajoutez, vous devrez ajouter un autre paramètre de coordonnées et un masque sphérique au matériau. Une méthode plus évolutive consiste à utiliser un champ vectoriel .

Qu'est-ce qu'un champ vectoriel?


Un champ vectoriel n'est qu'une texture dont chaque pixel correspond à une direction. Si vous travailliez avec des cartes de flux, elles sont similaires. Mais au lieu de déplacer les UV, nous utiliserons le contact World Position Offset pour déplacer les sommets. Contrairement à la solution avec un masque sphérique, pour obtenir la direction de flexion, il suffit que les matériaux échantillonnent le champ vectoriel une seule fois .

Voyons comment enregistrer les itinéraires dans une texture. Regardez cette grille:


Disons que le point rouge est l'objet que nous voulons déplacer. Si nous le déplaçons dans le coin inférieur droit, alors quel vecteur dénotera ce mouvement? Si vous avez répondu (1, 1) , alors vous avez raison! Comme vous le savez probablement, vous pouvez également représenter des vecteurs comme des fleurs, et ainsi les sauvegarder dans leur texture. Insérons ce vecteur dans le sélecteur de couleurs Unreal et voyons de quelle couleur il retourne.


Comme vous pouvez le voir, la direction (1, 1) revient en jaune. Cela signifie que si nous voulons plier l'herbe dans la direction des axes XY positifs, nous devrons utiliser cette couleur de texture. Regardons maintenant les couleurs de tous les vecteurs.


Le carré en bas à droite semble assez bon car il a des dégradés sur les deux axes. Cela signifie que nous pouvons stocker n'importe quel vecteur dans ce quadrant en tant que couleur, car chaque vecteur a une couleur unique.

Mais il y a un problème avec les trois autres quadrants. Nous n'avons qu'un gradient le long d'un axe, ou aucun gradient du tout. Cela signifie que plusieurs vecteurs auront la même couleur. Par exemple, nous ne pouvons pas distinguer les vecteurs (-1, 1) et (0, 1) .

Ces trois quadrants n'ont pas de couleurs uniques pour chaque vecteur car nous ne pouvons représenter les couleurs qu'en utilisant des valeurs de 0 à 1. Cependant, ces trois quadrants utilisent des valeurs négatives en dehors de cette plage.

La solution consiste à redistribuer les vecteurs afin qu'ils s'inscrivent tous dans l'intervalle de 0 à 1. Cela peut être fait en multipliant le vecteur par 0,5 et en ajoutant 0,5 . Voici une visualisation de ce que nous obtenons:


Maintenant, chaque vecteur a une couleur unique. Lorsque nous devons l'utiliser pour des calculs, nous le redistribuons simplement dans l'intervalle de -1 à 1. Voici quelques couleurs et les directions correspondantes après la redistribution:

  • (0, 0): X et Y négatifs
  • (0,5, 0,5): aucun mouvement
  • (0, 1): X négatif et Y positif
  • (1, 0): X positif et Y négatif

Maintenant, apprenons à créer un champ vectoriel dans Unreal.

Création d'un champ vectoriel


Contrairement à la création de traces dans la neige, nous n'effectuerons pas la capture de la forme des objets. Au lieu de cela, nous allons peindre sur la cible de rendu avec des pinceaux. Ce ne seront que des images du champ vectoriel sélectionné. Je les appellerai des pinceaux de direction .

Au lieu de dessiner sur la cible de rendu avec des contours, nous pouvons utiliser des particules . Les particules afficheront une brosse de directions et émises par le lecteur. Pour créer un champ vectoriel, il suffit d'utiliser la capture de scène et de capturer uniquement les particules. L'avantage de cette méthode est que la création de traces est très simple. De plus, il vous permet de gérer facilement des propriétés telles que la durée de stockage des pistes et leur taille. De plus, les particules créent des traces temporairement persistantes, car elles existent après avoir quitté la zone de capture et y être retournées.

Voici quelques exemples de brosses directionnelles que nous pouvons utiliser, ainsi que leur effet sur l'herbe. Notez que dans l'exemple ci-dessous, les particules sont invisibles.


Pour commencer, créons un matériau qui affichera une brosse directionnelle.

Création de matériel pour les directions


Il existe deux façons de créer un pinceau de direction:

  1. Mathématique: les directions et la forme sont définies à l'intérieur du matériau. Son avantage est qu'il ne nécessite pas de logiciel tiers et est pratique pour les formulaires simples.
  2. Conversion de carte normale: créez une carte normale des directions et des formes souhaitées. Pour convertir la carte en champ vectoriel approprié, il nous suffit de supprimer le canal bleu. L'avantage de cette méthode est que vous pouvez très facilement créer des formes complexes. Vous trouverez ci-dessous un exemple de pinceau qui sera difficile à créer mathématiquement.


Pour ce tutoriel, nous allons créer un pinceau mathématiquement. Accédez au dossier Matériaux et ouvrez M_Direction . Notez que le modèle d'ombrage Éteint est sélectionné pour ce matériau. Ceci est important car il permet la capture d'une scène pour capturer des particules sans les affecter.

Afin de ne pas compliquer les choses, nous allons créer un matériau qui fera que l'herbe s'éloignera du centre de la particule. Pour ce faire, créez le schéma suivant:


Maintenant, nous devons redistribuer. Pour ce faire, ajoutez les nœuds sélectionnés et connectez tout comme suit:


Donnons maintenant au pinceau une forme ronde. Pour ce faire, ajoutez les nœuds sélectionnés:


RadialGradientExponential contrôle la taille et la netteté de la circonférence du cercle. La multiplication par la couleur des particules vous permet de contrôler l'opacité des particules du système de particules. Je vais en discuter plus en détail dans la section suivante.

Voici à quoi ressemble le pinceau:


Cliquez sur Appliquer et fermez le matériau. Maintenant que nous avons créé le matériau, il est temps de se lancer dans un système de traces de particules.

Création d'un système de traces de particules


Accédez au dossier ParticleSystems et ouvrez PS_GrassTrail . Pour gagner du temps, j'ai déjà créé tous les modules nécessaires.


Voici comment chaque module affecte les empreintes de gazon:

  • Spawn: la fréquence de création affecte la fluidité des pistes. Si les pistes semblent intermittentes, vous devez augmenter la fréquence de création. Dans ce tutoriel, nous laisserons la valeur par défaut (20).
  • Durée de vie: la durée de vie du sentier jusqu'à ce que l'herbe retrouve son état d'origine
  • Taille initiale: taille de trace
  • Color Over Life: puisque nous utilisons la couleur des particules dans le matériau, vous pouvez contrôler l'opacité ici. Vous pouvez également modifier la courbe alpha pour contrôler la disparition de la piste. Par exemple, vous pouvez choisir la disparition linéaire, l'accélération et / ou la décélération. Dans ce tutoriel, nous laisserons le paramètre par défaut, c'est-à-dire la perte linéaire.
  • Verrouiller l'axe: utilisé pour diriger les particules vers la capture de scène
  • Rotation initiale: utilisée pour s'assurer que les particules sont orientées le long des axes corrects (plus de détails ci-dessous)

Nous devons d'abord définir le matériau. Sélectionnez le module requis et définissez Material sur M_Direction . Définissez également Mode de tri sur PSORTMODE Âge le plus récent en premier .


Ce mode de tri vous permet de rendre de nouvelles particules par-dessus les anciennes. Si cela n'est pas fait, ce n'est pas nouveau, mais les vieilles particules affecteront l'herbe.

Vient ensuite la durée de la trace. Sélectionnez le module Lifetime et définissez Constant sur 5 . Grâce à cela, la trace disparaîtra dans les cinq secondes.


Passons maintenant à la taille de la trace. Sélectionnez le module Taille initiale et définissez la constante sur (150, 150, 0) . Pour cette raison, chaque particule couvrira une zone de 150 × 150.


Maintenant, nous devons le faire regarder dans le sens de la capture de la scène. Puisque la scène est capturée par le haut, les particules doivent regarder dans la direction de l'axe Z positif. Pour ce faire, sélectionnez le module Verrouiller l'axe et réglez les drapeaux de l'axe de verrouillage sur Z.


Enfin, nous devons définir la rotation des particules. Actuellement, les couleurs des pinceaux ne sont pas alignées avec la direction qu'elles représentent. Cela s'est produit parce que par défaut, le système de particules est appliqué avec une rotation de 90 degrés. Pour résoudre ce problème, sélectionnez le module de rotation initiale et définissez la valeur constante sur -0,25 . Cela fera tourner les particules de 90 degrés dans le sens antihoraire.


Et c'est tout ce dont nous avons besoin pour le système de particules, alors fermons-le.

Ensuite, nous devons attacher un système de particules à ce qui est censé créer des traces. Dans notre cas, nous devons l'attacher au personnage du joueur.

Fixation du système de particules


Accédez à Personnages \ Mannequin et ouvrez BP_Mannequin . Ensuite, créez le composant Partice System et nommez-le GrassParticles .


Ensuite, nous devons définir un système de particules. Accédez au panneau Détails et définissez Particles \ Template sur PS_GrassTrail .


Il serait étrange que le joueur puisse voir la piste dans le jeu, donc ça vaut le coup de la cacher. Pour ce faire, activez Rendu \ Owner No See .


Puisque le système de particules est attaché au joueur (propriétaire), le joueur ne le verra pas, mais il sera visible pour tout le reste.

Cliquez sur Compiler , puis sur Lecture . Notez que les particules n'apparaissent pas pour la caméra du lecteur, mais sont affichées sur la cible de rendu.


Jusqu'à présent, la capture de scène est configurée pour tout capturer. Évidemment, cela ne nous convient pas, car seules les particules affectent l'herbe. Dans la section suivante, nous apprendrons à capturer uniquement les particules.

Capture de particules


Si nous capturons des particules maintenant, nous effectuerons une flexion inutile dans les zones sans particules. En effet, la couleur d'arrière-plan de la cible de rendu est noire. La flexion se produit parce que le noir indique un mouvement vers les axes XY négatifs (après redistribution). Pour que les zones vides ne contiennent pas de mouvement, nous devons effectuer le rendu de la cible d'arrière-plan (0,5, 0,5, 0) . La façon la plus simple de le faire est de créer un énorme avion et de le fixer au lecteur.

Tout d'abord, créez du matériel pour l'arrière-plan. Revenez au Navigateur de contenu et ouvrez Materials \ M_Background . Connectez ensuite la constante (0,5, 0,5, 0) avec Emissive Color .


Remarque: comme pour le matériau particulaire, tout matériau que nous capturons doit avoir un modèle de shader non éclairé .

Cliquez sur Appliquer et fermez le matériau. Revenez à BP_Mannequin , puis créez un nouveau composant Plan . Nommez-le Contexte .


Ensuite, définissez les propriétés suivantes:

  • Emplacement: (0, 0, -5000). Nous plaçons l'avion si bas qu'il ne chevauche aucune particule.
  • Echelle: (100, 100, 1). Nous évoluons donc à une taille suffisante pour couvrir toute la zone de capture.
  • Matériel: M_Background


Comme pour les particules, il serait étrange que le joueur voie un énorme avion jaune en dessous. Pour le masquer, activez Rendu \ Owner No See .


Maintenant que nous avons configuré l'arrière-plan, il est temps de capturer les particules. Nous pouvons le faire en ajoutant un système de particules à la liste en lecture seule de la capture de scène. Il s'agit d'une liste de composants qui captureront la capture de scène.

Utilisation de la liste en lecture seule


Avant de pouvoir ajouter à la liste des émissions uniquement, nous avons besoin d'un moyen d'obtenir tous les acteurs qui affectent l'herbe. Une façon de les obtenir est d'utiliser des balises . Les balises sont de simples chaînes qui peuvent être attribuées aux acteurs et aux composants. Ensuite, vous pouvez utiliser le nœud Obtenir tous les acteurs avec le tag pour obtenir tous les acteurs avec le tag correspondant.

Puisque l'acteur du joueur doit influencer l'herbe, il a besoin d'une étiquette. Pour ajouter une balise, cliquez sur le bouton Class Defaults . Créez ensuite une nouvelle balise dans Actor \ Tags et nommez-la GrassAffector .


Étant donné que seuls les composants peuvent être transférés dans la liste en lecture seule, nous devons ajouter des balises aux composants qui affectent le gazon. Sélectionnez le composant GrassParticles et ajoutez une nouvelle balise située dans la section Balises . Nommez-le également GrassAffector (il n'est pas nécessaire d' utiliser cette balise). Répétez la même chose pour le composant Arrière - plan .


Maintenant, nous devons ajouter des composants influençant l'herbe à la liste de capture de scène uniquement visible. Cliquez sur Compiler et fermez BP_Mannequin . Ouvrez ensuite Blueprints \ BP_Capture . Accédez à Event BeginPlay et ajoutez les nœuds en surbrillance. Assurez-vous également que les broches marquées sont connectées.


Ce circuit parcourra tous les acteurs avec la balise GrassAffector . Après quoi, elle vérifiera si l'acteur a des composants avec cette balise et les ajoutera à la liste en lecture seule.

Ensuite, nous devons dire à la capture de scène d'utiliser uniquement la liste à afficher uniquement. Sélectionnez le composant SceneCapture et accédez à la section Capture de scène . Définissez le mode de rendu primitif pour utiliser la liste ShowOnly .


Cliquez sur Compiler et fermez le plan. Si vous cliquez sur Lecture , vous verrez que la cible de rendu capture désormais uniquement les particules et le plan d'arrière-plan.


Dans la section suivante, nous arrivons à ce que nous attendions. Il est temps d'apprendre à l'herbe à se plier!

Pliez l'herbe


Nous devons d'abord projeter la cible de rendu sur l'herbe. Accédez au dossier Matériaux et ouvrez M_Grass . Créez ensuite les nœuds illustrés ci-dessous. Définissez la texture sur RT_Capture .


Puisque nous avons redistribué les couleurs dans l'intervalle de 0 à 1, avant de les utiliser, nous devons redistribuer les couleurs dans l'intervalle de -1 à 1. Pour ce faire, ajoutez les nœuds en surbrillance:


Maintenant que nous avons la direction de flexion, nous avons besoin d'un moyen de faire tourner l'herbe dans cette direction. Heureusement, il existe un nœud appelé RotateAboutAxis pour cela. Créons-le.


Commençons par le contact NormalizedRotationAxis . Comme son nom l'indique, il s'agit de l'axe autour duquel le sommet tournera. Pour calculer, nous avons juste besoin d'un produit vectoriel de la direction de flexion de (0, 0, -1) . Pour ce faire, nous devons ajouter les nœuds sélectionnés:


Nous devons également spécifier le RotationAngle , c'est-à-dire la quantité de rotation du sommet par rapport au point de rotation. Par défaut, la valeur doit être comprise entre 0 et 1, où 0 est 0 degré et 1 est 360 degrés. Pour obtenir l'angle de rotation, on peut utiliser la longueur du sens de flexion, multipliée par la rotation maximale.


La multiplication par une rotation maximale de 0,2 signifie que l'angle de rotation maximal est de 72 degrés.

Le calcul de PivotPoint est un peu plus difficile, car un seul maillage d'herbe contient plusieurs tiges. Cela signifie que nous ne pouvons pas utiliser quelque chose comme le nœud Position de l' objet , car il renverra un seul point pour toutes les tiges d'herbe.

Idéalement, vous devez utiliser un éditeur 3D tiers pour enregistrer les points de pivot à l'intérieur des canaux UV. Mais pour ce tutoriel, nous approchons simplement le point de pivot. Cela peut être fait en se déplaçant du haut vers le bas jusqu'à un certain décalage.


Pour ce faire, ajoutez les nœuds sélectionnés:


Dans ce didacticiel, l'herbe mesure environ 80 unités de hauteur, j'ai donc défini cette valeur pour PivotOffset .

Ensuite, nous devons effectuer deux masques. Le premier masque garantit que la racine de la tige ne bougera pas. Le deuxième masque garantit qu'aucun champ vectoriel n'agit sur l'herbe en dehors de la zone de capture.

Masquage


Pour ce tutoriel, j'ai défini les couleurs des sommets de l'herbe afin que les sommets inférieurs soient noirs et les sommets supérieurs blancs.


Pour masquer les racines, nous multiplions simplement le résultat de RotateAboutAxis par le nœud Vertex Color .


Pour masquer l'herbe en dehors de la zone de capture, nous multiplions le résultat précédent par le nœud sélectionné:


Cliquez sur Appliquer et fermez le matériau. Cliquez sur Play et courez à travers l'herbe pour y laisser des empreintes!


Où aller ensuite?


Le projet terminé peut être téléchargé ici .

Bien que la méthode présentée dans le didacticiel fonctionne très bien pour les objets simples tels que l'herbe, elle n'est pas suffisante lorsque vous utilisez des objets qui nécessitent plus de dynamisme. Une solution partielle au problème consiste à utiliser les versions physiques du feuillage. Voir cet article sur le feuillage interactif pour plus d'informations.

Enfin, je tiens à remercier Deathrey de la communauté Unreal Engine pour le conseil de cette méthode des particules!

Source: https://habr.com/ru/post/fr420079/


All Articles