The game i’m developing will have lots of score mechanics, for players to mold their own score instead being defined by only one route to ‘highscore’. I’m wondering how events are usually propagated in a large scale gameworld (mmo’s for instance).
The route im currently taking involves a ScoreAppState that has an ‘enqueueScoreEvent(ScoreEvent e)’. This event may then be the death of an enemy, but may also just be a tower hitting an enemy with a single shot. But how would I go about making this method threadsafe, seeing as there may be many threads generating scoreevents.
It’s my plan to then have the ScoreAppState somehow pull from this list and process the events. The event information should be compact to allow for the appstate to actually keep up…
Would my approach be completely wrong ? Any tips regarding other ideas ?
What’s the purpose of enqueuing events?
You’ll get better throughput by simply calling whatever the event would trigger in the recipient.
That doesn’t mean the approach is invalid, but it does man that you need to be clear about what you wish to gain in return - decoupling, better latencies (which means you’ll have deferred processing so you only exchange one latency with another, might be fine or not), ability to multicore, whatever.
We need to know your goals before we can say whether you’re getting nearer
(Your first stop for thread safety would be java.util.concurrent. It’s pretty comprehensive, and I hear it’s good enough for almost everything; I think even the Guava guys didn’t have too much to add.)
If this is about a server side solution then JME can’t really help you. You are probably best off using a database (which has had a lot of people spend a lot of time optimising it for just this sort of thing) and storing the scores in that.
So you want to keep keep overhead under control, exploiting the fact that if there are multiple updates to the same data, it’s okay if only the last update goes through.
Suggestion: Have an object that keeps the latest value, and send that to all subscribers on a periodic basis.
This works as long as the update to the latest-value object is faster than sending to subscribers.
You do not need any additional multithreads for that, you can do the publishing inside the update loop like normal. If the publishing is noticeably slow, you could spread that effort over multiple frames, serving all subscribers in a round-robin fashion.
If you get a framerate drop and want to exploit multiple CPU cores, this would indeed be a good candidate for a separate thread.
I consider it resolved, but i’ll clarify a bit more in case it makes a difference
An example of the data could be bonus points that revolves around shots being fired on the same enemy with x seconds. Now, shot 1 would generate a ‘ScoreEvent’ in itself and the same does shot 2 and 3. The Shot 1 event cannot be discarded entirely from memory once processed the first time, because its part of a streak-bonus that only activates when y or more shots lands on the same enemy within x seconds.
My worry is that the process handling this wont be able to keep up. But I think I’ll have to go by trial and error to see how to flies. I’ll try to update this post once I get around to doing this