La Bibliothèque de Neverwinter Nights
Aide et informations diverses sur Neverwinter Nights ainsi que D&D3.
La date/heure actuelle est 27/11/2024 14:29:11


  Page 1 sur 1 ¤

Voir le sujet précédent ¤ Voir le sujet suivant 
Auteur Message
Attention ! Vous êtes en train de lire un message hors de son contexte. Veuillez lire le sujet Script SOC demande d'aide sur une fonction en entier avant de répondre à ce message.
Léa
Novice
Inscrit le: 25 Oct 2003
Messages: 15
Répondre en citant
Posté le : 28/01/2005 22:24:17 Sujet du message : Script SOC demande d'aide sur une fonction

Bonsoir à tous,

Je poste ici dans l'espoir de trouver de l'aide sur un script récalcitrant. Le problême que nous rencontrons est que lors de la fabrication d'un item, seule la première ressource nécessaire est consommée. J'ai posté à la fin la partie du script qui semble poser problême avec quelques explications.
Gentils scripteurs, si vous pouviez jeter un oeil ... (*vous sera rendu au centuple*) (dsl pour le pavé)

NWScript :
#include "nw_i0_tool"
#include "aps_include"

//Fonction utilisee pour les ajustements de competence en fonction de la race
//dans la table SOCC (Les ajustements ne doivent aller que de -100 a +100)
int AjustementCompetence(object oCible, string sCompetence)
{
    string sCol;
    if (GetRacialType(oCible)==RACIAL_TYPE_DWARF)    sCol = "nain";
    if (GetRacialType(oCible)==RACIAL_TYPE_ELF)      sCol = "elfe";
    if (GetRacialType(oCible)==RACIAL_TYPE_HALFELF)  sCol = "demielfe";
    if (GetRacialType(oCible)==RACIAL_TYPE_GNOME)    sCol = "gnome";
    if (GetRacialType(oCible)==RACIAL_TYPE_HUMAN)    sCol = "humain";
    if (GetRacialType(oCible)==RACIAL_TYPE_HALFORC)  sCol = "demiorque";
    if (GetRacialType(oCible)==RACIAL_TYPE_HALFLING) sCol = "hafelin";
    string sSQL = "SELECT "+sCol+" FROM soc WHERE competence=" + sCompetence ;
    SQLExecDirect(sSQL);
    SQLFetch();
    return StringToInt(SQLGetData(1));
}

