JeuWeb - Crée ton jeu par navigateur
Petite solution pour alléger le code de certains - Version imprimable

+- JeuWeb - Crée ton jeu par navigateur (https://jeuweb.org)
+-- Forum : Discussions, Aide, Ressources... (https://jeuweb.org/forumdisplay.php?fid=38)
+--- Forum : Programmation, infrastructure (https://jeuweb.org/forumdisplay.php?fid=51)
+--- Sujet : Petite solution pour alléger le code de certains (/showthread.php?tid=4322)

Pages : 1 2 3


Petite solution pour alléger le code de certains - Origine - 01-09-2009

Voilà, Salut.

J'ai aidé plusieurs personnes à faire leurs systèmes de construction de bâtiments, et j'ai souvent vu une organisation comme ceci :

- Un fichier "batiments.php"
- Un fichier "Prix_batiments.php" inclus dans "batiments.php", et qui contient le prix en fer, cristal, or ... de chaque bâtiment, dans des variables.

Ce qui, par la suite, provoque l'apparition d'un code comme ça :
Code PHP :
<?php 
if(!empty($_GET['construction']))
{
switch(
$_GET['construction'])
{
case
"caserne" :
mysql_query("UPDATE ressources SET metal=metal-$MetalCaserne WHERE id='".$id."'") or die (mysql_error());
break;
case
"xxx" :
...
...
}
}

Ce qui donne lieu à un code très répétitif. Je vais donc proposer une solution, qui n'est pas celle que moi j'utilise, mais qui est, à mon gout, mieux que la votre.

Cette solution consiste à renommer d'une première part, toutes les variables du fichier "prix_batiments.php", sous la forme :
Code PHP :
<?php 
$BatimentRessource

Et de modifier votre fichier bâtiment, en remplacement le "switch", par cette fonction. Je vous ai mis son fonctionnement en commentaire.

Code PHP :
<?php 
////////////////////////////////////////////////////////////////////////////////////////////////////
// FONCTION "RessourcesAEnlever" le 1/09/09
////////////////////////////////////////////////////////////////////////////////////////////////////
/*
Cette fonction est appellée lorsqu'un bâtiment est mis en construction, pour indiquer à une requête SQL les
quantités de ressources à enlever de la base de données.
La fonction utilise la dénomination d'une variable à partir de la valeur d'une autre. Cela nous permet de
"personnaliser" les noms des variables pour chaque batiment sans avoir un code répétitif et barbant
autant que fastidieux.
Exemple : Je met construire le bâtiment "Centrale" :
On doit alors chercher dans le fichier "prix_batiments.php" le prix de la centrale (en métal par exemple), entré
sous la forme "CentraleMetal". Cette fonction va personnaliser une variable pour la nomer
"NombatimentRessource", donc ici : "CentraleMetal", exactement comme dans le fichier prix_batiments.php.
Ceci va nous permettre d'affecter la valeur de ce prix à une autre variable nommée "RessourceAEnlever",
donc ici : "MetalAEnlever".
La fonction retourne finalement un tableau (array) avec la valeur à enlever pour chaque ressource.

(Premières lignes commentées).
*/
function RessourcesAEnlever($Batiment)
{
include
'prix_batiments.php'; // On inclu le fichier où sont présentes les variables contenant les prix.
$BatimentAConstruire=$Batiment; // On stocke dans une variable le nom du batiment à construire, qui servira de préfixe.
$xMetal=$BatimentAConstruire.'Metal'; // On crée une variable qui se compose du nom du batiment et de la ressource, par exemple "CentraleMetal".
if(!empty($$xMetal)) // On vérifie si la variable que l'on viens de créer existe (pour éviter les erreurs).
{
$MetalAEnlever=$$xMetal; // Si oui, une variable "fer" est crée, pour contenir le contenu de la variable "CentraleMetal".
}
else{
$MetalAEnlever = 0;}

$xBeton=$BatimentAConstruire.'Beton';
if(!empty($
$xBeton))
{
$BetonAEnlever=$$xBeton;
}
else{
$BetonAEnlever = 0;}

$xVerre=$BatimentAConstruire.'Verre';
if(!empty($
$xVerre))
{
$VerreAEnlever=$$xVerre;
}
else{
$VerreAEnlever = 0;}

$xCuivre=$BatimentAConstruire.'Cuivre';
if(!empty($
$xCuivre))
{
$CuivreAEnlever=$$xCuivre;
}
else{
$CuivreAEnlever = 0;}

$xEnergie=$BatimentAConstruire.'Energie';
if(!empty($
$xEnergie))
{
$EnergieAEnlever=$$xEnergie;
}
else{
$EnergieAEnlever = 0;}

return array(
"MetalAEnlever"=>$MetalAEnlever,
"VerreAEnlever"=>$VerreAEnlever,
"BetonAEnlever"=>$BetonAEnlever,
"CuivreAEnlever"=>$CuivreAEnlever,
"EnergieAEnlever"=>$EnergieAEnlever);
}

Je l'ai testé, ça marche. Vous pouvez bien sûr l'adapter à d'autres situation. Ce code est probablement optimisable, et il existe même mieux, mais c'est une bonne base, je pense, sur laquelle partir.

PS : Dans le code de "batiments.php", vous l'utilisez comme ceci :
Code PHP :
<?php 
RessourcesAEnlever
($_GET['construction']);



RE: Petite solution pour alléger le code de certains. - My Hotel - 01-09-2009

Mouais, je suis pas convaincu... Plutôt que d'inventer des solutions assez "tordues" pour gérer ça, pourquoi ne pas stocker tous les coûts en BDD?
Après, on a plus qu'a lire les couts correspondants et à updater la BDD, c'est quand même mieux que des variables aux nom concaténés, et autres...

C'est comme ça que je fonctionne en tout cas Wink

P.S : au niveau de tes commentaires, évite les inutiles, genre : include'prix_batiments.php'; // On inclu le fichier où sont présentes les variables contenant les prix.
Ca clarifiera ton code qui est déjà pas fantastique à lire, pour moi en tout cas Smile


RE: Petite solution pour alléger le code de certains. - Origine - 01-09-2009

Oui, désolé pour les commentaires ^^

Cependant, inclure les prix en BDD est une solution ... mais faut voir à pas flooder le serveur et l'inonder de requêtes du type SELECT.

Comme je l'ai dit, c'est une solution comme une autre. Pour ma part, je n'utilise pas ce système, mais le tiens en partie. Cependant, c'est un peu plus long et compliqué à mettre en oeuvre.


RE: Petite solution pour alléger le code de certains. - My Hotel - 01-09-2009

Il faut pas avoir peur de surcharger un serveur avec quelques requêtes quand même. D'accord, SQL, c'est plus long, faut optimiser, toussa toussa, mais faut pas tomber dans la parano du SQL non plus, comme le font certain avec le moins de requêtes/pages. 45 requêtes/pages, c'est trop, mais 2 ou 3, c'est un minimum, selon la page.

SQL est tellement plus pratique, evolutif, etc... Franchement, pourquoi s'en priver? Après, c'est le débat habituel, faut-il faciliter la vie de l'admin au prix de quelques ms de plus à l'éxécution? Pour moi en tout cas, la réponse est oui. Evidemment, j'utilise un système de cache aussi, faut pas abuser quand même Wink


RE: Petite solution pour alléger le code de certains. - Origine - 01-09-2009

Avec un système de cache, ça devient tout de suite une solution meilleure, dans le sens où le risque de flood est diminué.

Maintenant, c'est vrai qu'au niveau de la facilitation du travail pour un admin, c'est un bien meilleur système.

Mais la mise en place d'un cache n'est pas toujours évidente =/


RE: Petite solution pour alléger le code de certains. - Roworll - 02-09-2009

Pour ma part, j'ai déjà utilisé un système très simple alliant BDD et fichier de ressource (pour les prix)
Il suffit d'une interface d'admin permettant de modifier la table des prix en BDD couplé avec une fonctionnalité d'export.
L'export prend alors les infos en BDD et reconstruit l'équivalent de batiments_prix.php
Rapide et efficace.

Le code que tu présentes laisse supposer qu'il y a autant de variables que de ressources x type de bâtiments

Code PHP :
<?php 
$CaserneMetal
$CaserneBeton
...
$GarageMetal
$GarageBeton
...

Ca me semble très verbeux et multiplie les variables.

Passer par un tableau et des constantes pour indexer les ressources n'aurait-il pas été plus payant ?
Le fichier batiments_prix.php ressemblerait alors à un truc du genre
Code PHP :
<?php 
define
("COUT_BETON",0);
define("COUT_VERRE",1);
define("COUT_CUIVRE",2);
define("COUT_ENERGIE",3);
define("COUT_METAL",4);
$Cout['caserne']=array(10,10,5,0,0);
$Cout['garage']=array(20,10,10,5,0);

La récupération des valeurs est alors simplifiée et unifiée.
Code PHP :
<?php 
$batiment
='caserne';
echo
'Cout en métal pour '.$batiment.' : '.$Cout[$batiment][COUT_METAL];

Ou encore, pour reprendre ton exemple de mise à jour de la BDD
Code PHP :
<?php 
$Query
="UPDATE ressources SET ";
$Query.="metal=metal-".$Cout[$_GET['construction']][COUT_METAL].", ";
$Query.="cuivre=cuivre-".$Cout[$_GET['construction']][COUT_CUIVRE].", ";
// même chose pour les autres ressources
$Query.="WHERE id='".$id."'";
mysql_query($Query) or die (mysql_error());



RE: Petite solution pour alléger le code de certains. - Argorate - 04-09-2009

J'espere que ce n'est pas vraiment serieux? Confused

Il n'y a ni besoin de fonction, ni de BDD pour ce genre de chose (a moins que le prix des btiments puissent varier avec des raisons in game)
Si ce n'est pas le cas, une fois le jeu équilibré, les couts en divers ressurces par batiment sont fixes, donc pas de BDD (perte de temps).
Quand a la fonction, j'ai pas saisie l'interet!?

En effet, il suffit de faire une page à inclure le cas échéant, comportant simplement un tableau...

exemple:
Code PHP :
<?php 
$info_cout_batiment
[1]['nom'] = 'Maison';
$info_cout_batiment[1]['nb_pa'_a_utiliser] = 2;
$info_cout_batiment[1]['cout_ressource_1'] = 20;
$info_cout_batiment[1]['cout_ressource_2'] = 50;

$info_cout_batiment[2]['nom'] = 'Tour de defence de la mort';
$info_cout_batiment[2]['nb_pa'_a_utiliser] = 3;
$info_cout_batiment[2]['cout_ressource_1'] = 15;
$info_cout_batiment[2]['cout_ressource_2'] = 100;
...
etc...

Ainsi on travail en RAM, donc rapidité garentit et accecibilité simplisime:

$info_cout_batiment[$id_du_batiment]['cout_ressource_'.$id_de_la_ressource]


RE: Petite solution pour alléger le code de certains - lemouix - 08-09-2009

Moi je dis que rien ne vaut la bonne progra objet :p avec des triggers en bdd pour tous les calculs de ressources, libération d'espaces, calcul de ressources, ...


RE: Petite solution pour alléger le code de certains - jo_link_noir - 08-09-2009

Je comprend pas bien comment vous faites pour stocké en bdd. Dans le cas ou j'ai plusieurs variable pour le prix c'est géré comment ? faut bien un fichier avec les calculs non ?

Personnellement j'ai fait une classe U1_Batiment qui étant Batiment (classe abstraite) avec dedans une méthode initPrice(ElementBatiment $element), qui calcul le prix et le rentre dans $element.
Et donc, à ce niveau je pourrait mettre un système de cache non ?


RE: Petite solution pour alléger le code de certains - Sephi-Chan - 08-09-2009

Et bien, tu as plusieurs moyens.

Dans la table qui stock tes bâtiments, pourquoi ne mettrais tu pas une colonne par ressource ?

Si cette solution ne te plaît pas, tu peux aussi mettre un champ de type texte dans la table et y stocker un tableau sérialisé en JSON, de la forme (et dans ta classe, tu le déserializes) :


{
gold: 46,
wood: 34
}

Après, je ne connais pas ton système, peut-être les bâtiments ont-il un niveau et que le coût de base se calcule seon ce niveau, etc.
M'enfin il y a toujours une solution plus propre que l'écriture en dur dans des variables.


Sephi-Chan