Im Moment akzeptiert der Server in einem eigenen Accept-Thread die Clients, führt ein Handshake mit Initialdaten aus und startet zwei neue Handling-Threads für jeden Client.
Mein Rat ist nicht für jeden Client einen neuen Thread zu machen sondern einen einzigen
Handler Thread der die Sockets der Clients durcharbeitet.
Solange du jedoch glaubst nicht mehr als sagen wir mal 10 Clients zu haben sind neue Threads pro Client aber auch OK.
Auf der Client Seite sollte es mindestens 3 Threads geben:
1.Render Thread
2.Netzwerk Thread
3.Worker Thread für alles was sonst so parallel ausgeführt werden kann.
Deine Frame Rate fällt evtl deswegen weil einfach alles in einem Thread
gemacht wird auch sachen die mal länger dauern wie Netzwerk Verarbeitung.
Ausserdem gibt es dann immer noch die GC-Pause-of-Death (oder wie die hiess).
Wenn der GC mal ein "Full-GC" macht, dann kann es schon mal sein, dass
deine Renerloop für 1 sec hängt.
Mach einfach mal in den Program Arguments "-verbosegc" rein und schau wie lange ein "Full-GC"
so dauert.