//Fais un listing des objets necessaires a la fabrication
//indiques dans une liste (cf mod_loading)
// - oFabricant = Joueur qui desire fabriquer
// - sTag : Tag de l'objet dont on doit faire le listing
int Lister(object oFabricant,string sTag);
int Lister(object oFabricant,string sTag)
{
    SetLocalString(oFabricant,"SOC_Objet_Tag",sTag);

    string sSQL = "SELECT actif,necessaire,chance,prix,nom  FROM soc WHERE objet='" + sTag +"'";
    SQLExecDirect(sSQL);
    SQLFetch();

    string sActif = SQLGetData(1);
    string sNecessaire = SQLGetData(2);
    string sChance = SQLGetData(3);
    string sPrix = SQLGetData(4);
    string sDescription = SQLDecodeSpecialChars(SQLGetData(5));

    //Rappel de l'actif sur le fabricant et du tag
    SetLocalString(oFabricant,"SOC_Objet_Actif",sActif);
    SetLocalString(oFabricant,"SOC_Objet_Tag",sTag);
    SetLocalString(oFabricant,"SOC_Objet_Chance",sChance);

    //Initialisation du Token de ressources necessaires
    SetCustomToken(19102,"");

    //Token 19000 : Prix de l'objet
    SetCustomToken(19103,sPrix);

    //Token 19111 : Actif ou inactif ?
    if (sActif == "1")
        SetCustomToken(19111,"ACTIF");
    else
        SetCustomToken(19111,"INACTIF");

    //Token 19100 : Description de l'objet
    SetCustomToken(19100,sDescription);

    //Token 19101 : Chance de reussite =  + ajustement
    string sCmpt = GetLocalString(OBJECT_SELF,"Numero_Competence");
    int iLevel = FloatToInt(GetCampaignFloat(GetPCPlayerName(oFabricant),"lvl_cmpt_"+sCmpt,oFabricant));
    int iValeur = AjustementCompetence(oFabricant,sCmpt)+StringToInt(sChance)+iLevel;
    if (iValeur<0) iValeur=0;
    SetCustomToken(19101,IntToString(iValeur));

    //Renvoie FALSE et donc s'arrete si l'objet n'est pas etalonne
    if (sNecessaire=="VIDE" || sNecessaire=="")
        return FALSE;

    string sProduit = sNecessaire+"+";
    int iLongueur = GetStringLength(sProduit);
    SetLocalInt(oFabricant,"SOC_FONCTION_RESULTAT",TRUE);
    int j; int iNbre; int iPositionNbre; string sNom;
    int iPositionNom; object oProduit; string sChar;
    string sChaine =""; int item;  int iNbreFabricant ;

    //Analyse des ressources necessaires et stockage
    for (j=0;j<=iLongueur-1;j++)
    {
        sChar = GetSubString(sProduit,j,1);
        //Quantite
        if (sChar=="*")
        {
            iPositionNbre = j-1;
            iNbre = StringToInt(GetSubString(sProduit,j-1,1));
        }
        //Tag
        if (sChar=="+")
        {
            iPositionNom = j-1;
            sNom = GetSubString(sProduit,iPositionNbre+2,iPositionNom-iPositionNbre-1);
            item++;
            SetLocalString(oFabricant,"SOC_FctFab_Item_"+IntToString(item),sNom);
            SetLocalInt(oFabricant,"SOC_FctFab_Nbre_"+sNom,iNbre);
        }
    }

    //Lit et stocke la quantite du fabricant
    oProduit = GetFirstItemInInventory(oFabricant);
    while (GetIsObjectValid(oProduit))
    {
          //Lecture des items enregistrees
          for(j=1;j<=item;j++)
          {
            //Si l'item lues dans l'inventaire est la meme que l'item enregistree
            sNom = GetLocalString(oFabricant,"SOC_FctFab_Item_"+IntToString(j));
            if (GetTag(oProduit)==sNom)
            {
                iNbre = GetLocalInt(oFabricant,"SOC_FctFab_NbreFabricant_"+sNom);
                SetLocalInt(oFabricant,"SOC_FctFab_NbreFabricant_"+sNom, iNbre+GetNumStackedItems(oProduit));
            }
          }
          oProduit = GetNextItemInInventory(oFabricant);
    }

    //Affichage et retour de la fonction
    for(j=1;j<=item;j++)
    {
        sNom = GetLocalString(oFabricant,"SOC_FctFab_Item_"+IntToString(j));
        iNbre = GetLocalInt(oFabricant,"SOC_FctFab_Nbre_"+sNom);
        iNbreFabricant = GetLocalInt(oFabricant,"SOC_FctFab_NbreFabricant_"+sNom);
        sChaine += " - "+GetName(GetObjectByTag(sNom))+" "+IntToString(iNbreFabricant) + "/"+ IntToString(iNbre)+"\n";

        //Resultat special de la double fonction (cf commentaire plus bas)
        if (iNbreFabricant<iNbre)
            SetLocalInt(oFabricant,"SOC_FONCTION_RESULTAT",FALSE);
        //Destruction des variables
        DeleteLocalString(oFabricant,"SOC_FctFab_Item_"+IntToString(j));
        DeleteLocalInt(oFabricant,"SOC_FctFab_Nbre_"+sNom);
        DeleteLocalInt(oFabricant,"SOC_FctFab_NbreFabricant_"+sNom);
    }
    SetCustomToken(19102,sChaine+"\n");

    //Ce retour est celui qui affirme que la fonction Lister a bel et bien detecte
    //que l'objet avait ete initialiser. Elle renvoie TRUE dans une variable speciale
    //si le fabricant possede tout ce qu'il faut. (C'est speciale je sais, car elle fait
    //deux fonction en une :economie de script et de temps)
    return TRUE;
}

