Publicité
+ Répondre à la discussion
Affichage des résultats 1 à 5 sur 5
  1. #1
    Acropole
    Invité(e)

    Par défaut Comment gérer correctement le réseau dans un FPS ?

    Bonjour,

    J'ai un problème avec mon code réseau sous Unity.

    Je procède comme ça :
    - Le client envoi les données du clavier et de la souris au serveur.
    - Le serveur envoi la position et la rotation résultantes à tous les clients (y compris l'envoyeur).
    - Les client fusionnent leur position et rotation avec celles reçues du serveur comme ceci :

    Code :
    1
    2
    3
    4
    5
     
    if(Network.isClient){
       transform.position = Vector3.Lerp(transform.position, serverPos, Time.deltaTime * 5.0);
       transform.rotation = Quaternion.Lerp(transform.rotation, serverRot, Time.deltaTime * 5.0);
    }
    Tout fonctionne correctement, même quand je fonce dans des objets physiques pour essayer de déphaser le client et le serveur.

    Mais ça lag !
    Et non seulement ça lag, mais si je bouge violemment la souris le personnage va jusqu'à la rotation désirée pour revenir légèrement en arrière en suite.

    Ceci malgré que j'exécute le serveur et le client sur la même machine. J'ose pas imaginer sur un serveur distant avec 80 de ping.

    Je suis obligé de faire un Lerp à cause de la physique, mais ça pause problème pour la rotation normale.

    Je souhaiterais avoir l'avis de spécialistes pour gérer ça correctement.

    Merci.

  2. #2
    Expert Confirmé Sénior
    Profil pro
    Développeur informatique
    Inscrit en
    novembre 2006
    Messages
    4 747
    Détails du profil
    Informations personnelles :
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Activité : Développeur informatique

    Informations forums :
    Inscription : novembre 2006
    Messages : 4 747
    Points : 6 534
    Points
    6 534

    Par défaut

    Salut Acropole par curiosité as-tu résolu le problème alors ?

  3. #3
    Acropole
    Invité(e)

    Par défaut

    Non, je ne m'occupe plus du réseau pour le moment. Quand j'aurais fini la partie solo toutes les données nécessaires seront disponibles pour passer en multi. Sinon il faut en permanence tester le mutli, puis rajouter des trucs gérés en solo, les tester puis les mettre en multi, etc. C'est un peu comme débugger deux programmes en même temps.

  4. #4
    Membre régulier

    Inscrit en
    août 2006
    Messages
    60
    Détails du profil
    Informations forums :
    Inscription : août 2006
    Messages : 60
    Points : 74
    Points
    74

    Par défaut

    Bonjour,
    pour faire simple, il est normal que ca "lag" !
    En effet, le serveur n'est pas censé calculé les rotations et les entrées clavier/souris des clients.
    Il est censé vérifier la véracité des informations (mouvement, rotation,..) des clients, mais ce n'est pas lui qui calcule la rotation de la camera lorsque la souris bouge. Sinon le temps que l'information fasse l'aller retour serveur, et que ton client fasse la rotation, un 1/10eme de seconde sera écoulé, et tu aura un lag.

    Si tu veux plus d'infos, n'hésite pas !

    edit : oups désolé pour la date du topic, pas fait attention

  5. #5
    Membre régulier
    Homme Profil pro
    Architecte serveur
    Inscrit en
    septembre 2011
    Messages
    58
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Architecte serveur
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : septembre 2011
    Messages : 58
    Points : 84
    Points
    84

    Par défaut

    Cette section du forum n'est pas très vivante dans tous les cas. Mais les gens répondent parfois sur des sujets antiques.
    Je vais donner plus de détails, Maldus ayant répondu succinctement.

    Sur une archi client-serveur, on distingue deux types d'actions côté client : Celles qui demande une vérification du serveur et celle qui ne le demande pas.
    Exemple, je tire sur un adversaire. Je suis obligé d'attendre la confirmation du serveur pour 'tuer' effectivement le joueur.
    Par contre, si je suis dans une salle vide, j'avance d'1 mètre. Qu'est ce que le serveur va me répondre ? Rien, vu que rien ne peut empêcher mon mouvement. Donc, dans ces cas là, on peut éviter d'envoyer une réponse au client, et le client peut immédiatement exécuter son déplacement.

    Sur un FPS, tu as besoin d'un maximum de répondant, donc tu dois maximiser les messages non vérifiés. Les messages de mouvement ne doivent pas être vérifiés, de même que les messages d'attaque (je veux pas avoir de lag entre le moment ou je clique et celui ou je vois partir mon tir).
    Les seuls messages vérifiés, ce sont les prises d'objets, et le fait de toucher un ennemi, toutes les actions que je qualifierai de binaires (soit tu as pris l'objet, soit tu l'as pas pris, soit l'adversaire est mort, soit il est vivant).

    Tu en déduis donc, à raison, que tu vas avoir une désynchro client-serveur de l'ordre du demi-ping (au lieu d'avoir un lag de l'ordre du ping). Il va donc te falloir faire des approximations.
    Par exemple, j'avance vers un ennemi, sur mon client je peux avancer, sur le serveur je ne peux pas car il y a collision. Il ne faut pas que le serveur 'annule' mon mouvement. En lieu et place, il faut qu'il y ait une marge, une zone dans laquelle on peut techniquement avancer sans que le serveur ne refuse ton mouvement, mais ou le client stoppera le joueur. Par exemple, côté client, tu peux avoir une zone de collision de 2 mètres, et sur le serveur une d'1 mètre. Donc, tant que je suis à plus de 2 mètres de mon adversaire, je peux avancer vers lui. Côté serveur, si mon mouvement ne m'amène pas à moins d'un mètre de l'adversaire, il sera validé. Par contre, si j'arrive à 2 mètres ou moins côté client, le client m'empêchera d'avancer plus (quand bien même techniquement le serveur m'y autoriserai). Ainsi, il y a peu de chance que le client m'autorise le mouvement et que le serveur me l'interdise, il faudrait que dans le temps d'un ping, mon adversaire ait parcouru plus que ce fameux mètre de marge. Ainsi, j'aurais un mouvement fluide et jamais invalidé côté serveur. Comme les collisions entre joueurs sont très rares sur les FPS, ça n'a que peu d'importance qu'il y ait approximation à ce niveau là.

    Une seconde chose très importante, c'est de ne jamais se baser sur le mouvement de ton personnage, mais sur sa position. Donc, plutôt que d'envoyer au serveur : J'avance d'un mètre. Tu lui envoies : Je suis ici. L'avantage étant que quelque soient les calculs, le serveur comme le client auront exactement la même position. Alors que si tu envoies des messages incrémentaux, tu as un risque de désynchronisation progressive entre le client et le serveur (je rappellerai à ce sujet qu'avec des doubles ou des floats, tu peux vérifier l'égalité suivante : "x != y && x - y == 0", donc tu auras quasi nécessairement une désynchro, même légère).

    Dernier point (j'aborde tous les points importants), l'interpolation des déplacements. Je vais l'aborder d'abord par un exemple. Je suis au point A, et je vais au point B. Au moment ou je suis au point B, j'envoie au serveur ma nouvelle position. Le serveur reçoit mon message, il me pose au point B, et envoie l'information aux autres clients. Les autres clients reçoivent le message et ... s'ils me mettent immédiatement au point B, il va y avoir téléportation de mon personnage => ultra laid.
    Il faut donc que tu fasses des interpolations. Au moment où je suis au point A, j'envoie l'information de position au serveur de même que l'information sur ma vitesse et direction. Au moment ou j'arrive au point B, j'envoie la nouvelle information. Le serveur ne positionnait plus mon personnage au point A, mais au point A + interpolation de déplacement par rapport aux informations de vitesse et de direction que je lui ai transmises. Donc je suis déjà très proche du point B. Au moment ou les autres clients reçoivent mon information de position, ils ont aussi fait une interpolation, donc mon point B est très proche du point de positionnement de mon personnage sur leur client.
    C'est la raison pour laquelle dans tous les FPS, il y a un léger effet retard (de l'ordre d'un ping) qui t'empêche de pouvoir changer de direction instantanément. Il y a 100ms entre le moment ou j'annonce que je change de direction et le moment ou mon personnage a vraiment changé de direction.

    Bon, après tout cela, il existe encore des optimisations possibles. Mais sur des ping inférieurs à 100ms, ça devrait déjà être bien suffisant pour donner de bonnes sensations à tes joueurs.

Liens sociaux

Règles de messages

  • Vous ne pouvez pas créer de nouvelles discussions
  • Vous ne pouvez pas envoyer des réponses
  • Vous ne pouvez pas envoyer des pièces jointes
  • Vous ne pouvez pas modifier vos messages
  •