mercredi 29 avril 2009

Vous avez toujours envie de développer votre premier jeu en C#, je vous avez promis « La bataille navale »,faisons le ensemble :D



Du nouveau, Oui, je reviens à vous avec du neuf, concernant quoi ?, … n’allez pas chercher bien loin, je vous l’avez promis … ouvrez bien vos oreilles : « The Navale Ballte : design , conception & codage en C# » Eh oui , on y est , ceci est donc le premier Tuto d’une série d’articles que je présenterai au fur et a mesure que je les préparerai.

Je ne vais pas non plus m’attarder à vous expliquer la philosophie de mon développement, donc, je vais essayer de faire le plus simple et le plus directe possible :D ,

A vos clavier donc, je vais commencer par introduire les couches que j’ai implémenté dans mon projet , ne soyez pas impressionné par ce mot , développer en couche ou en module vous offre plus de facilité ,une meilleure organisation de votre code et une plus grande efficacité d’intervention face aux bugs et aux éventuels problèmes.

Donc, en gros il y a mon application, c'est à dire mon jeu qui peut être lancé par n’importe quel utilisateur en vue de faire une partie et il y a le serveur qui se charge de synchroniser mon mode multi-joueurs, et pour que vous suiviez mon raisonnement je vais commencer par la partie serveur, les variables qui y sont définie et les fonctions de synchronisation que j’ai implémentée.

J’essayerai de détailler au maximum mon code, donc vous aurez des fois l’impression que
Je prendrai mon temps à expliquer les parties disons les plus compliquer même s’il n’y a rien de compliquer dans tout cela :D

Voici les variables que j’ai définie dans ma classe service, juste une petite remarque, les variables que j’ai définie en private ne sont accessible qu’a partir des fonctions de la même classe donc, pas a partir de mon applicatif coté client, ceux en static auront la particularité de
De rester statiquement modifiable par mes fonctions serveur , je sais ce que vous vous dite , mais c’est quoi ce truc de « statiquement modifiable » logiquement ; on ne peux modifié le statique et le modifiable ne peut pas être statique o_O ! , en réalité un objet statiquement modifiable restera statique jusqu'à sa prochaine modification pour ceux qui connaissent les principes du bistable par rapport au mono stable comprendront beaucoup plus facilement

private bool P1_play = false;

private bool P2_play = false;

private string P1_coup = "";

private string P2_coup = "";

static private bool P1_connection = false;

static private bool P2_connection = false;

static private bool P1_update = false;

static private bool P2_update = false;

static private string[] P1_B1 = new string[4];

static private string[] P1_B2 = new string[3];

static private string[] P1_B3 = new string[3];

static private string[] P1_B4 = new string[2];

static private string[] P2_B1 = new string[4];

static private string[] P2_B2 = new string[3];

static private string[] P2_B3 = new string[3];

static private string[] P2_B4 = new string[2];



Et comme vous voyez dans cette première potion de code j’ai définie six variables logiques. Les deux premières me permettrons de définir l’état ou disons rôle de chaque joueur, s’il a déjà joué, ou s’il a la main pour joué.les deux autres P1 & P2 connexion servent à définir le statut de chaque joueur (connecté ou non connecté) par rapport a la partie en cours. Et enfin les deux dernières celles de l’update qui permettent de connaitre si le joueurs a fournis ou pas toutes les informations nécessaire au lancement de la partie.

La question qui se pose maintenant, c’est comment faire pour animer tout cas, la je vous dirai « FONCTION » et je vais vous illustrer les quelques fonctions que j’ai développé coté serveur et qui me permettent de synchroniser ma partie.



public string allow_player()

public void play(string nb_player,string coup)

public string[] upload_position(string nb_player)

public void player_update(string nb_player,string pos1,string pos2,string pos3,string pos4)




Donc pour ce premier Tuto je vais faire tout simple et je vais commencer par ces 5 fonctions que je commenterai au fur et à mesure que je montre mon code.

Update_player , tout est dans sa définition :D , chaque joueurs sollicitera cette fonction avant de se mettre en état « je suis prêt a lancer ma partie » et cela permet d’updater les positions de ces quartes bateaux sur cette classe coté serveur , donc , après lancement de la partie chaque joueurs aura une grille caché , et elle n’aura qu’un seul truc a cacher cette grille , les positions des bateaux de son adversaire.

public void player_update(string nb_player,string pos1,string pos2,string pos3,string pos4)