//Fonction de construction d'un objet
//(Cette fonction n'a aucune contrainte ni de quantite ni de type d'item en ce qui concerne
//le necessaire et le fameux STACKED - item empilable)
//Par contre elle requiert que le fabricant possede bien les ressources necessaires
//et donc l'appelle de Lister().
// - oFabricant = Joueur qui desire fabriquer
// - sTag = tag de l'objet a fabriquer
void Fabriquer(object oFabricant,string sTag);
void Fabriquer(object oFabricant,string sTag)
{

    //La facon dont ce script est codee parait longue mais permet d'eviter des tests
    //d'inventaire en boucle qui sont tres lourd pour le serveur
    //Les variables sont ensuite detruites : donc no soucy ! Very Happy
    string sSQL = "SELECT necessaire FROM soc WHERE objet='" + sTag +"'";
    SQLExecDirect(sSQL);
    SQLFetch();
    string sProduit = SQLGetData(1)+"+";
    int iLongueur = GetStringLength(sProduit);
    int j; int iNbre;  int iPositionNbre;  string sNom;
    int iPositionNom; object oProduit;  string sChar ;
    int item; int k; int i;

    //Analyse des ressources necessaires et stockage
    for (j=0;j<=iLongueur-1;j++)
    {
        sChar = GetSubString(sProduit,j,1);
        //Quantite
        if (sChar=="*")
        {
            iPositionNbre = j-1;
            iNbre = StringToInt(GetSubString(sProduit,j-1,1));
        }
        if (sChar=="+")
        {
            iPositionNom = j-1;
            sNom = GetSubString(sProduit,iPositionNbre+2,iPositionNom-iPositionNbre-1);
            item++;
            SetLocalString(oFabricant,"SOC_FctFab_Item_"+IntToString(item),sNom);
            SetLocalInt(oFabricant,"SOC_FctFab_Nbre_"+sNom,iNbre);
        }
    }

    //Lit et stocke la quantite du fabricant
    oProduit = GetFirstItemInInventory(oFabricant);
    while (GetIsObjectValid(oProduit))
    {
          //Lecture des items enregistrees
          for(j=1;j<=item;j++)
          {
            //Si l'item lues dans l'inventaire est la meme que l'item enregistree
            sNom = GetLocalString(oFabricant,"SOC_FctFab_Item_"+IntToString(j));
            if (GetTag(oProduit)==sNom)
            {
                iNbre = GetLocalInt(oFabricant,"SOC_FctFab_NbreFabricant_"+sNom);
                SetLocalInt(oFabricant,"SOC_FctFab_NbreFabricant_"+sNom, iNbre+GetNumStackedItems(oProduit));
                k++;
                SetLocalObject(oFabricant,"SOC_FctFab_Object_"+IntToString(k), oProduit);
            }
          }
          oProduit = GetNextItemInInventory(oFabricant);
    }

    //Analyse des ressources enregistree chez le fabricant et reconstruction
    //des ressources si elles ne devait pas etre supprimees
    for(j=1;j<=item;j++)//parcourt les objets enregistres chez le necessaire
    {
        sNom = GetLocalString(oFabricant,"SOC_FctFab_Item_"+IntToString(j));
        iNbre = GetLocalInt(oFabricant,"SOC_FctFab_Nbre_"+sNom);

        for (i=1;i<=k;i++)//parcourt les objets enregistres chez le fabricant
        {
            oProduit = GetLocalObject(oFabricant,"SOC_FctFab_Object_"+IntToString(i));
            if (GetTag(oProduit)==sNom)
            {
                if (iNbre>=GetNumStackedItems(oProduit))
                {
                    iNbre = iNbre - GetNumStackedItems(oProduit);
                    DestroyObject(oProduit);
                }
                else
                {
                    SetItemStackSize(oProduit, GetNumStackedItems(oProduit)-iNbre);
                    iNbre=0;
                }
            }
            //Destruction des variables
            DeleteLocalObject(oFabricant,"SOC_FctFab_Object_"+IntToString(i));
        }

        //Destruction des variables
        DeleteLocalString(oFabricant,"SOC_FctFab_Item_"+IntToString(j));
        DeleteLocalInt(oFabricant,"SOC_FctFab_Nbre_"+sNom);
        DeleteLocalInt(oFabricant,"SOC_FctFab_NbreFabricant_"+sNom);
    }


    //Tirage pour la fabrication
    //==========================
    //numero de la competence
    string sCmpt = GetLocalString(OBJECT_SELF,"Numero_Competence");
    //niveau du joueur
    int iLevel = FloatToInt(GetCampaignFloat(GetPCPlayerName(oFabricant),"lvl_cmpt_"+sCmpt,oFabricant));
    //Chance de reussite ajustee
    int iValeur = AjustementCompetence(oFabricant,sCmpt)+StringToInt(GetLocalString(oFabricant,"SOC_Objet_Chance"))+iLevel;
    //Tirage d'echec critique
    int iEchecCritique = Random(1+(iValeur-iValeur%10)/10);

    //Augmentation de l'experience de joueur dans sa competence en fonction de son niveau actuel
    //==========================================================================================
    float fUpgrade = 0.02; //0.02 c'est une securite en cas de defaillance de la suite
    if (iLevel>=0 &&iLevel<=19)    fUpgrade=0.200; //niveau entre 0 et 4
    else if (iLevel>=20 &&iLevel<=44)    fUpgrade=0.180; //niveau entre 5 et 9
    else if (iLevel>=45 &&iLevel<=69)  fUpgrade=0.160;
    else if (iLevel>=70 &&iLevel<=99)  fUpgrade=0.140;
    else if (iLevel>=100 &&iLevel<=149)  fUpgrade=0.100;
    else if (iLevel>=150 &&iLevel<=199)  fUpgrade=0.090;
    else if (iLevel>=200 &&iLevel<=249)  fUpgrade=0.075;
    else if (iLevel>=250 &&iLevel<=299)  fUpgrade=0.050;
    else if (iLevel>=300 &&iLevel<=349)  fUpgrade=0.045;
    else if (iLevel>=350 &&iLevel<=399)  fUpgrade=0.040;
    else if (iLevel>=400 &&iLevel<=449)  fUpgrade=0.033;
    else if (iLevel>=450)                fUpgrade=0.015;

    SetCampaignFloat(GetPCPlayerName(oFabricant),"lvl_cmpt_"+sCmpt,GetCampaignFloat(GetPCPlayerName(oFabricant),"lvl_cmpt_"+sCmpt,oFabricant)+fUpgrade,oFabricant);

    //Test de reussite selon les donnees precedentes
    //==============================================
    if((Random(100)<iValeur && iEchecCritique != 0 && iLevel<=500) || GetIsDM(oFabricant))
    {
        //CreateItemOnObject(sPro,oFabricant,1);
        object oItem;
        SetIdentified(oItem = CreateItemOnObject(GetResRef(GetObjectByTag(sTag)),oFabricant),TRUE);
        FloatingTextStringOnCreature("Fabrication de l'objet réussie ! Compétence augmentée.",oFabricant,FALSE);
        //Donne 5 * [1+log(prix de l'objet)] XP  --> c.a.d 5 fois le nbre de colonnes du prix
        //de l'objet Very Happy --> exemple un objet a 136 po donnera 15 XP, un objet a 51214 po donne 25 XP
        GiveXPToCreature(oFabricant,5*(1+FloatToInt(log(IntToFloat(GetGoldPieceValue(oItem))))));//recompense en xp a hauteur de 1% de la valeur de l'objet
        //PlayVoiceChat(VOICE_CHAT_LAUGH,oFabricant);
        AssignCommand(oFabricant,ActionPlayAnimation(ANIMATION_FIREFORGET_VICTORY1));
    }
    else if (iLevel<500)
    {
        FloatingTextStringOnCreature("Fabrication de l'objet échouée mais votre compétence augmente !",oFabricant,FALSE);
        //PlayVoiceChat(VOICE_CHAT_CANTDO,oFabricant);
        AssignCommand(oFabricant,ActionPlayAnimation(ANIMATION_LOOPING_SPASM,1.0,2.0));
    }
    else
        FloatingTextStringOnCreature("Vous avez atteint le plus haut niveau dans cette compétence !",oFabricant,FALSE);



}

