Quick Links: Download Gideros Studio | Gideros Documentation | Gideros community chat | DONATE
Gideros Unite: framework for multiplayer mobile games — Gideros Forum

Gideros Unite: framework for multiplayer mobile games

ar2rsawseenar2rsawseen Maintainer
edited July 2012 in Code snippets
Finally I can lift it from my shoulders, been bothering me for some time, constantly improving and adding features. Now need to let it cool for a while, but here it is and feel free to use it.

Gideros Unite framework provides a way to implement Multiplayer games using Gideros Mobile. It uses LuaSocket to establish socket connections and even create server/client instances.

It provides the means of device discovery in Local Area Network, and allows to call methods of other devices through network.

There is also an example app, you can try out.

Framework: http://appcodingeasy.com/my_classes/gideros/Unite/Unite.lua

Example app: http://appcodingeasy.com/my_classes/gideros/Unite/DrawTogether.zip

Docs:
http://appcodingeasy.com/Gideros-Mobile/Gideros-Unite-framework-for-multiplayer-games

Any suggestions for improvements are welcome. ;)

Sample server code:

function onAccept(e)    
    --auto accept client with provided id
    serverlink:accept(e.data.id)
end
 
--create a server instance
serverlink = Server.new({username = 'myServer'})
--add event to monitor when new client wants to join
serverlink:addEventListener('newClient', onAccept)
--start broadcasting to discover devices
serverlink:startBroadcast()
 
 
--and then before entering game logic
--if we are ready toplay
--stop broadcasting
serverlink:stopBroadcast()
--and start only listening to clients
serverlink:startListening()

Sample client code:

function onJoin(e)
    --auto connect to server with provided id
    serverlink:connect(e.data.id)
end
 
--create client instance
serverlink = Client.new({username = 'IAmAClient'})
--create event to monitor when new server starts broadcasting
serverlink:addEventListener('newServer', onJoin)
 
--event to listen if server accepted our connection
serverlink:addEventListener('onAccepted', function()
    print('server accepted our connection')
end)

Sample game logic code:

--we can get all devices that are connected to our network
local devices = {}
serverlink:addEventListener('device', function(e)
    print(e.data.id, e.data.ip, e.data.host)
    devices[e.data.id] = {}
    devices[e.data.id].ip = e.data.ip
    devices[e.data.id].name = e.data.host
end)
 
serverlink:getDevices()
 
 
--add some methods, that could be called by other clients or server through network
--draw something
serverlink:addMethod('draw', self.drawLine, self)
--end drawing
serverlink:addMethod('end', self.stopDrawing, self)
--clear drawing
serverlink:addMethod('clear', self.reset, self)
 
 
--then you can call this methods when needed
serverlink:callMethod('clear')
serverlink:callMethod('draw', someX, someY)
 
 
--or call method of specific device using it's id
serverlink:callMethodOf('clear', 112233)
serverlink:callMethodOf('draw', someX, someY, 112233)
 
 
--and when game is finished
serverlink:close()
 
 
--and that's all

Example video

+1 -1 (+19 / -1 )Share on Facebook
«13

