TCP Script für Kartenspiel, Server/Client aufteilung

  • Halli halloo,

    Also mein Plan ist folgender: ein Kartenspiel, das komplett in Scite geschrieben wurde, soll über netzwerk die vorgänge simulieren, die live ablaufen würden.

    Ich kannte mich mit TCP bisher überhauptnicht aus und hab mir ein paar Grundkenntnisse über Tutorials und die Autoit Hilfe angeeignet, sodass ich folgende Idee bekommen habe:

    Der Host des Spiels wird den Server Starten und somit ein neues Spiel öffnen.
    Der Server wird den Dealer (=Kartengeber in Poker) simulieren, d.h. er übernimmt das "mischen", austeilen, berechnung der einsätze und des topfs, sowie die Auswertung der Hand zum schluss

    Außerdem muss überprüft werden, ob neue spieler an den tisch gekommen sind.

    Jeder weitere Spieler (=Gast) empfängt dann vom Server informationen über seine eigene Hand und die ausgeteilten Gemeinschaftskarten, worauf es eine Setzrunde gibt (=jeder Gast sendet Pakete zurück, die der Server auswertet


    Das Spiel besteht somit aus der server.exe, dem client.exe und ggf. einer lobby

    ich möchte mich aber nicht einfach aufs script stürzen und am ende einen sourcesalat produzieren


    da ich wie gesagt noch ziemlich neu in der materie bin würde ich mich über feedback freuen.
    Haltet ihr eine solche "Arbeitsaufteilung" für Server & Client für sinnvoll, wenn nein, warum nicht?

    Stimmt es dass sich der Host auch als client mit dem server verbinden muss?

    ich hab das gefühl meine lösung ist recht umständlich zu realisieren.

    Für jeden etwas stichhaltigen Hinweis gibts nen Freudensprung, versprochen !
    Lg


    -> wenn ich demnächst anfange, das Script zu schreiben, werd ich nochmal ein paar Ausschnitte posten
    bis dahin :thumbup:

  • Eine gute Idee, aber dann muss der Server immer ON sein damit das funktioniert.
    Wüsstest du denn wie du das machst oder hast du noch keinen Plan? Du hast dir ja die Tutorials schon durchgelesen, aber noch nicht angefangen.

    mfg BB

    "IF YOU'RE GOING TO KILL IT
    OPEN SOURCE IT!"

    by Phillip Torrone

    Zitat von Shoutbox

    [Heute, 11:16] Andy: ....böseböseböseböse....da erinnere ich mich daran, dass man den Puschelschwanz eines KaRnickels auch "Blume" nennt....ob da eins zum anderen passt? :rofl: :rofl: :rofl: :rofl:

    https://autoit.de/index.php?page…leIt#post251138

    Neon Snake

  • Würde dir empfehlen du gestalltest erstmal den "Server" ohne Tcp sprich du schreibst ihn so das er Mischen,Kartengeben,das Blatt auswerten,den Einsatz regeln usw. ohne die Daten der Clients machen kann. Sprich das Spiel im "offline" Modus.

    Dannach würde ich den Client schreiben der dann die Funktionen besitzt das wenn du auf eine Karte klickst das Packet gesendet wird oder wie auch immer das bei dir aussehen soll. Zu guterletzt setzt du vor das auswerten des Blatts noch das sammeln des Einsatzes (würde dir eine Zeitbegrenzung empfehlen).

    Rechtschreibfehler gehörem ausschlieslich dem Urheber, also mir, nin erlich Finger weg die gehören mir!

  • danke schonmal für die unterstützung :)
    rollen wir die antworten mal von hinten nach vorne auf:

    Würde dir empfehlen du gestalltest erstmal den "Server" ohne Tcp sprich du schreibst ihn so das er Mischen,Kartengeben,das Blatt auswerten,den Einsatz regeln usw. ohne die Daten der Clients machen kann. Sprich das Spiel im "offline" Modus.

    da es sich hierbei um Poker handelt, ist ein offline modus nicht notwendig (es kann ja nur multiplayer gespielt werden)

    hab die funktionen die ich brauche schon (für n spieler werden n*2 karten gegeben, im server in $aKarten gespeichert und dem clienten wird dann eine spielernummer zugewiesen (sagen wir m) sodass er dann vom Server $aKatzen[m] ausliest

    Wüsstest du denn wie du das machst oder hast du noch keinen Plan?

    also vom Grundgerüst in etwa so:

    server
    [autoit='server']


    ;#includes & globals
    dim $SvIp = @IPAddress1
    dim $SvPort = 3542 ;spielt der port eine rolle, außer dass der client den gleichen verwenden muss?

    tcpstartup()
    dim $MainSocket = TCPListen($svIp, $SvPort)
    If $MainSocket = -1 Then
    consolewrite("Error: Socket nicht erreichbar")
    Exit

    Dim $ConnectedSocket = -1 ;täusche verbindung vor
    Do
    $ConnectedSocket = TCPAccept($MainSocket)
    Until $ConnectedSocket <> -1

    #region MainProgramm
    #cs
    while schliefe (while connected)
    hier läuft das Mischen ab. dabei muss der Server folgende informationen verwerten:
    - anzahl der Spieler, die aktiv an der Hand beteiligt sind
    - die Plätze, die die jeweiligen Spieler gewählt haben
    - der Platz, an dem der Dealer Button liegt (der wandert von Runde zu Runde 1 weiter im Uhrzeigersinn)
    - die Anfrage an die betroffenen Spieler, ob sie die Grundeinsätze leisten wollen
    #ce
    if "alles in Orndnung" then
    $aKarten = _mischen/austeilen() ; mit TCPSend an die jeweiligen sockets
    endif
    _Setzrunde () ;mit TCPListen
    $aFlop[3] =_dealFlop () ;mit TcpSend
    _Setzrunde () ;mit TCPListen
    $turn = _dealTurn ;mitTCPSend

    ;usw usf
    ;while end
    #endregion

    TCPShutDown()

    [/autoit]
    client
    [autoit='client']


    ;#includes & globals
    global $svIPAddress = 123.456.7.101
    global $svPort = 3542

    TCPStartUp()

    Dim $ConnectedSocket = -1

    $ConnectedSocket = TCPConnect($svIPADDRESS,$svPORT)

    If @error Then
    consolewrite("TCPConnect failed with WSA error: " & @error)
    Else
    #cs
    Main programm des Clients
    - wartet auf Karten (TCPListen)
    - wartet darauf dass er an der reihe ist (läuft wohl auch übern server mit $iPlayersTurn oder so)
    - macht dann seinen Move (TCPSend(ConnectedSocket,$aMove))
    - wartet wieder darauf dass er dran ist
    #ce
    EndIf

    [/autoit]

    ich dachte mir, dass der Server jedem Seat ein Attribut zuweist (offen, besetzt mit Spieler "xyz")
    außerdem werden die Karten nicht an die Spieler, sondern die Plätze 1 bis 5 verteilt

    dazu bräuchte ich eine funktion, die überprüft, ob dieser Seat besetzt ist (= ob ein socket mit der Tischnummer existiert)

    Jeder Platz representiert also eine mögliche Verbindung


    SO << HIER EIN UPDATE >>

    Ich hab jetzt für jeden Platz eine TCPFunktion geschrieben und mit Adlibregister() eingebunden
    so sieht das beispielsweise mit Seat0 aus:

    [autoit]


    global $aSeat[1] = ["None"] ;none = nicht besetzt, IPadress = besetzt
    global $PORTSeat0 = 660 ;port für Seat 0
    global $Socket0 = TCPListen(@IPAddress1, $PORTSeat0) ;socket für seat 0

    [/autoit][autoit][/autoit][autoit][/autoit][autoit]

    func _tcpSeat0()
    Switch $aSeat[0]
    case string("None") ;wenn der Seat nicht besetzt ist
    Local $ConnectedSocket
    Do
    $ConnectedSocket = TCPAccept($Socket) ;warte auf anfrage
    Until $ConnectedSocket <> -1
    local $ClientIP = SocketToIP($ConnectedSocket) ;Hier wird die IP vom clienten zurückgegeben
    $aSeat[0] = $ClientIP
    case Else;wenn der Seat allerdings besetzt ist
    $recv = TCPRecv( $ConnectedSocket, 2048 ) ;wenn eine Nachricht eintrifft
    If @error Then
    $aSeat[0] = "None"
    Else
    _TCPTranslate($recv) ;interpretiere die daten und ändere variablen im script
    EndIf
    EndSwitch
    EndFunc

    [/autoit]

    wenn jetzt aber alle paar ms der TCP verkehr überprüft wird (über einen jeweils anderen Port obv) weiß ich nciht obd as zu Problemen führen kann

    haltet mich auf wenn ihr könnt haha :D

    E2:

    sah zwar schön aus aber wenn ich jetzt mit einem der 5 ports connecte, erhält der Server keine Nchricht

    um das zu überprüfen hab ich in das obige script folgendes hinzugefügt:

    [autoit]


    func _TCPTranslate ($sMsg)
    ConsoleWrite($sMsg)
    EndFunc

    [/autoit]

    und der client sieht so aus:

    client
    [autoit]

    #include <GUIConstants.au3>

    [/autoit] [autoit][/autoit] [autoit]

    TCPStartUp()

    [/autoit] [autoit][/autoit] [autoit]

    Dim $svIPADDRESS = @IPAddress1
    Dim $svPORT = 660
    Dim $ConnectedSocket = -1
    ;=======================================================
    $ConnectedSocket = TCPConnect($svIPADDRESS,$svPORT)

    [/autoit] [autoit][/autoit] [autoit]

    Dim $sData
    If @error Then
    MsgBox(4112,"Error","TCPConnect failed with WSA error: " & @error)
    Else
    ;Loop forever asking for data to send to the SERVER
    While 1
    ; InputBox for data to transmit
    $sData = InputBox("Data for Server",@LF & @LF & "Enter data to transmit to the SERVER:")

    If @error Or $sData = "" Then ExitLoop

    [/autoit] [autoit][/autoit] [autoit]

    TCPSend($ConnectedSocket,$sData)

    ; If send failed with @error then socket has disconnected
    ;----------------------------------------------------------------
    If @error Then ExitLoop
    WEnd
    EndIf

    [/autoit]

    könnte das an der do - schleife im adlib "_tcpSeat0" liegen? hängt sich das vllt irgendwie auf oder so?
    wenn ich meinem script vorgaukle, dass Spieler connected sind (durch manuelles ändern des eintrags in $aSeat) funktioniert es wunderbar, ich brauch also ne alternative für das ständige abfragen nach neuen paketen

    8 Mal editiert, zuletzt von zombie36 (21. Dezember 2010 um 07:07)

  • [autoit]

    Do
    $ConnectedSocket = TCPAccept($MainSocket)
    Until $ConnectedSocket <> -1

    [/autoit]


    Das würde bedeuten er wartet bis 1ne person beitritt, aber Poker spielt man bekanntlich ja mit mehreren.
    Du könntest ja durch ein Adlib Register immer Zugänge zulassen und so auch immer anzeigen lassen wie viele gerade mitspielen. Was ich mich auch frage ist,m die Kartenausteilung. Jede Karte darf nur einmal gegeben werden, also muss man viele If Fragen machen wenn du random benutzt.

    Zitat


    Zitat von »Sortoc«
    Würde dir empfehlen du gestalltest erstmal den "Server" ohne Tcp sprich du schreibst ihn so das er Mischen,Kartengeben,das Blatt auswerten,den Einsatz regeln usw. ohne die Daten der Clients machen kann. Sprich das Spiel im "offline" Modus.

    da es sich hierbei um Poker handelt, ist ein offline modus nicht notwendig (es kann ja nur multiplayer gespielt werden)

    Ich denke eher, er meinte um es erstmal zum Laufen zu bringen und dann einfach das TCPSend mit der jeweiligen Hand etc reinzubauen. Ich denke das ist das Schwerste.

    mfg BB

    "IF YOU'RE GOING TO KILL IT
    OPEN SOURCE IT!"

    by Phillip Torrone

    Zitat von Shoutbox

    [Heute, 11:16] Andy: ....böseböseböseböse....da erinnere ich mich daran, dass man den Puschelschwanz eines KaRnickels auch "Blume" nennt....ob da eins zum anderen passt? :rofl: :rofl: :rofl: :rofl:

    https://autoit.de/index.php?page…leIt#post251138

    Neon Snake

  • das kartengeben läuft folgendermaßen ab:

    [autoit]

    global $aDeck

    [/autoit][autoit][/autoit][autoit]

    For $i = 0 To 3
    For $j = 0 To 12
    $aDeck[$i * 13 + $j] = $aSuit[$i] & $j + 1
    Next
    Next
    $aCopyDekc = $aDeck

    [/autoit][autoit][/autoit][autoit]

    func _dealCard ()
    local $tRand = random(0,$ideckcount,1)
    local $iCard = $aCopyDeck[$tRand]
    $aCopyDeck[$tRand] = $acopyDeck[$ideckCount]
    $iDeckCount -= 1
    return $iCard
    EndFunc

    [/autoit]

    mein script funktioniert soweit, dass ich flop/turn/river und Holecards für eine runde in der console ausgebe (für jeden spieler wo nicht "None" in $aSeat ist.

    häng mein script man an

    ich versteh nämlich nciht so ganz was ich machen soll^^ sry


  • ich hab diese funktion für jeden seat und einen jeweils anderen port geschrieben..
    sodass er für jeden seat auf genau einen spieler wartet

  • 3 posts sind zwar zwei zuviel des guten, aber ich muss das nochmal pushen..

    bin nicht einen schritt weitergekommen.. schaffs immernochnicht zugänge zuzulassen
    die version mit der do schleife - kein erfolg
    adlib version - kein erfolg

    Zitat

    Du könntest ja durch ein Adlib Register immer Zugänge zulassen und so auch immer anzeigen lassen wie viele gerade mitspielen.

    wie würde das im grunde aussehen?

    hab mir übrigens die TCP udf angeguckt die ich oben verlinkt habe und sie funktioniert bei mir nicht (nur als info)

    ich denke ich mach irgendeinen gravierenden denkfehler weshalb ich mich nicht von der stelle bewege ^^

    wär über hilfe sehr glücklich

    frohe weihnachten und schöne feiertage