Aller au contenu

Photo

Funn w/ DRAGONS


  • Veuillez vous connecter pour répondre
76 réponses à ce sujet

#1
kevL

kevL
  • Members
  • 4 052 messages
Images hosted courtesy ImageShack.
.jpg, 1280 x 1024, ~250 mb

16 Dwarven Cleric vs. 20 Red Dragon + 20 Black Dragon (dragons have Str reduced 20 pts.)
otherwise our pal Dorin wouldn't have a clue what tore him a new one ..


the Spell line-up
Posted Image

I pseudo-solved the issue of Dragon sitting on my Ax, by having Ax get tossed backward
(ps. this blugher smoked for 300 pts. don't know how it did that)
note, checking for creatureCarapice immune to Fire
Posted Image

the Black Dragon's tailswipe animation is way cool, so is the Red Dragon's wingBuffet!
Posted Image


if the Vault ever gets back online .... let's hope.

#2
The Fred

The Fred
  • Members
  • 2 516 messages
Draconomicon!

#3
kevL

kevL
  • Members
  • 4 052 messages
hehe, ya

but/and it sure lets a guy wrap his head around what's going on, what's working, and what's not ..


the infinite loop i got was fun, fer bout 2 seconds. :|

#4
Guest_Chaos Wielder_*

Guest_Chaos Wielder_*
  • Guests
I've scripted dragons to use their tail swipe if and only if you're behind them. Very fun!

#5
kevL

kevL
  • Members
  • 4 052 messages
tis :)

i'm trying to configure things to hook in via the default onSpawn (~Pia) script (just a few lines of code that make the call ..), that sets the AI, then as long as the dragon has the default onUserDefined script (for regulating Dragon Abilities) it should be a blast

slowly I'm hoping to include all the dragon races .. might even try 'fixing' the anomalous dragon blueprints that Dann discovered.

then once i'm Happy, see if it can mesh seamlessly w/ the CSL  Posted Image

#6
kevL

kevL
  • Members
  • 4 052 messages
i Should add, the radii of WingBuffet, TailSwipe, even BreathAttacks are simple functions of the dragon's age ( HD )


so if i want to scale a young one down to say 0.2 Scale, it hopefully won't breathe out a withering blast for 300 pts. over half the country .. etc.

nb. just worked in the loop for AcidBreath alongside FireBreath


* gotta wear shades

#7
painofdungeoneternal

painofdungeoneternal
  • Members
  • 1 799 messages

kevL wrote...

tis :)

i'm trying to configure things to hook in via the default onSpawn (~Pia) script (just a few lines of code that make the call ..), that sets the AI, then as long as the dragon has the default onUserDefined script (for regulating Dragon Abilities) it should be a blast

slowly I'm hoping to include all the dragon races .. might even try 'fixing' the anomalous dragon blueprints that Dann discovered.

then once i'm Happy, see if it can mesh seamlessly w/ the CSL  Posted Image


Most of that stuff is in the default AI for the game, and CSL i have done IS the default AI with renaming and fixes for crazy loops, ideally the CSL likely just needs to fix the main AI functions that look at what feats are available, and then replacing the wing buffet, breath weapon, etc that are in use now with your versions. To make it work how it is like you have it now, it's just swapping out the includes you are using, and renaming the function names to match what they got changed to in my AI version. I imagine doing both would be best as a custom dragon AI would be more efficient, but i don't like the idea of not using what you've done in the default AI which non dragons might be able to use if they had those feats.

I'd probably want to look at the VFX and damage types so there is a flag for each elemental/damage type like i do for energy subbing- instead of a completely new separate for red dragon damage, red dragons have a constant that says they do fire type damage of a given size. This would let a fire dragon on the elemental plane of fire suddenly do maximum damage in a double sized cone, or for some oddball magic to allow that red dragon to change its breath weapon to negative energy ( and look black ). This would work the same, be easier to debug one script, and a module maker could just rename that red dragon a shadow dragon and tint it, and set a variable on it and how it's breath weapon looks would change, as well as the damage done. ( i know i have the element types done, but not sure on the cone sizes which i think has more to do with duration )

Modifié par painofdungeoneternal, 09 septembre 2011 - 04:44 .


#8
kevL

kevL
  • Members
  • 4 052 messages