//REMETTRE A JOUR CETTE FONCTION CI DESSOUS QUI SERT A L'ETALONNAGE EN TANT QUE MD
//DANS LA PARTIE

/*//Modifie la quantite de 1
void Modifier(string sPro, string sRessourceEnPlus)
{
    string sProduit = GetSOCMateriel(sPro)+"+";
    int iLongueur = GetStringLength(sProduit);
    int j; int iNbre; int iPositionNbre; string sNom;
    int iPositionNom; object oProduit; string sChar;
    string sChaine;
    SetLocalInt(GetModule(),"SOC_Nouvelle_Ressource",TRUE);
    for (j=0;j<=iLongueur-1;j++)
    {
        sChar = GetSubString(sProduit,j,1);
        if (sChar=="*")
        {
            iPositionNbre = j-1;
            //Quantite du produit en cours
            iNbre = StringToInt(GetSubString(sProduit,iPositionNbre,1));
        }
        if (sChar=="+")
        {
            iPositionNom = j-1;
            //Tag du produit en cours
            sNom = GetSubString(sProduit,iPositionNbre+2,iPositionNom-iPositionNbre-1);

            if (sNom == sRessourceEnPlus)
            {
                if (iNbre!=9)
                    sChaine += "+"+IntToString(iNbre+1)+"*"+sNom;
                SetLocalInt(GetModule(),"SOC_Nouvelle_Ressource",FALSE);
            }
            else
                sChaine +="+"+IntToString(iNbre)+"*"+sNom;
        }
    }

        if (GetLocalInt(GetModule(),"SOC_Nouvelle_Ressource"))
            sChaine += "+1*"+sRessourceEnPlus;
        DeleteLocalInt(GetModule(),"SOC_Nouvelle_Ressource");
        sChaine =  GetSubString(sChaine,1,GetStringLength(sChaine)-1);
        //Un bug !
        if (GetSubString(sChaine,0,5)=="0*DE+")
            sChaine =  GetSubString(sChaine,5,GetStringLength(sChaine)-1);
        SetSOCMateriel(sChaine,sPro);
}*/

