Codice:
Codice: Seleziona tutto
#include "structs.h"
#include "utils.h"
#include "spells.h"
#include <iostream>
#define PWP_NORMALIZATION 100
using namespace std;
long GetPQValue(obj_data obj, int apply);
long CalcPWP(obj_data obj);
long CalcPWP(char_data *ch);
int FindApplyIndex(short type);
long calcProgressiveCost(long cost, long bitvector, int bits[]);
long getApplyCost(short apply);
int FindWSIndex(long ws);
// tabella dei costi in pq degli apply
static struct ApplyPwpPrice {
short type; /* tipo apply */
long cost; /* costo in pq per ogni unita dell apply */
int isbitvector; /* 1 se e uno slot che non tiene un valore ma un vettore di bit es. ALIGN SLAYER by GOOD NEUTRAL EVIL */
int bitprice[32];
} PwpCostTable[]={
{ APPLY_DAMROLL , 400, 0, {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}},
{ APPLY_HIT , 40, 0, {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}},
{ APPLY_WEAPON_SPELL , 0, 2, {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}},
{ APPLY_ABSORB_DAMAGE , 400, 0, {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}},
/* spell affect: messo solo sanc */
{ APPLY_SPELL , 0, 1, {0,0,0,0,0,0,4000,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}},
/* align slay: un bitvector con costo progressivo 1000 per ogni bit acceso: trislay: 3000+(3000+1000)+(3000+2*1000) */
{ APPLY_ALIGN_SLAYER , 1000, 1, {3000,3000,3000,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}},
/* resistenze, da finire */
{ APPLY_IMMUNE , 0, 1, {1200,1200,1200,1200,4000,1800,3000,1200,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}},
/* immunita, da finire */
{ APPLY_M_IMMUNE , 0, 1, {5000,5000,5000,5000,9000,5000,7000,5000,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0}},
/* AGGIUNGERE ALTRI APPLY */
};
// tabella dei costi in pq delle weaponspell
static struct WeaponSpellPwpPrice {
long ws; /* tipo weaponspell */
long cost; /* costo in pq per la weaponspell */
} PwpWSCostTable[]={
{ SPELL_CAUSE_CRITICAL , 3200},
{ SPELL_FREEZE , 400}
};
// per testing (calcola il pwp di un pg triclasse con qualche prac e 2 x arma 45d1, 5 Dam, affect sanc, ws critical, triple slay, res varie)
int main(int argc, char *argv[]) {
obj_data *ob = (obj_data*)calloc(1,sizeof(obj_data));
ob->obj_flags.type_flag = ITEM_WEAPON;
ob->obj_flags.value[1] = 45;
ob->obj_flags.value[2] = 1;
ob->affected[0].location = APPLY_DAMROLL;
ob->affected[0].modifier = 5;
ob->affected[1].location = APPLY_SPELL;
ob->affected[1].modifier = 64; // sanc
ob->affected[2].location = APPLY_WEAPON_SPELL;
ob->affected[2].modifier = SPELL_CAUSE_CRITICAL;
ob->affected[3].location = APPLY_ALIGN_SLAYER;
ob->affected[3].modifier = 7;
ob->affected[4].location = APPLY_IMMUNE; // resistenza
ob->affected[4].modifier = 31; // fire cold elect energy blunt
char_data *ch = (char_data*)calloc(1,sizeof(char_data));
ch->equipment[0] = ob; // metto la spada come eq pezzo 1
ch->equipment[1] = ob; // metto la spada come eq pezzo 2
ch->points.cindy.hit = 90; // prac 90 HP
ch->points.cindy.damroll = 25; // prac 25 dam
ch->points.sig_cindy.damroll = 3; // train 3 dam
ch->player.level[0] = 50; // superior classe 0
ch->player.level[1] = 50; // superior classe 1
ch->player.level[3] = 50; // superior classe 2
int value = CalcPWP(ch);
free(ch);
free(ob);
cout << "Valore PWP TOTALE DELL PG: " << value << endl;
}
// calcola il pwp totale di un oggetto (obj_data)
long CalcPWP(obj_data obj) {
long total = 0;
int isweapon = GET_ITEM_TYPE( &obj ) == ITEM_WEAPON ? 1 : 0;
int i = 0;
for (i = 0; i < MAX_OBJ_AFFECT; i++)
{
long pq = GetPQValue(obj, i);
cout << "APPLY " << i+1 << " VALORE PQ: " << pq
<< " (Tipo:" << obj.affected[i].location
<< ",Valore:" << obj.affected[i].modifier << ")" << endl;
total += pq;
}
if (isweapon) {
int numdadi = obj.obj_flags.value[1];
int numfacce = obj.obj_flags.value[2];
double media = (int)((double)numdadi * ((double)(numfacce+1) / 2));
cout << "ARMA MEDIA DAM " << media << " (PQ " << media * PwpCostTable[FindApplyIndex(APPLY_DAMROLL)].cost << ") " << endl;
total += (long)(media * PwpCostTable[FindApplyIndex(APPLY_DAMROLL)].cost);
}
cout << "PWP TOTALE DELL OGGETTO " << total / PWP_NORMALIZATION << endl;
return total / PWP_NORMALIZATION;
}
// da il valore in pq di un apply (type = tipo apply, value = valore)
long GetPQValue(obj_data obj, int apply) {
long ret = 0;
short type = obj.affected[apply].location;
long value = obj.affected[apply].modifier;
int index = FindApplyIndex(type);
if (index == -1) {
return 0;
}
// casi speciali: weaponspell e varie
if (PwpCostTable[index].isbitvector > 1) {
cout << "SPC ";
if (PwpCostTable[index].isbitvector == 2) { // weaponspell
int wsindex = FindWSIndex(value);
if ( wsindex != -1) {
ret = PwpWSCostTable[wsindex].cost;
}
}
}
// bitvector : resistenze, affect e simile
else if (PwpCostTable[index].isbitvector!=0) {
cout << "BTV ";
ret = (long)calcProgressiveCost(PwpCostTable[index].cost, value, PwpCostTable[index].bitprice);
// apply normali con valore: dam hit etc
} else {
cout << "VAL ";
ret = (long)PwpCostTable[index].cost * value;
}
return ret;
}
// eleva un numero ad una potenza (es. 2^3 - serve per calcolare i bitvector)
long powNum(long num, long power) {
long count = 1;
int i;
for (i=1; i <=power; i++)
count = count*num;
return count;
}
// somma i costi di ogni bit attivo nel bitvector
// (es. trislay ha bitvector: 11100000000000000000000000000000 - equivale a 7 in decimale)
// basecost si aggiunge n volte per ogni bit attivo, dove n e la somma progressiva di bit attivi)
// trislay si definisce con basecost 1000 e si mette ogni slay a 3000
// quindi per trislay fa: 3000 + (3000+1000) + (3000+2000)
long calcProgressiveCost(long basecost, long bitvector, int bits[]) {
int i,bitstotal = 0;
long mask, ret = 0;
for (i=0; i<32;i++) {
mask = powNum(2,i);
if (bitvector & mask) {
bitstotal++;
ret += (long)((bitstotal-1)*basecost + bits[i]);
}
}
return ret;
}
// cerca la posizione dell apply nella tabella di costo in pq degli apply)
int FindApplyIndex(short type) {
int index = -1;
int i = 0;
int max = (int)sizeof(PwpCostTable)/sizeof(ApplyPwpPrice);
for (i = 0; i < max; i++) {
if (type == PwpCostTable[i].type) {
index = i;
break;
}
}
return index;
}
// cerca la posizione della WS nella tabella di costo in pq delle weaponspell)
int FindWSIndex(long ws) {
int index = -1;
int i = 0;
int max = (int)sizeof(PwpWSCostTable)/sizeof(WeaponSpellPwpPrice);
for (i = 0; i < max; i++) {
if (ws == PwpWSCostTable[i].ws) {
index = i;
break;
}
}
return index;
}
// il costo per unita di un apply
long getApplyCost(short apply) {
int index = FindApplyIndex(apply);
if (index == -1) return 0;
return PwpCostTable[FindApplyIndex(apply)].cost;
}
// calcola il pwp totale di un pg
long CalcPWP(char_data *ch) {
int i;
obj_data *obj;
long pwp = 0;
long pwp_eq = 0;
long pwp_prac = 0;
long pwp_train = 0;
long pwp_lev = 0;
for (i=0;i<MAX_WEAR;i++) {
if((obj = ch->equipment[i])){
pwp_eq += CalcPWP(*(obj));
}
}
// prac cindy
pwp_prac += ch->points.cindy.hit * getApplyCost(APPLY_HIT) / PWP_NORMALIZATION;
pwp_prac += ch->points.cindy.hit_gain * getApplyCost(APPLY_HIT_REGEN) / PWP_NORMALIZATION;
pwp_prac += ch->points.cindy.mana * getApplyCost(APPLY_MANA) / PWP_NORMALIZATION;
pwp_prac += ch->points.cindy.mana_gain * getApplyCost(APPLY_MANA_REGEN) / PWP_NORMALIZATION;
pwp_prac += ch->points.cindy.mov * getApplyCost(APPLY_MOVE) / PWP_NORMALIZATION;
pwp_prac += ch->points.cindy.mov_gain * getApplyCost(APPLY_MOVE_REGEN) / PWP_NORMALIZATION;
pwp_prac += ch->points.cindy.memorize * getApplyCost(APPLY_DAMROLL) / PWP_NORMALIZATION; // non ce apply per memo, uso il damroll
pwp_prac += ch->points.cindy.spellpower * getApplyCost(APPLY_SPELL_POWER) / PWP_NORMALIZATION;
pwp_prac += ch->points.cindy.damroll * getApplyCost(APPLY_DAMROLL) / PWP_NORMALIZATION;
pwp_prac += ch->points.cindy.hitroll * getApplyCost(APPLY_HITROLL) / PWP_NORMALIZATION;
cout << "PWP PRAC: " << pwp_prac << endl;
// train cindy
pwp_train += ch->points.sig_cindy.hit * 2 * getApplyCost(APPLY_HIT) / PWP_NORMALIZATION;
pwp_train += ch->points.sig_cindy.hit_gain * 2 * getApplyCost(APPLY_HIT_REGEN) / PWP_NORMALIZATION;
pwp_train += ch->points.sig_cindy.mana * 2 * getApplyCost(APPLY_MANA) / PWP_NORMALIZATION;
pwp_train += ch->points.sig_cindy.mana_gain * 2 * getApplyCost(APPLY_MANA_REGEN) / PWP_NORMALIZATION;
pwp_train += ch->points.sig_cindy.mov * 2 * getApplyCost(APPLY_MOVE) / PWP_NORMALIZATION;
pwp_train += ch->points.sig_cindy.mov_gain * 2 * getApplyCost(APPLY_MOVE_REGEN) / PWP_NORMALIZATION;
pwp_train += ch->points.sig_cindy.memorize * 2 * getApplyCost(APPLY_DAMROLL) / PWP_NORMALIZATION; // non ce apply per memo, uso il damroll
pwp_train += ch->points.sig_cindy.spellpower * 2 * getApplyCost(APPLY_SPELL_POWER) / PWP_NORMALIZATION;
pwp_train += ch->points.sig_cindy.damroll * 2 * getApplyCost(APPLY_DAMROLL) / PWP_NORMALIZATION;
pwp_train += ch->points.sig_cindy.hitroll * 2 * getApplyCost(APPLY_HITROLL) / PWP_NORMALIZATION;
cout << "PWP TRAIN: " << pwp_train << endl;
// conta il num di classi
int classe, numclassi = 0;
for (classe = 0; classe < MAX_CLASS; classe++) {
if (ch->player.level[classe]>0) {
numclassi += 1;
}
}
pwp_lev = (pwp_eq + pwp_prac + pwp_train) * numclassi * 5/100; // pwp accumulato + 5% per classe
cout << "PWP LEVEL: " << pwp_lev << endl;
// sommiamo tutto
pwp = pwp_eq + pwp_prac + pwp_train + pwp_lev;
return pwp;
}
Il test di un pg triclasse:
prac 90hp
prac 25 dam
train 3 damroll
pezzo di eq1: ARMA 45d1 5DAM TRIPLESLAY RES FIRE COLD ELECT BLUNT, affect SANC, WS critical
pezzo di eq2: ancora una volta la stessa spada
Codice:
C:\Test\Test>pwp.exe
VAL APPLY 1 VALORE PQ: 2000 (Tipo:19,Valore:5)
BTV APPLY 2 VALORE PQ: 4000 (Tipo:29,Valore:64)
SPC APPLY 3 VALORE PQ: 3200 (Tipo:30,Valore:56)
BTV APPLY 4 VALORE PQ: 12000 (Tipo:49,Valore:7)
BTV APPLY 5 VALORE PQ: 8800 (Tipo:26,Valore:31)
ARMA MEDIA DAM 45 (PQ 18000)
PWP TOTALE DELL OGGETTO 480
VAL APPLY 1 VALORE PQ: 2000 (Tipo:19,Valore:5)
BTV APPLY 2 VALORE PQ: 4000 (Tipo:29,Valore:64)
SPC APPLY 3 VALORE PQ: 3200 (Tipo:30,Valore:56)
BTV APPLY 4 VALORE PQ: 12000 (Tipo:49,Valore:7)
BTV APPLY 5 VALORE PQ: 8800 (Tipo:26,Valore:31)
ARMA MEDIA DAM 45 (PQ 18000)
PWP TOTALE DELL OGGETTO 480
PWP PRAC: 136
PWP TRAIN: 24
PWP LEVEL: 168
Valore PWP TOTALE DELL PG: 1288