Bewegung "Algorithmus" in der client-server-Multiplayer (MMO) - Spiele?
Ich habe das schreiben von einer 2D-flash-multiplayer-Spiel und einem socket-server. Mein ursprünglicher plan für die Bewegung Algorithmus zwischen client und server war die folgende:
- Der client informiert den server über die der Spieler die Bewegung des Modus (vorwärts bewegt oder nicht bewegt) und die player s-drehen-Modus (nicht drehen, Links abbiegen oder rechts), wenn diese sich ändern.
- Die server-loops alle Spieler alle paar Millisekunden und berechnet den Winkel gedreht und die Distanz verschoben, basierend auf der Differenz in der Zeit. Die gleiche Berechnung erfolgt durch den AUFTRAGGEBER.
Meine aktuelle Berechnung für den Kunden (gleich Mathematik ist in server) ==>
Drehen
var newTimeStamp:uint = UtilLib.getTimeStamp(); //set current timeStamp
var rot:uint = Math.round((newTimeStamp - turningTimeStamp) /1000 * 90); //speed = x degrees turning every 1 second
turningTimeStamp = newTimeStamp; //update timeStamp
if (turningMode == 1) //left
{
movementAngle = fixAngle(movementAngle - rot);
}
else if (turningMode == 2) //right
{
movementAngle = fixAngle(movementAngle + rot);
}
private function fixAngle(angle:int):uint //fixes an angle in degrees (365 -> 5, -5 -> 355, etc.)
{
if (angle > 360)
{
angle -= (Math.round(angle /360) * 360);
}
else if (angle < 0)
{
angle += (Math.round(Math.abs(angle) /360) + 1) * 360;
}
return angle;
}
Bewegung
var newTimeStamp:uint = UtilLib.getTimeStamp(); //set current timeStamp
var distance:uint = Math.round((newTimeStamp - movementTimeStamp) /1000 * 300); //speed = x pixels forward every 1 second
movementTimeStamp = newTimeStamp; //update old timeStamp
var diagonalChange:Array = getDiagonalChange(movementAngle, distance); //with the current angle, howmuch is dX and dY?
x += diagonalChange[0];
y += diagonalChange[1];
private function getDiagonalChange(angle:uint, distance:uint):Array
{
var rAngle:Number = angle * Math.PI/180;
return [Math.round(Math.sin(rAngle) * distance), Math.round((Math.cos(rAngle) * distance) * -1)];
}
Scheint dies gut zu funktionieren. Um Verzögerung zu berücksichtigen, die der server korrigiert das Kunden-info, jeden jetzt und dann, durch das senden dieser Daten.
Mit diesem system eine sehr geringe Bandbreite verwendet wird, um die handle-Bewegung. Allerdings sind die Unterschiede zwischen meinem server und den client-Koordinaten und Winkel sind zu groß. Sollte ich vielleicht verlängern mein "Algorithmus", um auch zu berücksichtigen, die Wartezeit hat ein Benutzer? Oder gibt es bessere Wege im Umgang mit Bewegung im client<>server für multiplayer-Spiele mit guter performance?
Du musst angemeldet sein, um einen Kommentar abzugeben.
Mein erstes design wäre ähnlich wie bei Ihnen, aber wenn das nicht funktioniert, könnten Sie vielleicht auch erlauben, den client zu tun, ALLE Bewegung und müssen nur die server einige Bereich überprüft.
Also, wenn Ihre Letzte gemeldete position war X, der nächste muss innerhalb eines radius von X, wo der radius ist auf die Differenz im Zeitstempel vom client gesendet mit der x,y-Daten.
Meist ist es nur notwendig, zu erkennen, zu betrügen.
Stoppen, kämpfen, etc erfordern würde, eine position, die gesendet werden, zusammen mit dem Angriff und Aktionen ausgelöst durch Positionen würden nur ausgelöst werden, nachdem der Kunde schickte das update für diese position wäre aber server-basiert.
Nicht sicher, ob dies helfen würde, zu viel, aber es könnte halt die Stöße resyncs Sie sehen würde, von Ihrer ersten Algorithmus.
Kommentar Antwort:
Nein, die clients würden weiterhin informieren die server Ihrer position, aber der server würde nicht versuchen, zur Berechnung der nächsten position. Dies würde bedeuten, dass der server (und alle anderen clients) wäre mindestens eine sende - /Empfangs-Zyklus hinter sich in position.
Ich denke, ich sage nur lassen Sie den Kunden die ganze Arbeit machen, herauszufinden, wo der Charakter ist und sagen dem server, aber genügend info, dass die server können wahlweise Gültigkeit überprüfen, um sicherzustellen, niemand ist Betrug.
Den cheat-Erkennung kann auch deaktiviert werden, damit die Leistung oder nach dem Zufallsprinzip überprüfen.
Hinweis: Alle Kollisions - /positions-info für Objekte im Bereich Reisen müssten, um an den client gesendet werden, damit dies funktioniert.
Gibt es 2 Möglichkeiten, die ich denken kann, dies zu tun - haben Sie den client Befehle an den server & der server wird die ultimative map-keeper.
Oder halten Sie die Karten in den clients, & die clients müssen verbindungen mit anderen clients, die Sie "in der Nähe", um in Bewegung, mit Aufzeichnung durch den server & geprüft durch ein paar Kollegen (hacker, Polizei).
Interessant für mich ist die Möglichkeit der monitor-peer-verbindungen, und Kollegen, die haben eine Latenz von über einer gewissen Schwelle einfach nicht zeigen, bis in das Spiel.
Ist euer server so langsam, dass es nicht in den Griff, alle von der Bewegung? Vor allem in einem 2-d Spiel? Normalerweise, wenn ich kleine 2d-Spiele, die der server gibt mir wieder alle meine Bewegungen, so dass keine Berechnungen auf dem client erforderlich. Wenn der server beginnt zu hinken, habe ich einfach einfrieren, bis ein bit, das, was man normalerweise erwarten würde sowieso (obwohl dies fast nie passiert).
In jedem Fall würde ich auf jeden Fall sehen, wie die performance ist, ohne dass der Kunde irgendwelche tatsächlichen Berechnungen selbst. Wenn die Leistung nicht gut genug ist, sehen Sie, wenn die Schleife durch Spieler-Bewegungen auf dem server verursacht wird die Verzögerung (und einen anderen thread für jeden client).
Wenn es sich tatsächlich um eine echte Einschränkung in der Bandbreite (Bewegungen selbst pass sehr wenig Daten), dann sicherlich die Sie benötigen, um zu finden die Durchschnittliche Verzögerung, die bestimmten Benutzer und berechnen, dass in den Algorithmus. Jedoch, kontinuierlich zu halten, finden der Durchschnitt (für die Präzision), müssen Sie weiterhin die ping-server zu finden die round-trip-Zeit, das sollte nicht alles sein, was teuer ist.