tks for the Reply, P.

if what I say here is somehow redundant, Pls ignore.

painofdungeoneternal wrote...

Most of that stuff is in the default AI for the game, and CSL i have done IS the default AI with renaming and fixes for crazy loops, ideally the CSL likely just needs to fix the main AI functions that look at what feats are available, and then replacing the wing buffet, breath weapon, etc that are in use now with your versions. To make it work how it is like you have it now, it's just swapping out the includes you are using, and renaming the function names to match what they got changed to in my AI version. I imagine doing both would be best as a custom dragon AI would be more efficient, but i don't like the idea of not using what you've done in the default AI which non dragons might be able to use if they had those feats.


as I think you're pointing out, i'm bypassing the default AI. (the primary scripts are taken from Tholapsyx in the OC, and seem unique for her). But i don't know enough about the larger perspective to say, oh Ok this goes into the CSL AI here ...

perhaps if & when it's done you can take a peek and inculcate it ;)

( my own motivation is (a) get Tholapsyx working, (B) get generic, default Dragons working ) - generalizing these scripts into default AI & global Feats is beyond.





I'd probably want to look at the VFX and damage types so there is a flag for each elemental/damage type like i do for energy subbing- instead of a completely new separate for red dragon damage, red dragons have a constant that says they do fire type damage of a given size. This would let a fire dragon on the elemental plane of fire suddenly do maximum damage in a double sized cone, or for some oddball magic to allow that red dragon to change its breath weapon to negative energy ( and look black ). This would work the same, be easier to debug one script, and a module maker could just rename that red dragon a shadow dragon and tint it, and set a variable on it and how it's breath weapon looks would change, as well as the damage done. ( i know i have the element types done, but not sure on the cone sizes which i think has more to do with duration )


Posted Image  <- i like turtles.

#9
Dorateen

Dorateen
  • Members
  • 477 messages
Go Dorin!

#10
painofdungeoneternal

painofdungeoneternal
  • Members
  • 1 799 messages
Yes i'd want to look at it basically, quite of what the CSL is mostly my integrating disparate features into a single system, and when i can i try to make things more moddable in the future. I would not want to implement all of what you are doing ( i really want to have separate projects ) but i'd like to have compatibility.

My AI has the same content as the real AI you are used to, so if you use TalentDragonCombat, i use SCTalentDragonCombat, and basically i kept all the core AI scripts almost the same names since there is a lot of community content which uses those basic scripts. If you modded any core functions, i'd want to add those modifications to what i am doing, and if i were to implement core improvements to the AI, i'd like for what you are doing to take advantage of it.

As for the turtles, i have an example of a spell called acid spittle which is similar in concept to a breath weapon. This is probably not needed, but the direction i am trying to take the game to make it far more flexible.

In the preliminary i have the following....
int iImpactSEF = VFX_HIT_SPELL_CONJURATION;
int iSaveType = HkGetSaveType( SAVING_THROW_TYPE_ACID );
int iShapeEffect = HkGetShapeEffect( VFX_DUR_MIRV_ACID, SC_SHAPE_MIRV );
int iHitEffect = HkGetHitEffect( VFX_HIT_SPELL_ACID );
int iDamageType = HkGetDamageType( DAMAGE_TYPE_ACID );
The above functions are wrappers, which have knowledge of CSL specific rules, so if for some reason acid damage were magically made to have half range, the visual effect would reflect that, but you mostly are just inputting the defaults. But most of the time it's just doing the defaults passed into the function keeping the overhead low.

Then i implement the above as the following excerpts
// total damage of d8, based on damage type
iDamage = HkGetSaveAdjustedDamage(SAVING_THROW_REFLEX,SAVING_THROW_METHOD_FORHALFDAMAGE,d8(), oTarget, iDC, iSaveType);

// apply an effect based on size, etc so any mods done to the damage or area show up
ApplyEffectAtLocation(DURATION_TYPE_INSTANT, EffectVisualEffect( iShapeEffect ), lImpactLoc);

// apply the damage
effect eDamage  = HkEffectDamage(iDamage, iDamageType );

