From: <ave...@us...> - 2007-08-27 16:12:22
|
Revision: 4788 http://gemrb.svn.sourceforge.net/gemrb/?rev=4788&view=rev Author: avenger_teambg Date: 2007-08-26 14:33:40 -0700 (Sun, 26 Aug 2007) Log Message: ----------- implemented call lightning opcode (more or less) Modified Paths: -------------- gemrb/trunk/gemrb/includes/strrefs.h gemrb/trunk/gemrb/override/bg1/strings.2da gemrb/trunk/gemrb/override/bg2/strings.2da gemrb/trunk/gemrb/override/how/strings.2da gemrb/trunk/gemrb/override/iwd/strings.2da gemrb/trunk/gemrb/override/iwd2/strings.2da gemrb/trunk/gemrb/override/pst/strings.2da gemrb/trunk/gemrb/override/tob/strings.2da gemrb/trunk/gemrb/plugins/Core/GSUtils.h gemrb/trunk/gemrb/plugins/Core/GameScript.cpp gemrb/trunk/gemrb/plugins/FXOpcodes/FXOpc.cpp gemrb/trunk/gemrb/plugins/IWDOpcodes/IWDOpc.cpp Modified: gemrb/trunk/gemrb/includes/strrefs.h =================================================================== --- gemrb/trunk/gemrb/includes/strrefs.h 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/includes/strrefs.h 2007-08-26 21:33:40 UTC (rev 4788) @@ -118,7 +118,9 @@ #define STR_CONT_CANTPICK 84 #define STR_LOCKPICK_DONE 85 #define STR_LOCKPICK_FAILED 86 +#define STR_STATIC_DISS 87 +#define STR_LIGHTNING_DISS 88 -#define STRREF_COUNT 87 +#define STRREF_COUNT 89 #endif //! IE_STRINGS_H Modified: gemrb/trunk/gemrb/override/bg1/strings.2da =================================================================== --- gemrb/trunk/gemrb/override/bg1/strings.2da 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/override/bg1/strings.2da 2007-08-26 21:33:40 UTC (rev 4788) @@ -87,3 +87,5 @@ DOOR_CANTPICK 23169 CONT_CANTPICK 23169 LOCKPICK_DONE 16517 +STATIC_DISSIPATE -1 +LIGHTNING_DISSIPATE -1 Modified: gemrb/trunk/gemrb/override/bg2/strings.2da =================================================================== --- gemrb/trunk/gemrb/override/bg2/strings.2da 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/override/bg2/strings.2da 2007-08-26 21:33:40 UTC (rev 4788) @@ -87,3 +87,5 @@ DOOR_CANTPICK 23169 CONT_CANTPICK 23169 LOCKPICK_DONE 16517 +STATIC_DISSIPATE -1 +LIGHTNING_DISSIPATE -1 Modified: gemrb/trunk/gemrb/override/how/strings.2da =================================================================== --- gemrb/trunk/gemrb/override/how/strings.2da 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/override/how/strings.2da 2007-08-26 21:33:40 UTC (rev 4788) @@ -87,3 +87,5 @@ DOOR_CANTPICK 23169 CONT_CANTPICK 23169 LOCKPICK_DONE 16517 +STATIC_DISSIPATE 26518 +LIGHTNING_DISSIPATE -1 Modified: gemrb/trunk/gemrb/override/iwd/strings.2da =================================================================== --- gemrb/trunk/gemrb/override/iwd/strings.2da 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/override/iwd/strings.2da 2007-08-26 21:33:40 UTC (rev 4788) @@ -87,3 +87,5 @@ DOOR_CANTPICK 23169 CONT_CANTPICK 23169 LOCKPICK_DONE 16517 +STATIC_DISSIPATE -1 +LIGHTNING_DISSIPATE -1 Modified: gemrb/trunk/gemrb/override/iwd2/strings.2da =================================================================== --- gemrb/trunk/gemrb/override/iwd2/strings.2da 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/override/iwd2/strings.2da 2007-08-26 21:33:40 UTC (rev 4788) @@ -88,3 +88,5 @@ CONT_CANTPICK 23169 LOCKPICK_DONE 16517 LOCKPICK_FAILED 16518 +STATIC_DISSIPATE 26518 +LIGHTNING_DISSIPATE 41008 Modified: gemrb/trunk/gemrb/override/pst/strings.2da =================================================================== --- gemrb/trunk/gemrb/override/pst/strings.2da 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/override/pst/strings.2da 2007-08-26 21:33:40 UTC (rev 4788) @@ -88,3 +88,5 @@ CONT_CANTPICK 23169 LOCKPICK_DONE 19281 LOCKPICK_FAILED 19282 +STATIC_DISSIPATE -1 +LIGHTNING_DISSIPATE -1 Modified: gemrb/trunk/gemrb/override/tob/strings.2da =================================================================== --- gemrb/trunk/gemrb/override/tob/strings.2da 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/override/tob/strings.2da 2007-08-26 21:33:40 UTC (rev 4788) @@ -87,3 +87,5 @@ DOOR_CANTPICK 23169 CONT_CANTPICK 23169 LOCKPICK_DONE 16517 +STATIC_DISSIPATE -1 +LIGHTNING_DISSIPATE -1 Modified: gemrb/trunk/gemrb/plugins/Core/GSUtils.h =================================================================== --- gemrb/trunk/gemrb/plugins/Core/GSUtils.h 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/plugins/Core/GSUtils.h 2007-08-26 21:33:40 UTC (rev 4788) @@ -49,7 +49,6 @@ void CreateVisualEffectCore(Actor *target, const char *effect, int iterations); void CreateVisualEffectCore(Scriptable *Sender, Point &position, const char *effect, int iterations); void GetPositionFromScriptable(Scriptable* scr, Point &position, bool trap); -int CanSee(Scriptable* Sender, Scriptable* target, bool range, int nodead); void BeginDialog(Scriptable* Sender, Action* parameters, int flags); void ChangeAnimationCore(Actor *src, const char *resref, bool effect); void PolymorphCopyCore(Actor *src, Actor *tar, bool base); @@ -102,6 +101,7 @@ int GetObjectLevelCount(Scriptable* Sender, Object* oC); void SetVariable(Scriptable* Sender, const char* VarName, ieDword value); //these are used from other plugins +GEM_EXPORT int CanSee(Scriptable* Sender, Scriptable* target, bool range, int nodead); GEM_EXPORT int SeeCore(Scriptable* Sender, Trigger* parameters, int justlos); GEM_EXPORT int DiffCore(ieDword a, ieDword b, int diffmode); GEM_EXPORT void DisplayStringCore(Scriptable* Sender, int Strref, int flags); Modified: gemrb/trunk/gemrb/plugins/Core/GameScript.cpp =================================================================== --- gemrb/trunk/gemrb/plugins/Core/GameScript.cpp 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/plugins/Core/GameScript.cpp 2007-08-26 21:33:40 UTC (rev 4788) @@ -603,7 +603,7 @@ {"incrementkillstat", GameScript::IncrementKillStat, 0}, {"incrementproficiency", GameScript::IncrementProficiency, 0}, {"interact", GameScript::Interact, 0}, - {"joinparty", GameScript::JoinParty, 0}, + {"joinparty", GameScript::JoinParty, 0}, //this action appears to be blocking in bg2 {"journalentrydone", GameScript::SetQuestDone, 0}, {"jumptoobject", GameScript::JumpToObject, 0}, {"jumptopoint", GameScript::JumpToPoint, 0}, Modified: gemrb/trunk/gemrb/plugins/FXOpcodes/FXOpc.cpp =================================================================== --- gemrb/trunk/gemrb/plugins/FXOpcodes/FXOpc.cpp 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/plugins/FXOpcodes/FXOpc.cpp 2007-08-26 21:33:40 UTC (rev 4788) @@ -680,9 +680,10 @@ { "State:Hasted", fx_set_hasted_state, -1 }, { "State:Hold", fx_hold_creature, -1 }, //175 { "State:Hold2", fx_hold_creature, -1 },//185 - { "State:Hold3", fx_hold_creature_no_icon, -1 }, //109 - { "State:Hold4", fx_hold_creature_no_icon, -1 }, //0xfb (iwd/iwd2) - { "HoldUndead", fx_hold_creature_no_icon, -1 }, //0x1a8 (iwd2) + { "State:Hold3", fx_hold_creature, -1 },//185 + { "State:HoldNoIcon", fx_hold_creature_no_icon, -1 }, //109 + { "State:HoldNoIcon2", fx_hold_creature_no_icon, -1 }, //0xfb (iwd/iwd2) + { "State:HoldNoIcon3", fx_hold_creature_no_icon, -1 }, //0x1a8 (iwd2) { "State:Imprisonment", fx_imprisonment, -1 }, { "State:Infravision", fx_set_infravision_state, -1 }, { "State:Invisible", fx_set_invisible_state, -1 }, //both invis or improved invis @@ -2654,7 +2655,15 @@ int fx_mirror_image (Actor* Owner, Actor* target, Effect* fx) { if (0) printf( "fx_mirror_image (%2d): Mod: %d, Type: %d\n", fx->Opcode, fx->Parameter1, fx->Parameter2 ); - ieDword images = core->Roll(1, fx->Parameter1, 0); + ieDword images; + + if (fx->Parameter2) { + images = 1; //reflection + } + else { + images = core->Roll(1, fx->Parameter1, 0); //mirror image + } + Effect *fx2 = target->fxqueue.HasEffect(fx_mirror_image_modifier_ref); if (fx2) { //update old effect with our numbers if our numbers are more @@ -2668,6 +2677,7 @@ } fx->Opcode = EffectQueue::ResolveEffect(fx_mirror_image_modifier_ref); fx->Parameter1=images; + //parameter2 could be 0 or 1 (mirror image or reflection) //execute the translated effect return fx_mirror_image_modifier(Owner, target, fx); } @@ -3256,6 +3266,8 @@ int fx_set_web_state (Actor* /*Owner*/, Actor* target, Effect* fx) { if (0) printf( "fx_set_web_state (%2d): Mod: %d, Type: %d\n", fx->Opcode, fx->Parameter1, fx->Parameter2 ); + target->SetSpellState(SS_WEB); + //attack penalty in IWD2 STAT_SET_PCF( IE_WEB, 1); STAT_SET(IE_MOVEMENTRATE, 0); // return FX_APPLIED; @@ -3265,8 +3277,10 @@ int fx_set_grease_state (Actor* /*Owner*/, Actor* target, Effect* fx) { if (0) printf( "fx_set_grease_state (%2d): Mod: %d, Type: %d\n", fx->Opcode, fx->Parameter1, fx->Parameter2 ); + target->SetSpellState(SS_GREASE); STAT_SET_PCF( IE_GREASE, 1); - STAT_SET(IE_MOVEMENTRATE, 3); // + //apparently the movement rate is set by separate opcodes in all engines + //STAT_SET(IE_MOVEMENTRATE, 3); //iwd2 doesn't have this? return FX_APPLIED; } @@ -3281,6 +3295,11 @@ return FX_NOT_APPLIED; } STATE_SET( STATE_MIRROR ); + if (fx->Parameter2) { + target->SetSpellState(SS_REFLECTION); + } else { + target->SetSpellState(SS_MIRRORIMAGE); + } //actually, there is no such stat in the original IE STAT_SET( IE_MIRRORIMAGES, fx->Parameter1); return FX_APPLIED; @@ -3441,23 +3460,24 @@ //0x6d State:Hold3 //0xfb State:Hold4 -//0x1a8 HoldUndead (iwd2) int fx_hold_creature_no_icon (Actor* /*Owner*/, Actor* target, Effect* fx) { if (0) printf( "fx_hold_creature_no_icon (%2d): Value: %d, IDS: %d\n", fx->Opcode, fx->Parameter1, fx->Parameter2 ); if ( STATE_GET(STATE_DEAD) ) { return FX_NOT_APPLIED; } - if (EffectQueue::match_ids( target, fx->Parameter1, fx->Parameter2) ) { - STAT_SET( IE_HELD, 1); - return FX_APPLIED; + if (!EffectQueue::match_ids( target, fx->Parameter1, fx->Parameter2) ) { + //if the ids don't match, the effect doesn't stick + return FX_NOT_APPLIED; } - //if the ids don't match, the effect doesn't stick - return FX_NOT_APPLIED; + target->SetSpellState(SS_HELD); + STAT_SET( IE_HELD, 1); + return FX_APPLIED; } //0xaf State:Hold //0xb9 State:Hold2 +//(0x6d/0x1a8 for iwd2) int fx_hold_creature (Actor* /*Owner*/, Actor* target, Effect* fx) { if (0) printf( "fx_hold_creature (%2d): Value: %d, IDS: %d\n", fx->Opcode, fx->Parameter1, fx->Parameter2 ); @@ -3465,13 +3485,14 @@ return FX_NOT_APPLIED; } - if (EffectQueue::match_ids( target, fx->Parameter1, fx->Parameter2) ) { - STAT_SET( IE_HELD, 1); - target->AddPortraitIcon(PI_HELD); - return FX_APPLIED; + if (!EffectQueue::match_ids( target, fx->Parameter1, fx->Parameter2) ) { + //if the ids don't match, the effect doesn't stick + return FX_NOT_APPLIED; } - //if the ids don't match, the effect doesn't stick - return FX_NOT_APPLIED; + target->SetSpellState(SS_HELD); + STAT_SET( IE_HELD, 1); + target->AddPortraitIcon(PI_HELD); + return FX_APPLIED; } // b0 see: fx_movement_modifier @@ -3920,11 +3941,19 @@ if (!fx->Parameter1) { return FX_NOT_APPLIED; } - + //this is the bg2 style stoneskin, not normally using spell states + //but this way we can support hybrid games + if (fx->Parameter2) { + target->SetSpellState(SS_IRONSKIN); + //gradient for iron skins? + } else { + target->SetSpellState(SS_STONESKIN); + SetGradient(target, 14); + } STAT_SET(IE_STONESKINS, fx->Parameter1); - SetGradient(target, 14); return FX_APPLIED; } + //0xDB ac vs creature type (general effect) //0xDC DispelSchool int fx_dispel_school (Actor* /*Owner*/, Actor* target, Effect* fx) @@ -4712,8 +4741,6 @@ //0x124 Protection:Backstab (bg2) //0x11f Protection:Backstab (how, iwd2) //3 different games, 3 different methods of flagging this -#define SS_NOBACKSTAB 40 - int fx_no_backstab_modifier (Actor* /*Owner*/, Actor* target, Effect* fx) { if (0) printf( "fx_no_backstab_modifier (%2d): Mod: %d, Type: %d\n", fx->Opcode, fx->Parameter1, fx->Parameter2 ); Modified: gemrb/trunk/gemrb/plugins/IWDOpcodes/IWDOpc.cpp =================================================================== --- gemrb/trunk/gemrb/plugins/IWDOpcodes/IWDOpc.cpp 2007-08-25 18:48:10 UTC (rev 4787) +++ gemrb/trunk/gemrb/plugins/IWDOpcodes/IWDOpc.cpp 2007-08-26 21:33:40 UTC (rev 4788) @@ -588,7 +588,8 @@ return FX_APPLIED; } -//0xda IronSkins (iwd2) +//0xda IronSkins (iwd2) +//This is about damage reduction, not full stoneskin like in bg2 int fx_ironskins (Actor* /*Owner*/, Actor* target, Effect* fx) { //todo: calculate buffered damage in param3 on first run @@ -1259,8 +1260,10 @@ return FX_NOT_APPLIED; } - if (!fx->Parameter1) { - return FX_NOT_APPLIED; + int ret = FX_APPLIED; + + if (fx->Parameter1<=1) { + ret = FX_NOT_APPLIED; } //timing @@ -1270,13 +1273,13 @@ //iwd2 style if (fx->Resource[0]) { - core->ApplySpell(fx->Resource, Owner, target, fx->Power); - return FX_APPLIED; + core->ApplySpell(fx->Resource, target, Owner, fx->Power); + return ret; } //how style target->Damage(DICE_ROLL(0), DAMAGE_ELECTRICITY, Owner); - return FX_APPLIED; + return ret; } //0x109 CloakOfFear (HoW/IWD2) @@ -1304,7 +1307,7 @@ //iwd2 style if (fx->Resource[0]) { - core->ApplySpell(fx->Resource, Owner, target, fx->Power); + core->ApplySpell(fx->Resource, target, Owner, fx->Power); return FX_APPLIED; } @@ -1550,6 +1553,7 @@ } else { Enemy->objectParameter->objectFilters[0]=EA_ALLY; } + //see the nearest enemy if (SeeCore(target, Enemy, false)) { target->SetTarget(target->GetCurrentArea()->GetActorByGlobalID(target->LastSeen)); //this is highly unsure @@ -2623,11 +2627,93 @@ } //449 CallLightning -int fx_call_lightning (Actor* /*Owner*/, Actor* /*target*/, Effect* fx) +Actor *GetRandomEnemySeen(Map *map, Actor *origin) { + int type = 2; //neutral, has no enemies + if (origin->GetStat(IE_EA) <= EA_GOODCUTOFF) { + type = 1; //PC + } + if (origin->GetStat(IE_EA) >= EA_EVILCUTOFF) { + type = 0; + } + if (type==2) { + return NULL; //no enemies + } + int i = map->GetActorCount(true); + //see a random enemy + int pos = core->Roll(1,i,-1); + i -= pos; + while(i--) { + Actor *ac = map->GetActor(i,true); + if (!CanSee(origin, ac, true, GA_NO_DEAD|GA_NO_HIDDEN)) continue; + if (type) { //origin is PC + if (ac->GetStat(IE_EA) >= EA_EVILCUTOFF) { + return ac; + } + } + else { + if (ac->GetStat(IE_EA) <= EA_GOODCUTOFF) { + return ac; + } + } + } + + i=map->GetActorCount(true); + while(i--!=pos) { + Actor *ac = map->GetActor(i,true); + if (!CanSee(origin, ac, true, GA_NO_DEAD|GA_NO_HIDDEN)) continue; + if (type) { //origin is PC + if (ac->GetStat(IE_EA) >= EA_EVILCUTOFF) { + return ac; + } + } + else { + if (ac->GetStat(IE_EA) <= EA_GOODCUTOFF) { + return ac; + } + } + } + + return NULL; +} + +int fx_call_lightning (Actor* /*Owner*/, Actor* target, Effect* fx) +{ if (0) printf( "fx_call_lightning (%2d)\n", fx->Opcode); - //TODO: implement - return FX_NOT_APPLIED; + + if (STATE_GET(STATE_DEAD)) { + return FX_NOT_APPLIED; + } + int ret = FX_APPLIED; + + Map *map = target->GetCurrentArea(); + if (!map) return ret; + + if (fx->Parameter1<=1) { + ret = FX_NOT_APPLIED; + } + + //timing + fx->TimingMode=FX_DURATION_DELAY_PERMANENT; + fx->Duration=core->GetGame()->GameTime+70*15; + fx->Parameter1--; + + //calculate victim (an opponent of target) + Actor *victim = GetRandomEnemySeen(map, target); + if (!victim) { + core->DisplayConstantStringName(STR_LIGHTNING_DISS, 0xf0f0f0, target); + return ret; + } + + //iwd2 style + if (fx->Resource[0]) { + core->ApplySpell(fx->Resource, victim, target, fx->Power); + return ret; + } + + //how style + victim->Damage(DICE_ROLL(0), DAMAGE_ELECTRICITY, target); + return ret; } //450 GlobeInvulnerability This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |