Richtung durch Netzwerk übertragen
Übersicht

mevsmpBetreff: Richtung durch Netzwerk übertragen |
![]() Antworten mit Zitat ![]() |
|
---|---|---|
hi,
ich hab das in meinem 3D Spiel mit dem Netzwerk so geregelt: if keydown(taste) then variablefurnetzwerk = 1 if variable = 1 then MoveEntity Gegner.... Also wenn ein Client läuft, wird durch Writebyte eine 1 an den Server geschickt und an alle anderen weitergeleitet. Wenn ein Client die 1 empfängt, wird der Gegner durch MoveEntity bewegt. Und das hab ich für alle Richtungen gemacht : nach links laufen, rechts, hoch.... Das klappt auch, nur dass das sehr ungenau ist. Ich befinde mich meisten wo anders als es bei den anderen Clienten angezeigt wird.... Wie macht ihr das??? |
||
![]() |
hecticSieger des IS Talentwettbewerb 2006 |
![]() Antworten mit Zitat ![]() |
---|---|---|
Da unterschiedliche Rechner unterschiedlich schnell laufen können, solltest du die Position an die Clients schicken und nicht die Bewegung. Willst du es ganz perfekt haben, so solltest du dich zusätzlich mit frameunabhängigem Programmieren beschäftigen. Dann würde das ganz so ablaufen. Senden der Position und der Bewegungsgeschwindigkeit in bestimmten Zeitabständen. Dann wird die Geschwindigkeit bei allen Rechnern mit der internen Deltavariable multipliziert. Dies kann sehr nützlich sein, wenn mal keine Daten von anderen Rechnern empfangen werden, dann wird bei jedem Rechner eine 'Zukunftsprognose' für die jeweiligen Positionen errechnet.
Hier mal ein Beispiel mit DP: Code: [AUSKLAPPEN] Graphics 400,400,0,2
SetBuffer BackBuffer() nettyp%=0 netfrm%=0 netabc$="" td#=0 tp#=0 Type pos Field xp# Field yp# Field xg# Field yg# Field id% Field nm$ End Type Print "1-Host" Print "2-Client" wahl=Input() If wahl=1 Then spiel=HostNetGame("IDKFA") If wahl=2 Then spiel=JoinNetGame("IDKFA","127.0.0.1") sp.pos=New pos sp\xp=20 sp\yp=20 sp\xg=0 sp\yg=0 sp\nm=Input("Spielername: ") sp\id=CreateNetPlayer(sp\nm) td=1 tp=MilliSecs() ;Hauptschleife While Not KeyHit(1) For sp.pos=Each pos sp\xg=sp\xg/((0.0002*td)+1) sp\yg=sp\yg/((0.0002*td)+1) sp\xp=sp\xp+sp\xg*td sp\yp=sp\yp+sp\yg*td If sp\xp<000 Then sp\xp=sp\xp+400 If sp\xp>400 Then sp\xp=sp\xp-400 If sp\yp<000 Then sp\yp=sp\yp+400 If sp\yp>400 Then sp\yp=sp\yp-400 Rect sp\xp-4,sp\yp-4,9,9,1 Text sp\xp+6,sp\yp-6,sp\nm Next ;Nachricht empfangen If RecvNetMsg()=1 Then nettyp=NetMsgType() netfrm=NetMsgFrom() ;NachrichtTyp Neu If nettyp=100 Then sp.pos=New pos sp\xp=20 sp\yp=20 sp\xg=0 sp\yg=0 sp\id=netfrm sp\nm=NetPlayerName$(netfrm) End If ;NachrichtTyp Weg If nettyp=101 Then For sp.pos=Each pos If netfrm=sp\id Then Delete sp Next End If ;NachrichtTyp Info If nettyp=1 Then For sp.pos=Each pos If netfrm=sp\id Then netabc=NetMsgData() sp\xp=Left$(netabc,Instr(netabc,"|")-1):netabc=Mid(netabc,Instr(netabc,"|")+1,-1) sp\yp=Left$(netabc,Instr(netabc,"|")-1):netabc=Mid(netabc,Instr(netabc,"|")+1,-1) sp\xg=Left$(netabc,Instr(netabc,"|")-1):netabc=Mid(netabc,Instr(netabc,"|")+1,-1) sp\yg=netabc End If Next End If Else ;Zeitschuld Delay 10 EndIf sp.pos=First pos If KeyDown(203) Then sp\xg=sp\xg-0.001*td If KeyDown(205) Then sp\xg=sp\xg+0.001*td If KeyDown(200) Then sp\yg=sp\yg-0.001*td If KeyDown(208) Then sp\yg=sp\yg+0.001*td td=MilliSecs()-tp tp=MilliSecs() ;Alle 200ms ;Info senden If tp>ts Then SendNetMsg 1,sp\xp+"|"+sp\yp+"|"+sp\xg+"|"+sp\yg,sp\id ts=tp+200 End If If KeyHit(57) Then w=1-w If w=1 Then Delay 80 Flip Cls Wend StopNetGame End Egal wie schnell oder langsam der andere Rechner läuft, beim eigenem wird die Bewegung flüssig dargestellt. Auch wenn mal keine Daten empfangen werden, wird die komplette Physik vom anderem dann interpoliert und vorrausberechnet. Erst wenn wieder Daten kommen, wird neu positioniert und eine Geschwidiglkeit vergeben. Mit [Space] kann man einen langsamen Rechner simulieren. Der Code wurde hier auf ein Rechner (funkioniert auch übers Internet (habs ausprobiert)) angepasst. Man muß eine Exe erstellen, damit man zweimal oder mehr das Programm (einmal als Host und maximal 99 mal als Client) auf einem Rechner starten kann. |
||
![]() |
rctuner |
![]() Antworten mit Zitat ![]() |
---|---|---|
hi,
schonmal danke für die antwort. Mit Frameunabhängigem Programmieren hab ich mich schon beschäftigt und hab das auch erfolgreich in meinem Code eingebaut. Deshalb lag das Problem sicher nicht an der Rechner Geschwindigkeit sondern am Netztwerk oder so... Damals hab ich auch immer nur die Positionen übertragen, aber mir wurde gesagt das wenn man nur die Richting überträgt und dann selber Movet, dass das schneller laufen würde.... Als ich auch nur die Positionen übertragen hab, hat die Gegner Figur sich nicht gerade flüssig bewegt, deshalb dachte ich es wär mit MoveEntity besser.. |
||
![]() |
hecticSieger des IS Talentwettbewerb 2006 |
![]() Antworten mit Zitat ![]() |
---|---|---|
rctuner und mevsmp die gleiche Person? Naja, egal. Lies mal den Text genauer durch, dann sollte es klar sein was genau gemacht wird.
Beispiele: 1) Nur Position Vorteil: garantiert das keine 'Verschiebung' im Spiel auftretten. Nachteil: Neupositionierung nur so schnell möglich wie Daten rein kommen. 2) Nur Bewegung Vorteil: Bewegungen laufen fliessend und sauber über die Bühne. Nachteil: Im fortlauf des Spieles kommt eine Verschiebung durch Rundungsfehlern auf. 3) Position und Bewegung Vorteil: Sowohl Neupositionierung als auch Bewegungen laufen gut ab. Nachteil: Aufwendigere Programmierung und etwas mehr Daten zu übertragen. In seltenen Fällen (nur wenn keine neue Daten mehr empfangen werden und die Spielfigur sich vorher schnell bewegt hat) kann es zu überschreitenden Bewegungen kommen. Die werden aber korrigiert, sobald neue Daten eintreffen. Mein Beispielcode beinhaltet die 3. Methode und wird wohl auch so in komerziellen Spielen gehandhabt. Nur halt nicht mit DP. Ist auch nur eine Übung gewesen. Zum testen kann man die Übertragungsrate mal runter setzen, zB auf ts=tp+1000 dann wird nur einmal in der Sekunde übertragen... |
||
Übersicht


Powered by phpBB © 2001 - 2006, phpBB Group