18-12-2011, 08:48 PM
(Modification du message : 18-12-2011, 08:50 PM par Sephi-Chan.)
Je ne suis pas sûr de bien comprendre la problématique. Quand le serveur retourne le bilan d'une action au joueur, tu peux tout à faite te limiter au minimum de données nécessaires.
Par exemple, dans Conquest on Rails, j'ai plusieurs situations de ce type, à la différence près que dans mon cas, il ne s'agit pas de retour individuel : ce sont plutôt des messages envoyés à plusieurs joueurs. Quelques exemples :
Pour l'implémentation, côté serveur j'envoie un petit objet JSON en push :
Comme on peut voir, le volume de données est plutôt faible puisque ce sont presque essentiellement des nombres et de petites chaînes de caractères.
Côté client, je traite le message qui arrive (ici c'est du CoffeeScript, qui est compilé en bon vieux Javascript). Comme je le disais, dans mon cas c'est un push mais ça pourrait être un retour de requête Ajax) :
Ici, j'utilise un hash tout bête qui contient associe un type d'événement (PLAYER_JOIN, ATTACK_REPORT, etc.) à une fonction qui accepte un hash de données. Finalement, je ne fais que déléguer les données reçue à la bonne fonction (stockée dans
Comme tu peux le voir, je n'affiche pas de texte, mais le mécanisme resterai le même si je le faisais : j'utiliserais en plus un framework d'internationalisation en Javascript.
Est-ce que ça répond à ta question ou te donne des pistes ?
Par exemple, dans Conquest on Rails, j'ai plusieurs situations de ce type, à la différence près que dans mon cas, il ne s'agit pas de retour individuel : ce sont plutôt des messages envoyés à plusieurs joueurs. Quelques exemples :
- Un joueur se joint à une partie, les autres participants sont notifiés. Cela se manifeste par un emplacement libre de la salle d'attente qui se remplit du nom d'un joueur.
- La partie démarre, tous les joueurs sont notifiés. Cela se manifeste par un bouton "Rejoindre la partie" qui passe de grisé à allumé.
- Au sein de la partie, un joueur en attaque un autre, les autres sont notifiés. Cela se manifeste par des textes "-2 unités", des changements de couleur du territoire, etc.
Pour l'implémentation, côté serveur j'envoie un petit objet JSON en push :
# Indique aux participants qu'un autre participant a rejoint la partie.
Juggernaut.publish("games/#{@participation.game_id}", {
eventType: "PLAYER_JOIN",
color: @participation.color,
gameId: @participation.game_id
})
# Envoie aux participants le résultat d'un combat.
Juggernaut.publish("games/#{@game.id}", {
eventType: "ATTACK_REPORT",
attacker: {
unitsLoss: @attack.attacker_losses,
territoryId: @attacker.territory_id,
color: @attacker.participation.color,
winner: @attacker == @attack.winner,
unitsCount: @attack.attackers_count,
remainingUnitsCount: @attack.remaining_attackers_count
},
target: {
unitsLoss: @attack.defender_losses,
territoryId: @target.territory_id,
color: @target.participation.color
}
})
Comme on peut voir, le volume de données est plutôt faible puisque ce sont presque essentiellement des nombres et de petites chaînes de caractères.
Côté client, je traite le message qui arrive (ici c'est du CoffeeScript, qui est compilé en bon vieux Javascript). Comme je le disais, dans mon cas c'est un push mais ça pourrait être un retour de requête Ajax) :
juggernaut.singleSubscribe channel, (data)->
handlers[data.eventType](data)
Ici, j'utilise un hash tout bête qui contient associe un type d'événement (PLAYER_JOIN, ATTACK_REPORT, etc.) à une fonction qui accepte un hash de données. Finalement, je ne fais que déléguer les données reçue à la bonne fonction (stockée dans
handlers["PLAYER_JOIN"]
).
handlers =
# Colorize the placeholder.
PLAYER_JOIN: (data)->
$participation = $(".participation[data-game=#{data.gameId}]")
$placeholder = $participation.find(".#{data.color}_placeholder")
$placeholder.addClass(data.color)
$placeholder.removeClass("nobody")
# Enable the button.
START: (data)->
$participation = $(".participation[data-game=#{data.gameId}]")
$button = $participation.find("a")
$button.text($button.data("enable-with"))
$button.removeClass("disabled")
$button.addClass("success")
# Display visual feedback for the attack.
ATTACK_REPORT: (data)->
attacker = data.attacker
target = data.target
$attackerBadge = $("#badge_territory_#{attacker.territoryId}")
$targetBadge = $("#badge_territory_#{target.territoryId}")
showFloatingLoss($attackerBadge, attacker.unitsLoss)
showFloatingLoss($targetBadge, target.unitsLoss)
if data.attacker.winner
removeUnitsFromBadge($attackerBadge, attacker.unitsCount)
changeBadgeOwnership($targetBadge, attacker.remainingUnitsCount, attacker.color)
else
removeUnitsFromBadge($attackerBadge, attacker.unitsLoss)
removeUnitsFromBadge($targetBadge, target.unitsLoss)
Comme tu peux le voir, je n'affiche pas de texte, mais le mécanisme resterai le même si je le faisais : j'utiliserais en plus un framework d'internationalisation en Javascript.
Est-ce que ça répond à ta question ou te donne des pistes ?