Liquides
Un liquide est composé de deux parties : un volume et une surface. Le volume détermine les limites de l'espace dans lequel le joueur nage au lieu de marcher et permet de configurer le courant, le brouillard qui s'applique quand le joueur se trouve dedans, etc. La surface est une simple représentation visuelle qui marque la limite du volume de liquide. Elle peut se composer d'une simple feuille 2D sans collision (comme c'était le cas dans les jeux utilisant l'Unreal Engine 1), mais l'Unreal Engine 2 propose un actor dédié pour créer une surface liquide et un autre qui permet de l'animer.
Volume liquide
Eau
Le WaterVolume permet de simuler un volume d'eau (comme on pouvait s'y attendre). Il s'agit d'un PhysicsVolume préconfiguré avec un brouillard bleu, un LocationName approprié ("under water") et deux paramètres modifiés : bWaterVolume est vrai et FluidFriction est réglé à 2.4 (contre 0.3 pour un PhysicsVolume normal).
Une fois ajouté, le volume est immédiatement actif, même sans rebuild. Il est invisible, mais rentrer dedans change la physique du joueur qui peut alors nager dans toutes les directions. Tout objet qui pénètre dans le WaterVolume est ralenti et cause un bruit et un effet visuel d'entrée dans l'eau.
Les projectiles sont aussi affectés : les grenades sont par exemple ralenties et les schrapnels du canon flak perdent leur traînée jaune.
Modifier un WaterVolume revient à modifier un PhysicsVolume. La physique de nage et le comportement dans l'eau ne sont pas vraiment paramétrables car ils dépendent du modèle physique appliqué au joueur (qui devient alors PHYS_Swimming au lieu de PHYS_Walking). Si l'on veut agir sur ce modèle, il faut donc en créer un nouveau.
Le brouillard se modifie comme n'importe quel brouillard de volume.
FluidFriction est le paramètre le plus spécifique car il ne s'applique que si bWaterVolume est vrai : il définit la résistance du fluide au mouvement. Plus la valeur est basse, plus les joueurs et objets (notamment les projectiles, comme les grenades) conservent leur mouvement. Avec une valeur de 0, un objet en mouvement dans le liquide ne s'arrête jamais tant qu'il ne rencontre pas un obstacle ou ne sort pas du volume. À l'inverse, plus la valeur est haute, plus il redevient vite immobile lorsque la source du mouvement (déplacement ou chute) s'arrête.
Ce paramètre détermine donc la conservation du mouvement dans le liquide, mais pas la vitesse, qui reste la vitesse normale du mouvement imprimée à l'objet.
L'autre paramètre intéressant est ZoneVelocity qui, en imprimant un mouvement aux joueurs et objets se trouvant dans le volume, permet de simuler le courant d'une rivière ou le passage de l'eau dans une conduite.
Liquides toxiques
UT2004 ne propose pas un équivalent du SlimeZone ou du NitrogenZone présents dans Unreal et Unreal Tournament, mais il est facile de modifier un WaterVolume pour obtenir le même effet : un fluide qui blesse et tue le joueur. En plus de modifier la couleur du brouillard de volume (généralement pour un vert radioactif), il suffit de régler bPainCausing sur vrai pour que le volume cause des dégâts à quiconque rentre dedans, même partiellement, sans être complètement immergé (en fait dès que la collision du joueur entre en contact avec le volume). DamagePerSec détermine ensuite combien de dégâts sont infligés à chaque seconde.
Il faut prendre en compte que la valeur de DamagePerSec est appliquée au joueur plusieurs fois lors de son entrée dans le liquide, puis une fois par seconde. Si la valeur est assez haute, le joueur peut être tué dès qu'il entre en contact avec la volume, même si la valeur est inférieure à son nombre de points de vie.
DamageType détermine le type de dégâts infligés. Pour un liquide toxique, les dégâts Corroded ("Joueur s'est dissout") et Drowned ("Joueur a oublié de respirer") sont les plus adaptés.
Lave
Un volume spécial, LavaVolume, permet de créer de la lave, mais il ne s'agit pas, par défaut, d'un liquide. Activer bWaterVolume suffit cependant à en faire un liquide brûlant : le LavaVolume inflige par défaut 40 points de dégâts par seconde avec le DamageType FellLava qui ajoute des flammes aux corps des joueurs qui en meurent.
Si le joueur est fait de chair (s'il ne joue pas un personnage classé comme robot), son corps sera également remplacé par un squelette noirci.
Le LavaVolume n'a pas de VolumeFog par défaut, mais on peut lui en ajouter un comme à n'importe quel autre volume, de préférence rouge ou orange avec une très faible distance pour rendre le liquide presque opaque.
Une fois le volume réglé comme souhaité, il faut matérialiser la surface du liquide qui est pour l'instant totalement invisible.
Surface
La surface du liquide est réalisée à l'aide d'un FluidSurfaceInfo. Il s'agit d'une sous-classe de l'Info, au même titre que la ZoneInfo ou que la TerrainInfo.
La FluidSurfaceInfo projette autour d'elle un quadrillage portant la texture par défaut, qui peut s'animer en temps réel. N'importe quelle texture peut lui être attribuée en l'ajoutant au champ Skins de l'onglet Display de ses propriétés. On peut donc l'utilise aussi bien pour de l'eau que pour de la lave ou tout autre type de liquide.
La texture n'est appliquée que sur le côté supérieur de la FluidSurfaceInfo. Pour qu'elle soit visible du dessous, il faut que la texture soit paramétrée avec bTwoSided = vrai.
Par défaut, un léger mouvement aléatoire est appliqué au quadrillage et l'effet est animé une fois le rendu en temps réel activé.
Le maillage de la FluidSurfaceInfo est noir par défaut, ce qui le rend peu visible dans l'éditeur en vue Wireframe. On peut changer la couleur du maillage avec FluidColor.
Pour aller plus loin, il faut se plonger dans l'impressionnante liste de paramètres de la FluidSurfaceInfo.
Une fois l'actor texturé et placé au milieu du bassin, sa taille doit être modifiée : elle doit être agrandie, pour couvrir toute la surface du liquide, ou réduite, pour ne pas générer des triangles inutiles. Modifier la taille peut se faire de deux façons : en modifiant la taille des triangles qui composent la surface ou en modifiant le nombre de ceux-ci. Dans le premier cas, on modifie le paramètre FluidGridSpacing qui détermine la taille des côtés des triangles équilatéraux qui forment le maillage de la surface.
Dans le second cas, on modifie FluidXSize et FluidYSize, qui indiquent le nombre de sommets de triangles le long des deux dimensions de la surface. Cette précision est importante car les triangles partageant leurs sommets deux à deux, le résultat sera toujours qu'il y aura un triangle de moins que le nombre indiqué.
On peut d'ailleurs mettre des nombres différents pour que la FluidSurfaceInfo soit rectangulaire au lieu d'être un carré. La taille maximum d'un côté est 256. Une valeur plus grande dans ces deux paramètres n'agrandira pas la FluidSurfaceInfo au-delà.
Il n'est pas possible de rendre la FluidSurfaceInfo non rectangulaire. Si la forme doit être modifiée ou si l'on veut créer des trous dans la surface, il faut utiliser une texture avec un masque de transparence pour rendre invisibles les parties non désirées.
Par défaut, les triangles sont assemblés de manière à former des diamants. On peut décider de changer cela et de les assembler en quads, comme les polygones composant un terrain, en changeant FluidGridType en FGT_Square. A FluidXSize, FluidYSize et FluidGridSpacing équivalents, cela donne une surface légèrement plus grande que FGT_Hexagonal.
Remarquez au passage que la FluidSurfaceInfo est alignée sur la grille et peut subir une rotation comme n'importe quel autre actor. On peut ainsi avoir une FluidSurfaceInfo en biais, verticale ou même retournée du haut vers le bas.
À ce stade, tester la map permet de voir que la base du comportement du fluide est déjà préparamétrée : marcher dedans émet un son de pas dans l'eau et affiche des ronds là où le joueur se déplace, la surface réagit aux tirs et aux objets qui passent à travers en simulant des remous. Si un volume approprié se trouve sous la FluidSurfaceInfo, l'effet est déjà tout à fait convaincant et peut être suffisant.
Le paramétrage par défaut permet de simuler de l'eau, mais si l'on veut lui donner l'aspect d'un liquide gluant ou de lave épaisse, il est nécessaire de modifier le comportement de la surface et la façon dont les vagues se déplacent dessus. La FluidSurfaceInfo possède un grand nombre de propriétés qui permettent de modifier la façon dont les triangles se déforment et se déplacent.
Si le bassin se trouve dans un terrain, une priorité est d'ajouter le TerrainInfo au champ ClampTerrain. En cliquant dans le champ, le bouton "Trouv." apparaît. En cliquant dessus puis en cliquant quelque part sur le terrain, l'éditeur ajoute lui-même le nom de la TerrainInfo correspondante.
Par défaut, les polygones du terrain sont ignorés pour la collision des vagues à la surface du liquide, ce qui signifie que si deux bassins séparés sont couverts par une même FluidSurfaceInfo, les vagues de l'un peuvent déborder sur l'autre.
ClampTerrain permet de s'assurer que les vagues rebondissent et s'arrêtent en recontrant les polygones du terrain et ne peuvent donc pas influencer les autres bassins éventuels. Cela évite aussi qu'une vague forte passant sous le terrain ne fasse sortir du sol des polygones de la FluidSurfaceInfo qui doivent rester cachés.
La plupart des propriétés restantes gèrent le comportement des vagues et la génération d'un mouvement aléatoire sur le surface.
- FluidDamping : Plus la valeur est haute, plus le mouvement des vagues est amorti par la surface et s'arrête vite. Une valeur très haute empêche pratiquement les vagues de se former, à moins de leur donner une force très importante, et les empêche de se déplacer dans le fluide.
- FluidHeightScale : Cette valeur est un multiplicateur de tous les mouvements verticaux des vertices de la FluidSurfaceInfo. Utiliser par exemple une valeur de 2 double la hauteur des crêtes et la profondeur des creux, tandis qu'une valeur de 0.5 la réduit de moitié.
- FluidNoiseFrequency et FluidNoiseStrength : Ces deux paramètres permettent de définir la fréquence et la force des mouvements aléatoires générés à la surface de l'eau. FluidNoiseFrequency détermine le nombre d'oscillations par seconde de chaque vague générée. FluidNoiseStrength permet de spécifier les extrêmes entre lesquels une valeur sera choisie aléatoirement pour chaque mouvement généré.
- FluidSpeed : Détermine la vitesse à laquelle les vagues se déplacent à la surface du fluide. Plus la valeur est haute, plus la vitesse est grande. Avec une valeur basse, le liquide semble visqueux et les vagues se déplacent lentement. Ce paramètre est important si l'on veut simuler une boue toxique épaisse ou de la lave, car il permet de modifier radicalement l'aspect de la surface.
- FluidTimeScale : Permet d'accélérer la vitesse à laquelle le fluide est calculé. Plus la valeur est élevée, plus les effets sont rapides.
- ShootEffect, OrientShootEffect, ShootRadius et ShootStrength : Les deux premiers permettent respectivement de spawner un actor lorsqu'un tir touche la surface (par exemple en emitter) et de l'orienter ou non en fonction de la direction du tir. ShootRadius et ShootStrength permettent de paramétrer l'onde de choc créée sur la surface lorsqu'un tir la traverse.
- TouchEffect, OrientTouchEffect et TouchStrength : Identiques au précédent, mais gèrent l'effet produit lorsqu'un joueur ou un autre actor entre dans l'eau.
- RippleVelocityFactor : En relation avec les paramètres précédents, ce paramètre détermine le rapport entre la vitesse d'un actor qui rentre dans l'eau et l'amplitude des vagues qu'il cause.
- UpdateRate : La fréquence de mise à jour de la FluidSurfaceInfo. Si des oscillations très rapides sont ajoutées à la surface avec un FluidSurfaceOscillator (voir plus bas), il est possible que la simulation soit trop lente et que certaines impulsions soient "perdues". Augmenter l'UpdateRate permet de prendre en compte plus d'événements, au prix d'un impact sur les performances.
- WarmUpTime : Nombre de secondes de simulation précalculées au lancement de la map. Permet de ne pas commencer avec une FluidSurfaceInfo inerte, le temps que les premières vagues s'activent et commencent à la parcourir.
Un ensemble de propriétés permet également de modifier l'apparence de la texture appliquée sur la FluidSurfaceInfo :
- UTiles et VTiles : Nombre de répétitions de la texture sur les deux axes de la surface. Par défaut, ces valeurs sont à 1, ce qui signifie que la texture est parfaitement ajustée à la surface. Si l'on règle ces champs à 2, la texture sera répétée 2 fois sur la côté U et 2 fois sur le côté V (pour un total de 4 répétitions sur la totalité de la surface).
- UOffset et VOffset : Permettent de décaler la texture sur la surface.
Par défaut, les FluidSurfaceInfos sont insensibles à l'éclairage car bUnlit est vrai dans l'onglet Display de leurs propriétés. Il peut être souhaitable de désactiver bUnlit pour que la FluidSurfaceInfo prennent la lumière en compte. Attention néanmoins : le paramètre FluidColor, qui colore le maillage, colore aussi la totalité de la surface si bUnlit = faux.
L'éclairage n'est "naturel" que si FluidColor est totalement noir (c'est-à-dire si tous les champs qui composent sa couleur sont à 0), comme c'est le cas par défaut.
Enfin, la FluidSurfaceInfo possède son propre générateur de vagues de test pour expérimenter le comportement du fluide :
- TestRipple : Génère une vague paramétrable sur la surface qui tourne autour du centre de la FluidSurfaceInfo. La vague de test réagit aux collisions avec les actors et les terrains comme n'importe quelle autre.
- TestRippleRadius, TestRippleStrength et TestRippleSpeed : Spécifient la taille, la force et la vitesse de la vague de test. La force peut être positive ou négative pour créer une vague ou un creux, respectivement.
Un certains nombre de propriétés semblent non-opérantes.
- AlphaCurveScale, AlphaHeightScale et AlphaMax : Ces 3 propriétés permettent normalement d'opérer un mélange entre deux textures sur les plus hautes vagues, par exemple pour créer un effet d'écume. Dans les faits, il semble impossible de faire fonctionner cet effet qui n'est d'ailleurs jamais utilisé dans le jeu.
- bShowBoundingBow : Censé afficher une boîte englobant la totalité de la FluidSurfaceInfo, ce paramètre n'affiche que les limites de la surface au repos. Les vagues peuvent largement en dépasser, ce qui rend son intérêt limité.
Deux paramètres sont assez mystérieux :
- bNoRenderZ : Active le paramètre suivant ou non.
- NoRenderZ : Détermine une distance à partir de laquelle la FluidSurfaceInfo n'est plus affichée. Curieusement, il s'agit d'une limite de proximité et non d'éloignement : plus la valeur est élevée, plus il faut s'éloigner pour que la FluidSurfaceInfo soit visible ; elle disparaît lorsque l'on s'approche. Les valeurs négatives sont sans effet.
Pour réinitialiser une FluidSurfaceInfo (et notamment ramener les vagues à zéro), il suffit de rebuilder ou recharger la map. Il est possible qu'après le rebuild, la FluidSurfaceInfo reste parfaitement vierge et ne réagisse à aucune interaction, aussi bien dans l'éditeur qu'en jeu. Elle doit alors être réactivée en changeant temporairement une de ses propriétés, ce qui la "réveille", mais rebuilder la map à nouveau reproduira le bug. Il sera donc nécessaire de réveiller les FluidSurfaceInfos après tout rebuild et avant de sauvegarder la map afin qu'elles restent actives.
Ce bug est notoirement présent dans DM-IronDeity, où toutes les FluidSurfaceInfos sont figées (et où les FluidSurfaceOscillators ne sont pas paramétrés correctement).
Vagues
Il est possible de générer des vagues à des endroits précis de la surface et de leur donner la force et la vitesse voulue à l'aide d'un actor prévu pour : le FluidSurfaceOscillator, qu'il faut placer à la surface de la FluidSurfaceInfo. Ses propriétés sont très simples.
Le champ FluidInfo permet de lier l'oscillateur à la surface. Si ce champ est vide, l'actor n'a aucun effet. En cliquant dans le champ, les trois options "Util"., "Trouv." et "Eff." deviennent disponibles. "Util." ne fonctionne pas et "Eff." permet simplement de vider le champ si une FluidSurfaceInfo est déjà paramétrée. "Trouv." permet de cliquer sur la FluidSurfaceInfo voulue, mais il faut alors cliquer sur l'actor FluidSurfaceInfo (l'icône de vagues bleues), car cliquer sur la surface elle-même ou sur un autre objet (par exemple un terrain) fait planter l'éditeur.
Une fois la FluidSurfaceInfo voulue paramétrée, l'oscillateur fonctionne dès que l'affichage en temps réel est activé. Par défaut, cependant, rien n'est créé car Frequency et Radius sont à 0.
- Frequency : Le nombre d'oscillations par seconde. Par défaut, une valeur supérieure à 3 ou 4 ne marche pas car la FluidSurfaceInfo n'est pas rafraîchie assez vite pour prendre toutes les impulsions en compte. Il faut donc augmenter son UpdateRate.
- Phase : Permet de dire à quel point de sa courbe l'oscillation commence. Utile pour synchroniser la vague avec un événement extérieur si les deux sont décalés. Par défaut, cette valeur est 0. Une oscillation étant composée d'une impulsion vers le haut et d'une impulsion vers le bas, si, au lancement du jeu, la surface reçoit l'impulsion vers le haut, alors une Phase de 128 correspondra à une impulsion vers le bas.
- Radius : Le rayon de l'oscillation. Si la valeur est très basse, il peut être nécessaire de positionner l'oscillateur précisément sur un vertex de la surface. Plus le rayon est grand, plus le nombre de vertices affectés sera important.
- Strength : La puissance de la vague. Plus la valeur est haute, plus les creux seront profonds et les crêtes élevées. Si la valeur est positive, l'oscillation commence par une impulsion vers le haut puis une équivalente vers le bas. Cet ordre est inversé si la valeur est négative.
L'interaction de Strength et Radius permet de doser finement l'amplitude des vagues et le rayon d'action de l'effet pour obtenir le résultat désiré.
Notez enfin que plusieurs FluidSurfaceOscillators peuvent être utilisés sur une seule FluidSurfaceInfo. Les vagues réagissent les unes avec les autres et se mélangent pour donner un effet réaliste.
RSS Feed