Comments

  • I can't wait to start using this. I have an app that needs this right now and I was dreading having to get to grips with Sockets.lua on my own. I'll let you know how I get on.

    Many thanks and best regards,
  • Great! Thank for sharing. That help me save a lot of time.
  • @ar2rsawseen as usual very cool code, I will certainly be giving this a go very soon :)
    ThumbHurt Games / FB: ThumbHurt Games / FB: Eli/Teranth | Skype: teranth37
  • atilimatilim Maintainer
    edited July 2012
  • this seems really perfect thanks for sharing.
  • gorkemgorkem Maintainer
    Arturs strikes again. Must tweet :)
  • Godsend! Thank you for sharing

    ps: is that the voice of your kid in the video ;) ?
    have fun with our games~
    http://www.nightspade.com
  • thanks for the awesome code =D>
  • ar2rsawseenar2rsawseen Maintainer
    edited July 2012
    @Nascode
    yep it is my kid, that was a hard day for him, because daddy was playing with ipods and mobiles all day. The problem is that he wanted to play with them :) He's got very good at using ipod.
    And ipod is just small enough not to skate on it :)
  • >:) >:) >:) >:) >:)

    i'm waiting for glass digitizer (it come from olanda) then my ipad back to life... :)
    >:) >:) >:) >:) >:) >:)
    TNT ENGiNE for Gideors Studio - Particle Engine, Virtual Pad, Animator Studio, Collision Engine - DOWNLOAD NOW !!! IT'S FREE!!! -
    www.tntengine.com
  • pykasopykaso Member
    Breathtaking work! Thanks !
  • AlexRuAlexRu Member
    @ar2rsawseen, thanx very much!
  • @ar2rsawseen
    Amazing, I'm looking forward to integrating this in my app.
    Question that might be out of the scope of this thread : Is that possible, in one way or another, that a client joins the server without having the app installed on both devices? (server only)?

    See Mario Kart's Download Play
    If all your racing buddies have a Nintendo 3DS system, only one of you needs a copy of Mario Kart 7 to enjoy Download Play.
    twitter@TheWindApps Artful applications : The Wind Forest. #art #japan #apps
  • ar2rsawseenar2rsawseen Maintainer
    @Mells well it would be similar to send all app code and assets to that other device and on the other end load them and execute using loadString().

    It is possible, but I'd probably wouldn't do it. As it will be hard to install an app that loads some code dynamically by Apple terms
  • @ar2rsawseen
    I see, thank you for the answer.
    twitter@TheWindApps Artful applications : The Wind Forest. #art #japan #apps
  • is it possible to connect to a pc written server? e.g. A windows drawing app talking to the iphone, or would this need the likes of bonjour etc
  • Well, when Gideros would support Desktop applications on Windows and Mac, that won't be a problem. :)

    But right now, yeah it's still possible to do this, but you must implement same protocol that Gideros Unite uses. I may need to write some docs to explain different commands it handles. But it is possible.

    If you are interested in it, let me know and I'll prepare the docs.

    I also had an idea of creating a php script using sockets and same protocol for creating central remote server. But probably won't have enough time to complete it in near future
  • @ar2rsawseen
    I was wondering (before I can try myself it this weekend) do you think there is a delay from client to server?
    For example for a game like ready steady bang where each millisecond counts, should I consider that this kind of system would never be fast enough? (obviously I am talking about the system itself, not about your coding abilities :)
    twitter@TheWindApps Artful applications : The Wind Forest. #art #japan #apps
  • ar2rsawseenar2rsawseen Maintainer
    edited August 2012
    @Mells, well even in Local Network, even using only UDP for faster connection, server would still have some advantage, because information delivery is not instant. And in these kind of games even 100ms could be a huge advantage.

    So some different approach is needed.

    Let's say (using minutes:seconds:millisecond format) :

    Server sends a start countdown signal at 00:00:000, and bang signal should appear after 3 seconds.
    So server starts countdown immediately and bang signal appears in 00:03:00.

    But other phone receives signal at 00:00:100 and only then launches the countdown, which will end at 00:03:100. As you see other phone has disadvantage.

    What we do, as we take current time in each device separately, when countdown starts
    local startTime = os.timer()
    And then take current time when player shoots (releases finger or how it is done).
    local endTime = os.timer()
    Then we calculate the difference between start and shooting
    local diffTime = endTime - startTime
    And send it to server. In server we compare our relative times from all players and find fastest one (basically find minimal value).

    So even if other phone receives bang signal 100ms later, it's relative time would still be the same, from countdown start, to shooting time.

    Hope that clears something :)



  • @ar2rsawseen
    that would work :)
    That will be a bit harder to add to my game because I check victories differently (with handicap and delay for some characters etc) and I remove the event listener for the second player as soon as the first one has played (lot of behaviors depend on that choice that I made from the beginning) so I can't compare their relative times without having to rewrite other areas.
    The app grew up beyond my plan, a few parts are in spaghetthi mode :/ (I know it's bad... will do better next time!).

    But this framework would be perfect for my game, I'll experiment after the initial release.
    twitter@TheWindApps Artful applications : The Wind Forest. #art #japan #apps
  • @ar2rsawseen

    This works great. I am trying to get my head around the code now.

    There is one thing I notice though so can you give me an explanation?

    1. I loaded the DrawTogether sample into Gideros

    2. I changed my Player settings to run on the player on my iphone and ran the code from the editor. The start screen comes up with Start new, Join and About buttons on the iPhone.

    3. Switched over to the editor and changed the player settings to localhost and ran the code again. The start screen comes up with Start new, Join and About buttons on the PC player as well. So far so good.

    4. I can now start a server on the iPhone and Join from the PC but not vice versa. If I start the server (Start new) on the PC Player the iPhone does not show that a server is available and I cannot join.

    But if I start the server on the iPhone and join from the PC Player instance then everything works fine.

    Is there a reason for this? Is it something in the code or is it the setup I am using?
  • Hi, @bernard
    it's really hard to tell, where is the problem.

    I vaguely remember some problem with discovering, let's see if this makes difference.

    For example, in Gideros Studio you start app in IOS player, then change to localhost (so localhost now has active connection to Gideros Studio) and then you try your experiment.

    What about if you do it vice versa, first you connect to localhost and start the app, then switch to IOS player and start the app there, so IOS app remain the active connection to Gideros Studio. Does it change anything?
  • This is great @ar2rsawseen. With this and all you other efforts I think you should be promoted to demi-god status :)

    Likes: ar2rsawseen

    +1 -1 (+1 / -0 )Share on Facebook
  • Hi, @bernard
    it's really hard to tell, where is the problem.

    I vaguely remember some problem with discovering, let's see if this makes difference.

    For example, in Gideros Studio you start app in IOS player, then change to localhost (so localhost now has active connection to Gideros Studio) and then you try your experiment.

    What about if you do it vice versa, first you connect to localhost and start the app, then switch to IOS player and start the app there, so IOS app remain the active connection to Gideros Studio. Does it change anything?
    Nope. Tried that as well. Irrespective of whichever session is started first, and has the current "active" connection, I can only run the server on the iOS player and be seen in the Gideros Player. Running the server on the Gideros player and "Join"ing from the iOS player does not show any connection or server, so at this time there appears to be a difference and a problem with discovery.


    The only 2 things I have not tried are (1) to create an .ipa and install on 2 devices and then test and that is not possible now for me and (2) Disable the Firewall on my PC and try again.

    So to be very clear, irrespective of whichever session is the current connection to Gideros, the server broadcast from the Gideros PC Player is NOT seen by the session running on my iPhone player, but the server running on the iPhone player is seen by the Gideros player and works fine.

    I also tried this:

    I ran the player on my iPad1 and ran the app on Gideros, ran the player on iPhone and ran the app on Gideros and finally ran the PC player and ran the app.

    Between the iPad and the PC there is no problem connecting either way (server or client)

    But on the iPhone it only works as a server which both the PC and the iPad can connect. The iPhone session does not "see" the server sessions of either the iPad or the PC player.

    I was able to run 3 separate sessions on each device and by setting the iPhone as the server, could connect from the PC and iPad and have a 3 way session that worked.

    This leads me to the conclusion that there is some problem with the iPhone player and not actually with your code.
    <b>Server    Client       Result</b>
    PC         iPad          Works
    PC         iPhone      Not Working
    iPad       PC            Works
    iPad       iPhone      Not Working
    iPhone   PC            Works
    iPhone   iPad          Works
  • ar2rsawseenar2rsawseen Maintainer
    edited October 2012
    Wow thank you for comparison @bernard.

    Only thing that comes to mind, is that you might have two Internet connections on your Iphone (local wifi network, and some 3g from your carrier) and maybe it automatically selects 3g connection from your carrier and not a local wifi?

    @paul_k_clark ooh, thank you! ;)
  • Wow thank you for comparison @bernard.

    Only thing that comes to mind, is that you might have two Internet connections on your Iphone (local wifi network, and some 3g from your carrier) and maybe it automatically selects 3g connection from your carrier and not a local wifi?

    @paul_k_clark ooh, thank you! ;)
    I doubt that because when I tested it the 3G data was switched off as I was at home with Wifi. So as far as the iPhone was concerned, there was only 1 IP address.

    Also as I said above the app works fine as long as the iPhone is the server. It just does not work when acting as a client.
Sign In or Register to comment.