//void main(){}
Le code a colorer syntaxiquement est trop long (plus de 10240 caractères) et risque de ne pas s'afficher du tout. Vous pouvez le voir en version colorée ici.


----------------------------------------------
le premier script applique les bonus de race a la creation d objet

le deuxieme sert a afficher dans le dialogue les ingredients de l inventaire par rapport a ceux necessaire pour la fabrication de l objet.
Donc c est pas celui la non plus

la troisieme fonction reverifie (?) les ingredients possede par le pj .
Si c est en adequation avec les ingredients necessaire, la fabrication est lancee. les ingredients sont donc detruits. Ensuite vient les tests de reussite de fabrication.

Donc, en cas d ingredient multiple, ceux ci deivent etre detruit. Or, seul le premier l'est.je crois que c est cette partie du script qui foire :
Code :

for (i=1;i<=k;i++)//parcourt les objets enregistres chez le fabricant
        {
            oProduit = GetLocalObject(oFabricant,"SOC_FctFab_Object_"+IntToString(i));
            if (GetTag(oProduit)==sNom)
            {
                if (iNbre>=GetNumStackedItems(oProduit))
                {
                    iNbre = iNbre - GetNumStackedItems(oProduit);
                    DestroyObject(oProduit);
                }
                else
                {
                    SetItemStackSize(oProduit, GetNumStackedItems(oProduit)-iNbre);
                    iNbre=0;
                }
            }
            //Destruction des variables
            DeleteLocalObject(oFabricant,"SOC_FctFab_Object_"+IntToString(i));
        }

        //Destruction des variables
        DeleteLocalString(oFabricant,"SOC_FctFab_Item_"+IntToString(j));
        DeleteLocalInt(oFabricant,"SOC_FctFab_Nbre_"+sNom);
        DeleteLocalInt(oFabricant,"SOC_FctFab_NbreFabricant_"+sNom);
     }


Le gars qui a modifie les scripts pour faire la version 2.2 m'a dit que le probleme etaient dans des destructions de variables trop hatives....
Ce qui me semble sur, c est qu a priori, de tout les scripts soc, cette fonction est la seule avec la fonction DestroyObjet......

Merci au(x) noble(s) scripteur(s) qui saura(ont) nous apporter un peu de lumière.
 
Revenir en haut Voir le profil de l'utilisateur Envoyer un message privé MSN Messenger
 
Montrer les messages depuis :
Page 1 sur 1 ¤


Vous ne pouvez pas poster de nouveaux sujets dans ce forum
Vous ne pouvez pas répondre aux sujets dans ce forum
Vous ne pouvez pas éditer vos messages dans ce forum
Vous ne pouvez pas supprimer vos messages dans ce forum
Vous ne pouvez pas voter dans les sondages de ce forum


Sauter vers:
FAQ | Rechercher | Liste des Membres | Groupes d'utilisateurs | S'enregistrer | Profil | Se connecter pour vérifier ses messages privés | Connexion
Powered by phpBB 2.* [m] © 2001, 2002 phpBB Group
Theme rewritten in beautiful XHTML code by Baldurien.
Thème "La Bibliothèque de Neverwinter" crée par Kruger
Traduction par : phpBB-fr.com
Page generated in 41.235ms