This allows the system to handle varied results for fire breath, like if you are underwater fire does not always even work ( impeded rules ), on other planes fire does double aoe size, extra damage and the like. This also allows people not directly editing your scripts, to modify the effects, so putting a variable on a blueprint would make something that normally does fire damage suddenly do positive damage, so if a "positive" dragon was added to a red dragon, it's breath weapon and ANY spells it casts suddenly do positive damage, are all white flames instead of the regular ones.

Think of the PNP rules which look at Descriptor, Element, subschool, and that sort of thing, with my system the logic is exactly like what you see in the rulebook, while the game actually does it with lots of if/then in each spell or feat which only handle situations the original coder planned on. This should make it simpler for separate systems to work together, and far more flexible -- just imagine if i created a illusion/shades red dragon which is 60% real, it's breath weapon is fire, but it's a illusion, i thus have hooks to easily implement a dragon whose damage is actually an illusion just by putting variables on said creature.

This can be used to implement magic items, new classes ( frost mage for example, imagine an ice dragon with frost mage levels whose breath weapon is treated similar to his other spells ), and anything really you can imagine.

( side effect is you don't have to constantly do new visuals, as the visual is defined by the shape, element and size )

End result though is, a single breath weapon script which handles all dragon types.

#11
kevL

kevL
  • Members
  • 4 052 messages
hehe D. he's holding his own pretty darn good


Pain: ahh, i See. very noble. Then there's no conflict with what I'm doing, just a need for integration; here's what I'm thinking (the AI angle):

The feats that get called (breath(s), buffet, swipe) are using the standard entries in Feat.2da & Spells.2da ( the impact scripts are completely *based* on the old ones ).

- just took a glance at TalentDragonCombat( ) and, without eating pasta, it seems that the DragonAI i've been working from is farther reaching ... as in, it includes Buffet & Swipe not just Breath (though i didn't follow TALENT_CATEGORY_DRAGONS_BREATH to be certain) - the AI scripts that I'm using come from the OC campaign.


An odd note, in the HeartBeat (onUserDef), I decided to place a call to DetermineCombatRound( oMaster )

which *does* tie into the default AI ... at first I though this would create a massive conflict, but tried it out anyway and what i've noticed in testing is that it keeps the Dragons focused more on the PC, and more aggressively so.


These are the AI scripts (apart from the Feat/Spell scripts) :

kl_ai_dragon_roundend (was "ai_reddragon_roundend", Tholapsyx has this major AI-script set via her custom Spawn script)
kl_ai_dragon_spawn (was "ai_reddragon_spawnscript", called through the default Spawn via "SpawnScript" variable on Tholapsyx herself)
nw_c2_defaultd (was "ai_dragon_userdef", Tholapsyx' UserDef script)

thats it. Now looks misty rather than murky :) so, all one has to do for Override functionality is place a call in a dragon's onSpawn to the spawn script (and have all the files in MyDocs->override ( barring conflicts )). For Module building functionality, the "SpawnScript" variable could be set on the dragon and the UserDef script should be renamed and placed into that Event slot. No calls to SC/TalentDragonCombat (yet?)


a comment in one of the scripts:
// What does this do? Mysteries abound in the land of Faerun.


#12
painofdungeoneternal

painofdungeoneternal
  • Members
  • 1 799 messages
Yes, it would involved removing the includes you are using to use mine instead, seeing what errors out and prefixing those functions with my new prefixes,( you can look it up, but i often just guess, SCAI, SC and CSL are generally what is used ). So if you used DetermineCombatRound, it would be be SCAIDetermineCombatRound, and i could just develop search replace patterns to do this sort of things as well. This allows you to accidentally include default AI libraries if you need to and still make sure you use the other ones.

I would want to take your better logic, and redo SCTalentDragonCombat based on that, so if anything did not have the onspawn change, it would be able to use that core AI function. This could be a lot simpler logic as what you are doing is a dedicated AI, that just lets it know there is wing buffet and breath as an option and your AI might be reserved for major dragon opponents.

The feat and spellability scripts, i would just review and change based on anything you added.

AI is not something i am focusing on now, but i definitely want to have my dragons act like dragons which you seem to be doing and plan on adding more features to the default AI, so would really like to have what you are doing integrated.

Modifié par painofdungeoneternal, 09 septembre 2011 - 10:46 .


#13
kevL

kevL
  • Members
  • 4 052 messages
ok

#14
kevL

