Android multiplayer tutorial kellene
2015-08-17T18:04:53+02:00
2015-09-17T10:41:02+02:00
2022-07-22T05:33:31+02:00
  • Na akkor most felteszem a kérdést: Milyen előnye van a websocket-nek a többi sockettel szemben?

    Menni fog bárhonnan, ahonnan megy a HTTP(S) is, át tud menni proxy szervereken is, illetve ezen az elven alapul a HTTP/2 protokoll is, amin most dolgoznak gőzerővel, mint az SPDY utódja.

    Lehet szimpla socket-et is használni, de azzal magadra húzol mindenféle support problémákat, amikor jönnek a felhasználók, hogy nem megy és adják sorra az egy csillagos értékeléseket - mondjuk jogosan.

    Annyit szeretnék tőle, hogy egy akármilyen szerver ki tudjon szolgálni sok androidos klienst.

    Wildfly 9.0.1, standalone web profile, egy darab war kell egy darab osztállyal:

    package com.sample.websocket; import javax.websocket.*; import javax.websocket.server.ServerEndpoint; @ServerEndpoint("/hello") public class HelloWorldEndpoint { @OnMessage public String hello(String message) { System.out.println("Received : "+ message); return message; } @OnOpen public void myOnOpen(Session session) { System.out.println("WebSocket opened: " + session.getId()); } @OnClose public void myOnClose(CloseReason reason) { System.out.println("Closing a WebSocket due to " + reason.getReasonPhrase()); } }

    Persze lehet mindenféle egyébbel szívni, de - ha már Java van a kliens oldalon, akkor érdemes a szerver oldalra is Java-t tenni.
    Mutasd a teljes hozzászólást!
  • Jóéjt :)
    Mutasd a teljes hozzászólást!
  • Köszönöm!

    Akkor úgy tűnik megvan a hálózati motorom is végre :)
    Ez lesz az

    Kiindulásnak nagyon jó lesz. Kétszemélyes "szobákat" nyitok, és minden kliens regisztrálja magát hogy melyikben játszik. Aztán már csak üzengetni kell. Végre alhatok :)
    Mutasd a teljes hozzászólást!
  • Megy http protokollon keresztül, ami a legtöbb helyen engedélyezve van (tűzfalak, proxyk, cégek, mobilnetek stb), míg valami 10666 -s portra sokan nem tudnak majd csatlakozni.

    De amúgy rossz a megközelítés, mert nem kell feltétlen socket, php/mysql jatékokszerverek simán elmennek socket nélkül. Ha meg komolyabb lesz a játékod, akkor is elég a sima tcp, és a jaték szerveren a 80-s porton legyen a játékod, akkor semmi előnye nem lesz a websocketnek, sőt csak lassabb lesz.

    http://eng.kifi.com/websockets-vs-regular-sockets/

    Ja, mivel a http az ugye sima tcp-n megy :)
    Mutasd a teljes hozzászólást!
  • Elvitte már ez életkedvemet az a sok-sok példa és forrás amit eddig átrágtam és kb semmi eredményre nem jutottam. Vagy mert nem működik, vagy mert extrém bonyolult. Legfrissebb élményem egy c++ kód volt, ami a boost libet használja. Speciel működik, le is tudom fordítani, és ugyan elvileg nem idegen tőlem a c++, de ezt egészen egyszerűen nem értem :(

    Ellenpéldának találtam például egy ilyet, elég egyszerűnek tűnik.

    public class TCPEchoServer { private static ServerSocket servSock; private static final int PORT = 1234; public static void main(String[] args) { System.out.println("Opening port...\n"); try { servSock = new ServerSocket(PORT); //Step 1. } catch(IOException ioEx) { System.out.println("Unable to attach to port!"); System.exit(1); } do { handleClient(); } while (true); } private static void handleClient() { Socket link = null; //Step 2. try { link = servSock.accept(); //Step 2. Scanner input = new Scanner(link.getInputStream()); //Step 3. PrintWriter output = new PrintWriter(link.getOutputStream(),true); //Step 3. int numMessages = 0; String message = input.nextLine(); //Step 4. while (!message.equals("***CLOSE***")) { System.out.println("Message received."); numMessages++; output.println("Message " + numMessages + ": " + message); //Step 4. message = input.nextLine(); } output.println(numMessages + " messages received."); //Step 4. } catch(IOException ioEx) { ioEx.printStackTrace(); } finally { try { System.out.println( "\n* Closing connection... *"); link.close(); //Step 5. } catch(IOException ioEx) { System.out.println("Unable to disconnect!"); System.exit(1); } } } }
    Na akkor most felteszem a kérdést: Milyen előnye van a websocket-nek a többi sockettel szemben? Annyit szeretnék tőle, hogy egy akármilyen szerver ki tudjon szolgálni sok androidos  klienst. Az egyszerű kezelhetőség igénye lépett elő szinte minden más szempont elé.

    A példa amúgy innen származik.
    Mutasd a teljes hozzászólást!
  • Phpwebsocket nem játszik, ultraweb nem szereti, és egyébként is. A Jwebsocket amit idáig nézegettem mert a demója elindul és szépen működik, de ez egy atombomba :( Nekem valami pehelysúlyú kellene ehhez képest...
    Mutasd a teljes hozzászólást!
  • Milyen jól elvagyok itt magamban.. Szóval aludtam rá egyet, és arra jutottam hogy feleslegesen frusztráltam magam tegnap. Voltaképpen nem is kell hogy a szerver is androidos legyen, sőt még jobb is ha nem. Csak az volt a tézisem hogy ha már egy helyen van, akkor könnyebb tesztelni. Közben meg kb nincs rá lehetőség (vagy legalábbis eldugva az internet bugyraiban). Kliensre van kitaposott út, szerverre meg keresek valami más platformot mondjuk linuxra valami scriptet. Lehetőség szerint natív megoldást azért, hogy kicsi legyen az erőforrás igénye. Ötlet szintjén mindjárt itt van egy phpwebsocket például. Nem tudom az ultraweb engedi-e egyáltalán. Azért keresek tovább is.
    Mutasd a teljes hozzászólást!
  • Találtam egy oldalt, ahol állítólag klasszul működik ez a dolog. Kis szépséghiba, hogy java applet adja a szervert, és javascript a kliens. Gondoltam ha már van valami szerverszerűség, akkor csak jó lehet. Nos amit az oldal ígér az tényleg működik, de amint megpróbáltam ráfaragni az androidra, máris csőd.
    Amúgy ez az az oldal: WebSocket tutorial with Java server (Jetty) and JavaScript client - jansipke.nl
    Mutasd a teljes hozzászólást!
  • Na, csak sikerült összelapátolni egy fordítási hiba mentes valamit.

    package com.example.websocket_demo; import android.app.Activity; import android.os.Bundle; import com.example.websocket_demo.R; import com.koushikdutta.async.http.AsyncHttpClient; import com.koushikdutta.async.http.WebSocket; public class ClientActivity extends Activity { String baseUrl = "192.168.0.106"; protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); final AsyncHttpClient client = AsyncHttpClient.getDefaultInstance(); client.websocket("ws://" + baseUrl + "/ws/proxy", "ws", new AsyncHttpClient.WebSocketConnectCallback() { @Override public void onCompleted(final Exception ex, final WebSocket ws) { if (ws != null) { ws.setStringCallback(new ResponseCallback()); } } }); } private class ResponseCallback implements WebSocket.StringCallback { @Override public final void onStringAvailable(final String payload) { } } }
    De ez így még kevés a boldogsághoz. Ha jól látom, akkor a ws csak az onCompleted-ben áll rendelkezésre, ami ha jól gondolom akkor hívódik meg ha kaptam valamit. Tehát ha valahol küldeni szeretnék, akkor a ws-t szednem kell valahonnan. A másik pedig hogy az a frame az micsoda? Úgy látom csak a kérdések szaporodnak, a cél meg egyre messzebb lebeg :(
    És akkor még csak kliensem van, szerver sehol.. Ha hiszed ha nem, már napok óta túrom a netet, de egy nyomorult echo programot nem találtam ami ezt használná. Csak annyi, hogy egyik program csücsül és várja hogy valaki szóljon, a másik meg felhívja és egy mondatot váltsanak egymással. De semmi. Nem hiszem el. :(
    Mutasd a teljes hozzászólást!
  • Hát ez nem akar összejönni.

    Próbáltam úgy hogy letöltöm a jar fájlt az oldalról, beleteszem a próba projektem lib könyvtárába, és a beállítások között megadom hogy van egy ilyen lib-em, használja. Na így nem megy.
    Azt is próbáltam hogy bemásoltam az AndroidAsync src mappáját a sajátom mellé, de így is nyafog, hogy ebben a sorban: 

    ws.setStringCallback(new ResponseCallback());

    a stringcallback  csak stringcallback-ot kaphat paraméterül, azt meg nem tudja példányosítani. Olyan mintha az importok nem akarnának összeállni.
    Mit rontok el, hogy kell ezt beüzemelni?
    Mutasd a teljes hozzászólást!
  • Én megfogadom a tanácsot, de akkor ugyan mutass már egy példát az autobahn kezelésére, ami nem pilótavizsgás!

    Hinnye, megnéztem a forrást és rájöttem, hogy már másik klienst használok: koush/AndroidAsync

    Így kell kapcsolódni:

    final AsyncHttpClient client = AsyncHttpClient.getDefaultInstance(); client.websocket("ws://" + baseUrl + "/ws/proxy, "ws", new AsyncHttpClient.WebSocketConnectCallback() { @Override public void onCompleted(final Exception ex, final WebSocket ws) { if (ws != null) { ws.setStringCallback(new ResponseCallback()); } } });

    A küldés ennyi:

    ws.send(frame.toString());

    A fogadást pedig a ResponseCallback osztály végzi:

    private class ResponseCallback implements WebSocket.StringCallback { @Override public final void onStringAvailable(final String payload) { } }
    Mutasd a teljes hozzászólást!
  • Én megfogadom a tanácsot, de akkor ugyan mutass már egy példát az autobahn kezelésére, ami nem pilótavizsgás! Annyi kell, hogy egyik androidos eszköz (kliens) elküld bármit a másik androidos eszköznek (szerver), és ez oda vissza megy. A többit már megoldom!
    Mutasd a teljes hozzászólást!
  • Összefoglalom: libgdx lesz az alapja az egésznek, ez már biztos.

    Az jó, én is erre jutottam, amikor egy éve körbenéztem, hogy mit érdemes használni... ha esetleg kell valami segítség vagy inspiráció, akkor lehet, hogy tudok valamit mondani. :)

    Most a websocketre keresek valami könnyen használható megoldást. Egyik jelölt az általad javasolt autobahn, a másik amit most találtam az a libgdx-net.

    Az Autobahn tud WebSocket-et, a libGdx hálózati rétege nem, a különálló libGdx-net projekt valamennyire tud, de ahhoz három éve nem nyúltak és van vele bőven szívás... én azt javaslom, hogy a libGdx hatáskörén kívül oldjad meg a hálózat kezelését... :)
    Mutasd a teljes hozzászólást!
  • Vannak bizony!

    Éppen túrom a netet egy egyszerű, de azért használható okosságért. Összefoglalom: libgdx lesz az alapja az egésznek, ez már biztos. A váz már működik, vannak figurák akiket el lehet indítani, egymást megkeresik, egymásnak ugranak, némi haláltusa után elhaláloznak. Amikor létrehozok egy figurát, akkor ő tárolja hogy a játékidő szerint mikor jött létre, megkapja hogy most mennyi az idő, ebből tudja hogy hol kellene lennie. Ha találkozik valakivel, akkor leáll csatázni. HA túléli, akkor újrakezdi az életciklusát az új pozícióból, természetesen a csökkentett élettel. Ha belepusztul, akkor van egy lejárati ideje amíg a meghalás animációt mutatja. Ekkor már nincs a játékban. Kb ennyi a lényeg egyenlőre. Mindezt a kliens számolja ki, elég ráérősen. Hálózati forgalomnak annyit gondoltam, hogy amikor küld a user egy karaktert akkor azt elküldi, és a jelentősebb eseményeket is, pl varázslat (ez még nincs). Most a websocketre keresek valami könnyen használható megoldást. Egyik jelölt az általad javasolt autobahn, a másik amit most találtam az a libgdx-net. Még nem tudom mire jutok vele, de bizakodó vagyok. Elejében egy androidos kütyü lesz a szerver, később az élő fázisban egy linuxos gépen fog futni valami. Még később.. az még a kutya vacsorája esete. Ha jól gondolom abban a szerencsés helyzetben vagyok, hogy gyakorlatilag egy chat-szerverre van csak szükségem. A szobák a játékteret jelentik. A userek bejelentkeznek egyesével, és ha megvan a létszám (2 fő), akkor indulhat a játék. Az meg csak annyi hogy elküldi mindenki hogy éppen mit indított, meg egy-két apróság. Bárki bármit küld, azt mindenki megkapja a szobában. A résztvevők a két játékos, a szerver, meg opcióként egy monitor alkalmazás, hogy lássam ha valaki huncutkodik, vagy csak szeretném kívülről megfigyelni a játékot. Ami most következik az az, hogy megírom ezt a chat-alkalmazást. Ha ez megvan, a többi már szerintem nem lesz gond.
    Mutasd a teljes hozzászólást!
    Csatolt állomány
  • Ilyesmi... :)

    ...vannak fejlemények? :)
    Mutasd a teljes hozzászólást!
  • Mutasd a teljes hozzászólást!
  • Az azonosítással kell még játszani, hogy ne a user:pass párost küldjem át.

    Ne küldj ilyet... Android-on ott a GoogleId, OAuth2 protokollon, amit tudsz a szerveren validálni, így csak egy token megy át és nem kell azzal törődnöd, hogy regisztráljon és nem kell authentikációval, se authorizációval foglalkoznod.
    Mutasd a teljes hozzászólást!
  • Egyenlőre maradtam a php+sql-nél, hogy legyen egy prototipusom. Két három játékot el kell bírjon így is egyszerre. Most ott tartok, hogy van egy "chat-room", amibe két játékos tud bemenni egyszerre. Ha nincs játékos, akkor nincs room se, valamint egy játékos nem tud bemenni kétszer. A ping időt 50ms-nak mértem (+-30), ez nem egzakt csak a miheztartás végett. Ha sorozatban nyomtam, akkor lement 40-re. Használhatónak tűnik. Következő egy androidos frontend lesz a php-ra, majd pár adatot próbálok meg  megosztani a játékosok között. Nagyon komoly tesztprogram lesz: egy-egy bogyót lehet majd tologatni a képernyőn ;o)
    Az azonosítással kell még játszani, hogy ne a user:pass párost küldjem át. Ennek még utána kell néznem, bár ha egy eleve kódolt adatcsomagot küldök át, akkor kvázi mindegy is..

    Ami a "nagyokat" illeti, ez már annyira túlmutat rajtam, hogy valószínűleg ebben az életben nem kerülök egy országba se velük. Maradok a kissebb egyszerűbb megoldásoknál. Ha véletlenül annyira kinőné magá t a program hogy kezd számítani, akkor majd kerítek valakit aki át tudja dolgozni a gyenge részeket. De erre szerintem nem fog sor kerülni. Hiába no, a hobbi az hobbi ::)
    Mutasd a teljes hozzászólást!
  • A játéktér nem kell máshová. Instance belépés/kilépésnél mentik csak a karaktert (minek lépésenként az adatbázis??).

    Például azért, hogy ha megdöglik a szerver, akkor ne vesszen el minden és ne legyen inkonzisztens a letárolt adathalmaz... és a szerverek már csak olyanok, hogy időnként megdöglenek, főleg, ha van belőlük több tízezer. :)

    Instance -ok meg szépen skálázhatóak több szerverrel (pl: wow, diablo is így megy).

    A Battle.net mögött elég komoly elosztott infrastruktúra van, az utóbbi pár év álláshirdetéseiből nekem az jön le, hogy többnyire Oracle stack-et használnak, legalábbis mindig igényeltek RAC ismeretet és előny volt a Coherence tudás is. Meglepődnék, ha pusztán memóriában tárolnák a játékteret és az állapotokat.

    Se IO művelet, se adatbázis, csak szimplán a memóriában. Nyilván ezen engine-eket nem apache mögé php-ban tervezik.

    Nyilván nem ilyesmit használnak... terveztem és kiviteleztem már pár magas rendelkezésre állású földrajzilag elosztott rendszert különféle terhelési profillal... :)

    Az elvi eltérésünk oka, a más játékmenet: én egy RPG MMO (wow, diablo, metin, taichi panda stb.) játékok képzeltem el, és írtam.

    Ami hol érhető el és mekkora volt a legnagyobb terhelése? :)
    Mutasd a teljes hozzászólást!
  • Ez a Cassandra.. ez mivel tud többet mint mondjuk egy mysql?

    Teljesen másra jó... nem SQL, hanem NoSQL adatbázis, földrajzilag elosztott architektúrára találták ki. :)

    Ha van egy szervernek való gépem, akkor ezt fel kell telepítenem, és ez futtatja a szerver programomat?

    Igen.
    Mutasd a teljes hozzászólást!
  • A wildFly alkalmazásszerver gyakorlatilag egy java ee megvalósítás jól értem? Ha van egy szervernek való gépem, akkor ezt fel kell telepítenem, és ez futtatja a szerver programomat?
    Mutasd a teljes hozzászólást!
  • Az architektúra jelenleg így néz ki (oldalra és lefelé is lapozható prezentáció, a nyilak jelzik az elérhető irányokat): Golden Age of Civilizations - Rule your empire!

    Nem piskóta!
    Mutasd a teljes hozzászólást!
  • Ahja... elméletben... és csak memóriában, csak egy gépen, csak egy szálon. Nekem erre van most egy három különböző kontinensen futó elosztott adatbázis

    Így van, memóriban. A játéktér nem kell máshová. Instance belépés/kilépésnél mentik csak a karaktert (minek lépésenként az adatbázis??). Instance -ok meg szépen skálázhatóak több szerverrel (pl: wow, diablo is így megy).

    Se IO művelet, se adatbázis, csak szimplán a memóriában. Nyilván ezen engine-eket nem apache mögé php-ban tervezik.

    Több gépen, több szálon, jól skálázható. Írtam is hogy hogyan és miért (játéktér particionálás).

    Az elvi eltérésünk oka, a más játékmenet: én egy RPG MMO (wow, diablo, metin, taichi panda stb.) játékok képzeltem el, és írtam.

    (de azért ha az 1msec-be nem fér bele, akkor legyen 20x, azaz 20msec a 3000 heartbeat: hát nem izzad bele a szerver :D de ennek is belefér még  20x is, mert az is csak 400msec, még mindig van tengernyi ideje a szervernek, és a többi magja elbírja a kommunikációt meg az egyebeket).
    Mutasd a teljes hozzászólást!
  • Na erről van szó! Köszönöm szépen! Ezért kerestem én hiába..

    Ez a Cassandra.. ez mivel tud többet mint mondjuk egy mysql?
    Mutasd a teljes hozzászólást!
  • Tudnál valami példát linkelni amúgy a témával kapcsolatban?

    Az architektúra jelenleg így néz ki (oldalra és lefelé is lapozható prezentáció, a nyilak jelzik az elérhető irányokat): Golden Age of Civilizations - Rule your empire!

    Szóval websocket, de normális használható anyagot nem találtam csak html5-re :(

    A HTML5 a kliens oldal...

    Android-ra ott az Autobahn, remek leírással és példákkal: http://autobahn.ws/android/downloads/

    Szerver oldalra pedig a lehetőségek végtelenek, ha a JavaScript megy, akkor ott a Node.js, ha inkább Java, akkor Wildfly, mindegyikre van rengeteg WebSocket példa, meg kell keresni és kipróbálni. :)
    Mutasd a teljes hozzászólást!
  • Köszi a tanácsot!
    Tudom hogy neki kell futnom még egy párszor. Ez kb az ötödik verzió, de már nem számolom. Eddig azonban nem volt szükség a hálózatra. Ez még odatesz egy lapáttal. A tervezést úgy értettem, hogy azzal el tudok vonulni egy viszonylag csendesebb zugba öt percre. De ha lógnak rajtam a gyerekek, akkor kódolás közben már nem marad kapacitásom koncepcionálni, így az plusz munka lesz. És most még szabin is vagyok :)

    Tudnál valami példát linkelni amúgy a témával kapcsolatban? Nyilván nem az üzleti megoldásod érdekel, csak valami, amivel el lehet indulni. A php gyengesége a sebesség hiánya mellett hogy nem tud visszahívni. Szóval websocket, de normális használható anyagot nem találtam csak html5-re :(
    Mutasd a teljes hozzászólást!
  • A nekiugrást azért nem akarom elsietni, mert két (aktív) gyerek mellett nagyon fájna ha az alapoktól kellene újraírnom az egészet.

    Úgyis újra fogod írni az egészet néhányszor... :)

    ...mindig a rapid prototyping és a premature optimization is the root of all evil elve lebegjen a szemed előtt. A lehető leghamarabb tegyél ki működő prototípust a leendő felhasználóid elé, mert azonnal visszajelzéseket fogsz kapni, hogy jó-e az elképzelésed vagy sem. És több mint a fele nem lesz jó, mindenképpen faragnod kell a koncepción, az architektúrán és a protokollokon.

    Mindig csak egy kicsivel lépj túl a határaidon, ne álmodozz nagy dolgokról, ugyanakkor ne ess abba a csapdába se, hogy csak olyan eszközöket használsz, amelyeket jól ismersz. És ne add fel. :)
    Mutasd a teljes hozzászólást!
  • Nyilván nincs meg az ideális 1.5 ipc, legyen mondjuk 0.8. Egy sima 2Ghz -s 1 core -n, azaz 1 sec alatt elvégez 1600millió utasítást. Azaz ennyit (1M) kevesebb mint 1 msec alatt hajtja végre. Nekem nem tűnik soknak :)

    Ahja... elméletben... és csak memóriában, csak egy gépen, csak egy szálon.

    Nekem erre van most egy három különböző kontinensen futó elosztott adatbázis és middleware rendszerem (például https://eu.gacivs.info és https://us.gacivs.info) ami ugyanazt a játékteret kezeli... egészen konkrét méréseim és megoldásaim vannak, hogy melyik megoldás mennyire skálázható és mekkora terhelést okoz.

    De legyen igazad, iteráljátok a játékteret, nem nekem fog fájni, ha majd az első komolyabb felfutásnál összeomlik és nincs az a gép, amit alá tudsz tenni.
    Mutasd a teljes hozzászólást!
  • Igen, ezt én is észrevettem! A nekiugrást azért nem akarom elsietni, mert két (aktív) gyerek mellett nagyon fájna ha az alapoktól kellene újraírnom az egészet. Inkább a tervezési fázisra fordrdítok nagyobb hangsúlyt (a kissebik éppen egy gumimalacba gurgulázik, nem éppen programozóbarát környezet). Arra gondoltam, hogy mivel számításaim szerint elég kevés csomagra lesz szükség, mégis előbb php-vel támogatom meg (az gyorsan megvan), csak írok hozzá egy olyan felületet, hogy ha bármi miatt kevés lenne, akkor egy mozdulattal le tudjam cserélni websocket alapúra.
    Hát kíváncsi leszek.

    Mindenesetre köszönöm mindkettőtöknek!!!
    Mutasd a teljes hozzászólást!
  • Nincs vita, szerintem fejben más játékhoz tervezzük a leírásainkat.

    Szerintem kezd el írni, sokminden ki fog még jönni közben. Hajrá :)
    Mutasd a teljes hozzászólást!
abcd