{

if (nb_player=="P1")

{

P1_B1[0]=pos1.Substring(0,2);

P1_B1[1]=pos1.Substring(2,2);

P1_B1[2]=pos1.Substring(4,2);

P1_B1[3]=pos1.Substring(6,2);

P1_B2[0]=pos2.Substring(0,2);

P1_B2[1]=pos2.Substring(2,2);

P1_B2[2]=pos2.Substring(4,2);

P1_B3[0]=pos3.Substring(0,2);

P1_B3[1]=pos3.Substring(2,2);

P1_B3[2]=pos3.Substring(4,2);

P2_B4[0]=pos4.Substring(0,2);

P2_B4[1] = pos4.Substring(2, 2);

P1_update = true;

}

else

{

P2_B1[0]=pos1.Substring(0,2);

P2_B1[1]=pos1.Substring(2,2);

P2_B1[2]=pos1.Substring(4,2);

P2_B1[3]=pos1.Substring(6,2);

P2_B2[0]=pos2.Substring(0,2);

P2_B2[1]=pos2.Substring(2,2);

P2_B2[2]=pos2.Substring(4,2);

P2_B3[0]=pos3.Substring(0,2);

P2_B3[1]=pos3.Substring(2,2);

P2_B3[2]=pos3.Substring(4,2);

P2_B4[0]=pos4.Substring(0,2);

P2_B4[1]=pos4.Substring(2,2);

P2_update = true;

}

}



Je vous disais que la fonction update sert à faire parvenir les positions a ma classe coté serveur Pour que chaque joueurs puisse les updater, une deuxième fonction a été élaborer la fonction upload_posision , et la vous remarquez que les position sont retourner sur un tableau de string , donc , je les envoie en chaine de caractère et pour les exploiter coté joueur j’effectue une dé-concaténation et cela m’évitera bien sur d’entrer à chaque fois dans l’exécution de plusieurs boucles for(…) if()….else….





public string[] upload_position(string nb_player)

{

string[] Positions = new string[4];

if (nb_player == "P1")

{

Positions[0] = P2_B1[0] + P2_B1[1] + P2_B1[2] + P2_B1[3];

Positions[1] = P2_B2[0] + P2_B2[1] + P2_B2[2];

Positions[2] = P2_B3[0] + P2_B3[1] + P2_B3[2];

Positions[3] = P2_B4[0] + P2_B4[1];

return Positions;

}

else

{

Positions[0] = P1_B1[0] + P1_B1[1] + P1_B1[2] + P1_B1[3];

Positions[1] = P1_B2[0] + P1_B2[1] + P1_B2[2];

Positions[2] = P1_B3[0] + P1_B3[1] + P1_B3[2];

Positions[3] = P1_B4[0] + P1_B4[1];

return Positions;

}

}



Je continue alors avec mes fonctions, il en reste deux pour ce premier tuto , les fonctions , play et Allow_player, la fonction Play est sollicité a chaque coup dans la partie , elle informe chaque joueur sur son tour, s’il doit jouer ou s’il doit attendre le cout de son adversaire.
Et cela a travers les deux variables que j’ai définie précédemment, P1_play et P2_play

public void play(string nb_player,string coup)

{

if (nb_player == "P1")

{

P1_play = true;

P2_play = false;

}

else if (nb_player == "P2")

{

P2_play = true;

P1_play = false;

}

}



Et pour finir une dernière fonction, que n’était présente dans mon code, mais que j’ai préféré implémenté pour que ca fasse plus propre et que mon code soit bien compréhensible
Une fonction de ce genre vous sera surtout utilise si vous travailler sur une plus grosse application serveur , genre un serveur qui supporte 5,10 voir plus de 20 joueurs , la vous devrai allouer un état a chaque joueur , or , dans mon code la , je ne fais que fournir deux information , quel joueur s’est connecté et quel est son statue par rapport à la partie qui vas se lancer « P1 » ou « P 2 » imaginez un peu ce que cela risquerai de donner comme fonction dans le cas ou je travaille avec 10 joueurs en même temps. Je sais que ca vous excite tout ca ,ben , ne vous en faite pas , aussitôt que je terminerai ces premier tutos ou je vais montrer le plus gros de mon code on redéveloppera ensemble ce même algorithme pour une charge minimale de 10 utilisateurs :D , j’ai ma petite idée sur la manière la plus optimale de le faire ;)

Et si vous vous encore une fois revoir à quoi ça va ressembler à la fin , c'est ICI que ça se passe :)













6 commentaires:

  1. Tu devrais penser à incorporer une balise code, pour l'indentation et la mise en forme :)

    RépondreSupprimer
  2. oui , ça sera beaucoup plus pratique, je vais rectifier ça ;)

    RépondreSupprimer
  3. Bonsoir,

    Merci pour ce début de tuto très intéressant je voulais savoir quand on pourra avoir la suite ou si tu peux m'envoyer les sources

    RépondreSupprimer
  4. Sorry j'ai oublié mon nom c'est amadou

    RépondreSupprimer
  5. et bein cher ami je croyais pas qu'on avez de si bons développeurs en Algérie. je peut savoir quel étais ton projet de mémoire? merci.

    RépondreSupprimer
  6. slt amine ,
    en réalité mon projet de mémoire n'a rien à voir avec l'informatique vu qu'a l'époque je préparais un diplôme d'ingénieur en Automatique , depuis , j'ai carément changé de cap , j'ai intégré une Ecole d'ingénieur en France pour etre ingénieur Architecte des systemes d'information , ...

    RépondreSupprimer