kevL
  • Members
  • 4 052 messages
great .. now i'm trying to see things through the eyes of a master scripter
my own worst enemy, Lol

( it's a blast! )


Does anyone know if it's possible to have two combat-AI routines running at the same time - I don't see why not. but,

I've come to the conclusion that DetermineCombatRound( ) knows what the onSpawned custom AI combat script is (surprise). Putting in too many DCRs tends to confuse the animations (& hence the engine), but it also makes the dragons utterly ferocious. They become belligerent, arrogant & aggressive, standing there flapping their wings & spreading fire about as they await your approach ... but from a logic PoV it's a nightmare.


So i'm trying to find one or two strategic points in the routine that might give the effect judiciously, w/out overtly encumbering the rest of runtime ..

Ps. came across a *very* interesting file:

--------
//::///////////////////////////////////////////////
//:: Custom AI Demo Template
//:: x2_ai_demo
//:: Copyright (c) 2003 Bioware Corp.
//:://////////////////////////////////////////////
/*
This is a template for those who want to
override the standard combat AI NWN uses.

The code in this file effectivly replaces
the DetermineCombatRound() function in
nw_i0_generic.nss, which is the core of the
NWN combat AI.

To override the default AI with this or any
other AI script you created, you can either
call the SetCreatureOverrideAIScript from
x2_inc_switches

[ ... or what!!?!11 - must be: Or set the
CreatureVariable "X2_SPECIAL_COMBAT_AI_SCRIPT"
with the name of your AI script on the
creature / blueprint ]

*/
//:://////////////////////////////////////////////
//:: Created By: Georg Zoeller
//:: Created On: 2003-08-21
//:://////////////////////////////////////////////

#include "nw_i0_generic"
#include "x2_inc_switches"
void main()
{
  // The following two lines should not be touched
  object oIntruder = GetCreatureOverrideAIScriptTarget();
  ClearCreatureOverrideAIScriptTarget();


  // ********************* Start of custom AI script ****************************


  // Here you can write your own AI to run in place of DetermineCombatRound.
  // The minimalistic approach would be something like
  //
  // TalentFlee(oTarget); // flee on any combat activity


  // ********************* End of custom AI script ****************************

  // This line *** has to be called here *** or the default AI will take over from
  // this point and really bad things are going to happen
  SetCreatureOverrideAIScriptFinished();
}
--------


for those curious, the AI script seems to run in the instant between End & Begin of combat Rounds. I have to work the SetCreatureOverrideAIScriptFinished( ) properly, however, else the script fires multiple times ....


mmm, pasta, very filling.


Run, Dorin! Run!!!
Posted Image

#15
kevL

kevL
  • Members
  • 4 052 messages
it's starting to feel really tight, P.

( but it's so tempting to throw DCR into the heartbeat .. )

#16
kevL

kevL
  • Members
  • 4 052 messages
ok, so i decided to keep the call to DCR out of it and go the logical route.

Fortunately i Found a little nook in the code where the same "Look at me, I'm a dragon" effect can be achieved (and in greater details ..)

#17
kevL

kevL
  • Members
  • 4 052 messages
well, after getting Combat & combatFeats solid

i decided to take a closer look at preliminary buffing ... the chunk of code that came from the OC is rather lightweight, and sure doesn't account for all sorts of dragons of all different ages, so I took a look at TalentAdvancedBuff( ) and quickly realized it could be improved w/ comprehensive list of buffing spells.

- dividing them into Long, Medium, and Short durations (which then means separating some out for use in a combatTactics routine) which is going to take some time figuring that stuff out. Then adding in their offensive choices .. henchspells, here i come! haha


On the upside, will be looking for exactly what makes Casters run into combat when they still have a storeLoad of spells, and stop that. ( most casters should just run away from anyone in armor once they run out of spells )

Tales of the Dragon, tbc



structs, *brr

#18
painofdungeoneternal

painofdungeoneternal
  • Members
  • 1 799 messages
I have an auto buff function for that purpose, very simple, but might be a helpful starting point, i started it based off of that same function. I use it for NPCs, but also allow players to use it to avoide repetive buffing, if you have it memorized it will auto cast it just like if you were an NPC.
if ( CSLGetIsInTown(oChar) )
		{
			// fast buffing in town
			HkAutoBuff( oChar, oChar, TRUE, 10, FALSE, FALSE );
		}
		else
		{
			HkAutoBuff( oChar, oChar, FALSE, 10, FALSE, FALSE );
		}

_HkSpell.nss excerpt at http://pastebin.myrror.net/2993 ( its the bottom function )


My neverworker has preliminary support for editing henchspells.2da. ( description here http://social.biowar...index/6659984/2 )

You won't like structs until you have to code PNP coinage systems, then you will love them. Usually not needed, but useful when they are.

Modifié par painofdungeoneternal, 13 septembre 2011 - 01:22 .


#19
kevL

kevL
  • Members
  • 4 052 messages
mornin' Pain

yep that's the one; you got some fancy stuff in there 'tis all


It's the offensive cast script that i'm onto now. Took a look through the AI includes (but didn't get much love there). Both the defensive and offensive functions have been cut from the primary script (and put in an include) - a bit of careful surgery on the patient there .. snipped out a few tumors and its healing well. so to speak

I notice that sections or segments of the AI are hardcoded, it seems. TALENT_CATEGORIES, eg. So if i can't see it, I'm not inclined to use it : or do you think these tie into Henchspells.2da?

ps. I can see how structs would be great once i become familiar with their syntax and am able to just read them line by line - i've come up against them two places: OC cutscene info, and (some) AI parameters. no biggie


oh, what - or who - is Hk ??? ( it helps keep my head straight )

#20
kevL

kevL
  • Members
  • 4 052 messages
holy moly, major setup.

It seems that neither a blueprint nor a placed instance critter (Dragon) wants to save the # of Uses per Special Ability.

Pls Willis (someone) tell me I'm wrong!!! I set the uses, make a save, & plays fine. Reopen the toolset and the # Uses has reverted to 1


this means either a .2da or ... structs.

#21
painofdungeoneternal

painofdungeoneternal
  • Members
  • 1 799 messages
A struct is just a way of packaging multiple variables together.

struct moneystruct {
int gold;
int silver:
string name;
object whatever;
}

Which can be used as

struct MyStruct money;
or
struct MyStruct money1 money2;

You can pass a single variable into a function.

so

money1.gold = 20
money2.gold = 30

// function here, instead of int or void its "struct MyStruct"
struct MyStruct combinemoney( struct MyStruct moneyA, struct MyStruct moneyB )
{
moneyA.gold += moneyB.gold;
moneyA.silver += moneyB.silver;
return moneyA;
}

then using it on above money1 and money2
struct MyStruct moneyfinal;

moneyfinal = combinemoney( money1, money2);

moneyfinal.gold should now be equal to 50 as it added it together in the function. Better use of it is to do a money subtract function, which just uses gold, which then looks at both the gold and silver values above, and if not enough removes 1 platinum for every how many gold. Mainly you use it to return multiple values from your function.

The main issue though,is you need to convert it to regular ints and strings to store it anywhere, then rebuild it later each time your script fires. That overhead makes it usually too much work for the benefit it gives, and PNP coinage and math is a rare place where it is useful.

Note that x, y and z on a vector is basically a struct.

If it's boolean values, you are better off learning bitwise math and storing all the values in a integer. You get 32 values.


Hk stands for hook, largely named after the spell hook. Idea is the vanilla game has getcasterlevel or the like, i make hkgetcasterlevel which wraps getcasterlevel and do that for ALL functions related to spells. If you decide that a spellcaster is holding the sword of omens and his caster level is doubled, you set a var in the spell hook and it does that, thus allowing anyone to mod the game without editing every spell script in the game themselves and running into multiple conflicts.

You can also modify the hkspell include which has all of these, i really did not like the original includes for spells which made me hunt thru multiple includes to find what to modify ( often times i'd change something and find there is more than one function doing the exact same thing ).

Hk = hook used in spells
SCAI = AI specific of SC
SC = function from a implementation library
CSL = core CSL library

I do this because i have rules for includes, no CSL function can include a SC function or Hk function, as it's the lowest level. SC are only for specific packages which are in standalone includes to support specific implementation scripts, ie the summoning include, if you don't want my summoning code you just delete the entire file. I also move constants to _c includes, as many will need to modify them, or include just the custom spell constants, and keep the config include down at the very bottom.

#22
kevL

kevL
  • Members
  • 4 052 messages
valuable datums, Sir. thank you


// Gate
case 1:
iSpell = SPELL_GATE;
sSpell = "SPELL_GATE";
iCast = GetLocalInt(oCaster, "kL_" + sSpell);

// references how many casts a dragon of 20hd gets for Gate:
iCastTotal = Get2DAInt("dragon_spells", "20", 0);


if (GetHasSpell(iSpell) && GetIsLocationValid(lTarget) && iCast <= iCastTotal)
{
  if (kL_Debug) SendMessageToPC(oPC, ". kL Dragon Spell - " + sSpell);
  kL_CastSpellAtLocation(iSpell, lTarget);

  // have to keep track of casts/total per Dragon, because the
  // #uses does not stick around on the Special Abilities tab (creature)
  SetLocalInt(oCaster, "kL_" + sSpell, iCast + 1);
  return TRUE;
}
else
{
  if (kL_Debug) SendMessageToPC(oPC, ". kL Dragon Spell - no Spell uses OR location Invalid ( GATE )");
  return FALSE;
}


( Above uses .2da ) but I'm keeping my mind open to the struct route, just because i feel it would be better to do it all in code. The challenge, if i go Struct, is congealing:

- dragon (type)
- spell
- uses

- (casts)

but for now it's going to be .2da ... Ps. the spell has to be granted via Special Abilities, and the CastSpell function must be set to bCheat. it's working so far

#23
painofdungeoneternal

painofdungeoneternal
  • Members
  • 1 799 messages
Think string

string = SerializeLocation( struct )

struct = UnserializeLocation ( string )

struct location {
object area; // AreaName
float facing; //8.04
float x; // 9.05
float y; //10.06
float z; // 11.07
string whatever; // haha
}

Then SerializeLocation stores it as follows
##AreaName#8.04#9.05#10.06#11.07#haha

I have some examples under in my position include.

#24
kevL

kevL
  • Members
  • 4 052 messages
Edit, parsed this down to what works.

// kl_dragoncast

// kevL's, 2011 Sept 14
//  - second attempt at Struct.

#include "ginc_2da"

// the struct:
struct strDragonCastStruct
{
  object oDragon;
  int iSpell;
  string sSpell;
  int iCastTotal;
  int iCastsDone;
};

// the struct funct Declaration:
struct strDragonCastStruct BuildDragonCastVariableStructure();

// the struct funct Definition:
struct strDragonCastStruct BuildDragonCastVariableStructure()
{
  struct strDragonCastStruct stDragonCastVars;

  stDragonCastVars.oDragon = OBJECT_SELF;
  stDragonCastVars.iSpell = SPELL_GATE;
  stDragonCastVars.sSpell = "SPELL_GATE";
  stDragonCastVars.iCastTotal = Get2DAInt("dragon_spells", "20", 0);
  stDragonCastVars.iCastsDone = GetLocalInt(OBJECT_SELF, "kL_DragonCast_SPELL_GATE");

  return stDragonCastVars;
}

// hehe - IT COMPILES!!


void main()
{
  struct strDragonCastStruct stDragonCastVars = BuildDragonCastVariableStructure();

  object oPC = GetFirstPC(FALSE);
  SendMessageToPC(oPC, GetName(stDragonCastVars.oDragon));
  SendMessageToPC(oPC, IntToString(stDragonCastVars.iSpell));
  SendMessageToPC(oPC, stDragonCastVars.sSpell);
  SendMessageToPC(oPC, IntToString(stDragonCastVars.iCastTotal));
  SendMessageToPC(oPC, IntToString(stDragonCastVars.iCastsDone));
}


// Go out & buy yerself a beer, Pain. ;)

Modifié par kevL, 15 septembre 2011 - 05:37 .


#25
kevL

kevL
  • Members
  • 4 052 messages

painofdungeoneternal wrote...

The main issue though,is you need to convert it to regular ints and strings to store it anywhere, then rebuild it later each time your script fires. That overhead makes it usually too much work for the benefit it gives, and PNP coinage and math is a rare place where it is useful.

i'm starting to see that's the case here (for DragonCast)

I should play around with it to get myself straighter on it ...


(and possibly get rid of those infernal switch/case blocks)