Jump to content

Changing NPC model by force power


Go to solution Solved by Asgarath83,

Recommended Posts

someone can find this question really weird but i need to ask

 

i am trying to do a little edit for forcetelepathy for my mod for a custom playermodel character.

basically, when this class use this power on an enemy with certain condition i want enemy is changed to another NPC, already allocated into ,NPC file . so basically this "spell" transform an enemy into a monster that attack other enemies nearest. that is the function.

this is the code related:

 

ON NPC file

 

 

NeoProxy
{
    playerModel    shadow
    scale        90
    weapon         WP_SABER    
    saber        claw4
    FP_HEAL            2
    FP_ABSORB        0
    FP_PROTECT        0    
    FP_LEVITATION        3
    FP_PUSH            0
    FP_PULL            0    
    FP_DRAIN        1
    FP_LIGHTNING        0
    forceRegenRate        150
    forcePowerMax        100
    reactions    3
    aim        1
    move        2
    aggression    3
    evasion        3
    intelligence    2
    rank        ensign
    playerTeam    TEAM_PLAYER
    enemyTeam    TEAM_ENEMY
    class        CLASS_DARK
    yawSpeed    120
    walkSpeed    55
    runSpeed    150
    snd        shadow
    sndcombat    shadow
    sndjedi        shadow
    health        50
    dismemberProbHead    100
    dismemberProbArms    100
    dismemberProbLegs    100
    dismemberProbHands    100
    dismemberProbWaist    100
}

Proxy
{
    playerModel    shadow
    weapon         WP_SABER    
    saber        claw4
//    saber2        claw4
    FP_HEAL            2
    FP_ABSORB        0
    FP_PROTECT        0    
    FP_LEVITATION        3
    FP_PUSH            0
    FP_PULL            0    
    FP_DRAIN        1
    FP_LIGHTNING        0
    forceRegenRate        150
    forcePowerMax        100
    reactions    4
    aim        2
    move        3
    aggression    4
    evasion        4
    intelligence    3
    rank        ltjg
    playerTeam    TEAM_PLAYER
    enemyTeam    TEAM_ENEMY
    class        CLASS_DARK
    yawSpeed    120
    walkSpeed    55
    runSpeed    150
    snd        shadow
    sndcombat    shadow
    sndjedi        shadow
    health        75
    dismemberProbHead    100
    dismemberProbArms    100
    dismemberProbLegs    100
    dismemberProbHands    100
    dismemberProbWaist    100
}

Proxy2
{
    playerModel    shadow
    scale        110
    weapon         WP_SABER    
    saber        claw4
    saber2        claw4
    FP_HEAL            2
    FP_ABSORB        0
    FP_PROTECT        0    
    FP_LEVITATION        3
    FP_PUSH            0
    FP_PULL            0    
    FP_DRAIN        1
    FP_LIGHTNING        0
    forceRegenRate        150
    forcePowerMax        100
    rank            lt
    reactions    3
    aim        1
    move        2
    aggression    3
    evasion        3
    intelligence    2
    playerTeam    TEAM_PLAYER
    enemyTeam    TEAM_ENEMY
    class        CLASS_DARK
    yawSpeed    120
    walkSpeed    55
    runSpeed    150
    snd        shadow
    sndcombat    shadow
    sndjedi        shadow
    health        100
    dismemberProbHead    100
    dismemberProbArms    100
    dismemberProbLegs    100
    dismemberProbHands    100
    dismemberProbWaist    100
}
 

 

on void forcetelepathy into wp_saber.cpp

 

else if ( self->client->NPC_class == CLASS_SHIFTER ||
                            self->client->NPC_class == CLASS_SHADOWTROOPER )
                        {
                            if ( self->client->ps.forcePowerLevel[FP_TELEPATHY] == FORCE_LEVEL_1 )
                            {
                                if ( self->s.weapon != WP_SABER || self->health <= 75 )
                                {
                                    G_SoundOnEnt( self, CHAN_ITEM, "sound/weapons/force/nocast.mp3" );
                                }// Shifter cannot summon anyone if not use reaver and is too weak.
                                else
                                // Target begin a proxy!
                                {
                                // works ONLY ON HUMANS CLASSES NOT BOSSES
                                if ( traceEnt->client->NPC_class == CLASS_PRISONER ||
                                    traceEnt->client->NPC_class == CLASS_HUNTER ||
                                    traceEnt->client->NPC_class == CLASS_WARRIOR ||
                                    traceEnt->client->NPC_class == CLASS_SCOUT ||
                                    traceEnt->client->NPC_class == CLASS_ALCHEMIST ||
                                    traceEnt->client->NPC_class == CLASS_BIRD ||
                                    traceEnt->client->NPC_class == CLASS_SHARK ||
                                    traceEnt->client->NPC_class == CLASS_BEAST ||
                                    traceEnt->client->NPC_class == CLASS_RODIAN ||
                                    traceEnt->client->NPC_class == CLASS_IMPWORKER ||
                                    traceEnt->client->NPC_class == CLASS_STORMTROOPER /*||
                                    traceEnt->client->NPC_class == CLASS_SARAFAN ||
                                    traceEnt->client->NPC_class == CLASS_DRUID ||
                                    traceEnt->client->NPC_class == CLASS_WIZARD ||
                                    traceEnt->client->NPC_class == CLASS_IMPERIAL ||
                                    traceEnt->client->NPC_class == CLASS_CENOBITA ||
                                    traceEnt->client->NPC_class == CLASS_PROPHET */)
                                {
                                    G_ChangeNPCModel( traceEnt, "neoproxy" );
                                    G_PlayEffect( G_EffectIndex( "force/proxymorph" ), self->playerModel, self->chestBolt, self->s.number, self->currentOrigin);
                                    G_SoundOnEnt( self, CHAN_ITEM, "sound/weapons/force/proxymorph.mp3" );
                                    team_t    saveTeam = traceEnt->client->enemyTeam;
                                    traceEnt->client->enemyTeam = traceEnt->client->playerTeam;
                                    traceEnt->client->playerTeam = saveTeam;
                                    if ( PM_HasAnimation( traceEnt, BOTH_COWER1 ) )
                                    {// FREEZE ANIMATION
                                        NPC_SetAnim( traceEnt, SETANIM_LEGS, BOTH_COWER1, SETANIM_FLAG_NORMAL );
                                        NPC_SetAnim( traceEnt, SETANIM_TORSO, BOTH_COWER1, SETANIM_FLAG_OVERRIDE|SETANIM_FLAG_HOLD );
                                        traceEnt->client->ps.torsoAnimTimer = level.time + mindTrickTime[self->client->ps.forcePowerLevel[FP_TELEPATHY]];
                                        traceEnt->client->ps.weaponTime = traceEnt->client->ps.torsoAnimTimer;
                                    };
                                }
                            }
                        }
                        else if ( self->client->ps.forcePowerLevel[FP_TELEPATHY] == FORCE_LEVEL_2 )
                            {
                                if ( self->s.weapon != WP_SABER || self->health <= 50 )
                                {
                                    G_SoundOnEnt( self, CHAN_ITEM, "sound/weapons/force/nocast.mp3" );
                                }// Shifter cannot summon anyone if not use reaver and is too weak.
                                else
                                // Target begin a proxy!
                                {
                                // works ONLY ON HUMANS CLASSES NOT BOSSES
                                if ( traceEnt->client->NPC_class == CLASS_PRISONER ||
                                    traceEnt->client->NPC_class == CLASS_HUNTER ||
                                    traceEnt->client->NPC_class == CLASS_WARRIOR ||
                                    traceEnt->client->NPC_class == CLASS_SCOUT ||
                                    traceEnt->client->NPC_class == CLASS_ALCHEMIST ||
                                    traceEnt->client->NPC_class == CLASS_BIRD ||
                                    traceEnt->client->NPC_class == CLASS_SHARK ||
                                    traceEnt->client->NPC_class == CLASS_BEAST ||
                                    traceEnt->client->NPC_class == CLASS_RODIAN ||
                                    traceEnt->client->NPC_class == CLASS_IMPWORKER ||
                                    traceEnt->client->NPC_class == CLASS_STORMTROOPER ||
                                    traceEnt->client->NPC_class == CLASS_SARAFAN ||
                                    traceEnt->client->NPC_class == CLASS_DRUID ||
                                    traceEnt->client->NPC_class == CLASS_WIZARD
                                    /*
                                    traceEnt->client->NPC_class == CLASS_IMPERIAL ||
                                    traceEnt->client->NPC_class == CLASS_CENOBITA ||
                                    traceEnt->client->NPC_class == CLASS_PROPHET */)
                                {
                                    G_ChangeNPCModel( traceEnt, "proxy" );
                                    G_PlayEffect( G_EffectIndex( "force/proxymorph" ), self->playerModel, self->chestBolt, self->s.number, self->currentOrigin);
                                    G_SoundOnEnt( self, CHAN_ITEM, "sound/weapons/force/proxymorph.mp3" );
                                    team_t    saveTeam = traceEnt->client->enemyTeam;
                                    traceEnt->client->enemyTeam = traceEnt->client->playerTeam;
                                    traceEnt->client->playerTeam = saveTeam;
                                    if ( PM_HasAnimation( traceEnt, BOTH_SONICPAIN_HOLD ) )
                                    {// FREEZE ANIMATION
                                        NPC_SetAnim( traceEnt, SETANIM_LEGS, BOTH_SONICPAIN_HOLD, SETANIM_FLAG_NORMAL );
                                        NPC_SetAnim( traceEnt, SETANIM_TORSO, BOTH_SONICPAIN_HOLD, SETANIM_FLAG_OVERRIDE|SETANIM_FLAG_HOLD );
                                        traceEnt->client->ps.torsoAnimTimer = level.time + mindTrickTime[self->client->ps.forcePowerLevel[FP_TELEPATHY]];
                                        traceEnt->client->ps.weaponTime = traceEnt->client->ps.torsoAnimTimer;
                                    };
                                }
                            }
                        }
                        else if ( self->client->ps.forcePowerLevel[FP_TELEPATHY] == FORCE_LEVEL_3 )
                            {
                                if ( self->s.weapon != WP_SABER || self->health <= 25 )
                                {
                                    G_SoundOnEnt( self, CHAN_ITEM, "sound/weapons/force/nocast.mp3" );
                                }// Shifter cannot summon anyone if not use reaver and is too weak.
                                else
                                // Target begin a proxy!
                                {
                                // works ONLY ON HUMANS CLASSES NOT BOSSES
                                if ( traceEnt->client->NPC_class == CLASS_PRISONER ||
                                    traceEnt->client->NPC_class == CLASS_HUNTER ||
                                    traceEnt->client->NPC_class == CLASS_WARRIOR ||
                                    traceEnt->client->NPC_class == CLASS_SCOUT ||
                                    traceEnt->client->NPC_class == CLASS_ALCHEMIST ||
                                    traceEnt->client->NPC_class == CLASS_BIRD ||
                                    traceEnt->client->NPC_class == CLASS_SHARK ||
                                    traceEnt->client->NPC_class == CLASS_BEAST ||
                                    traceEnt->client->NPC_class == CLASS_RODIAN ||
                                    traceEnt->client->NPC_class == CLASS_IMPWORKER ||
                                    traceEnt->client->NPC_class == CLASS_STORMTROOPER ||
                                    traceEnt->client->NPC_class == CLASS_SARAFAN ||
                                    traceEnt->client->NPC_class == CLASS_DRUID ||
                                    traceEnt->client->NPC_class == CLASS_WIZARD ||
                                    traceEnt->client->NPC_class == CLASS_IMPERIAL ||
                                    traceEnt->client->NPC_class == CLASS_CENOBITA ||
                                    traceEnt->client->NPC_class == CLASS_PROPHET ||
                                    traceEnt->client->NPC_class == CLASS_TUSKEN ||
                                    traceEnt->client->NPC_class == CLASS_MELC ||
                                    traceEnt->client->NPC_class == CLASS_ZEPH ||
                                    traceEnt->client->NPC_class == CLASS_RODIAN ||
                                    traceEnt->client->NPC_class == CLASS_WEEQUAY ||
                                    traceEnt->client->NPC_class == CLASS_RAHABIM ||
                                    traceEnt->client->NPC_class == CLASS_GRAN ||
                                    traceEnt->client->NPC_class == CLASS_TURELIM ||
                                    traceEnt->client->NPC_class == CLASS_DUMAHIM ||
                                    traceEnt->client->NPC_class == CLASS_SWAMPTROOPER )
                                {
                                    G_ChangeNPCModel( traceEnt, "proxy2" );
                                    G_PlayEffect( G_EffectIndex( "force/proxymorph" ), self->playerModel, self->chestBolt, self->s.number, self->currentOrigin);
                                    G_SoundOnEnt( self, CHAN_ITEM, "sound/weapons/force/proxymorph.mp3" );
                                    team_t    saveTeam = traceEnt->client->enemyTeam;
                                    traceEnt->client->enemyTeam = traceEnt->client->playerTeam;
                                    traceEnt->client->playerTeam = saveTeam;
                                    if ( PM_HasAnimation( traceEnt, BOTH_SONICPAIN_HOLD ) )
                                    {// FREEZE ANIMATION
                                        NPC_SetAnim( traceEnt, SETANIM_LEGS, BOTH_SONICPAIN_HOLD, SETANIM_FLAG_NORMAL );
                                        NPC_SetAnim( traceEnt, SETANIM_TORSO, BOTH_SONICPAIN_HOLD, SETANIM_FLAG_OVERRIDE|SETANIM_FLAG_HOLD );
                                        traceEnt->client->ps.torsoAnimTimer = level.time + mindTrickTime[self->client->ps.forcePowerLevel[FP_TELEPATHY]];
                                        traceEnt->client->ps.weaponTime = traceEnt->client->ps.torsoAnimTimer;
                                    };
                                }
                            }
                        }
                    }

 

and now the bad taste: how encode correctly the function G_ChangeNPCModel i am trying of doying?

cannot use the default G_changeplayermodel because on NPC it crash and not work

 

void G_ChangePlayerModel( gentity_t *ent, const char *newModel )
{
    if ( !ent || !ent->client || !newModel )
    {
        return;
    }
    
    G_RemovePlayerModel( ent );
    if ( Q_stricmp( "player", newModel ) == 0 )
    {
        G_InitPlayerFromCvars( ent );
        return;
    }

    //attempt to free the string (currently can't since it's always "player" )
    if( ent->NPC_type && gi.bIsFromZone(ent->NPC_type, TAG_G_ALLOC) ) {
        gi.Free(ent->NPC_type);
    }
    ent->NPC_type = G_NewString( newModel );
    G_RemoveWeaponModels( ent );

    if ( strchr(newModel,'|') )
    {
        char name[MAX_QPATH];
        strcpy(name, newModel);
        char *p = strchr(name, '|');
        *p=0;
        p++;

        G_SetG2PlayerModel( ent, name, p, NULL, NULL );
    }
    else
    {
        //FIXME: everything but force powers gets reset, those should, too...
        //        currently leaves them as is except where otherwise noted in the NPCs.cfg?
        //FIXME: remove all weapons?
        if ( NPC_ParseParms( ent->NPC_type, ent ) )
        {
            G_AddWeaponModels( ent );
            NPC_SetAnim( ent, SETANIM_LEGS, ent->client->ps.legsAnim, SETANIM_FLAG_NORMAL|SETANIM_FLAG_RESTART );
            NPC_SetAnim( ent, SETANIM_TORSO, ent->client->ps.torsoAnim, SETANIM_FLAG_NORMAL|SETANIM_FLAG_RESTART );
            ClientUserinfoChanged( ent->s.number );
            //Ugh, kind of a hack for now:
            if ( ent->client->NPC_class == CLASS_BOBAFETT
                || ent->client->NPC_class == CLASS_ROCKETTROOPER )
            {
                //FIXME: remove saber, too?
                Boba_Precache();    // player as boba?
            }
        }
        else
        {
            gi.Printf( S_COLOR_RED"G_ChangePlayerModel: cannot find NPC %s\n", newModel );
            G_ChangePlayerModel( ent, "stormtrooper" );    //need a better fallback?
        }
    }
}

void G_ChangeNPCModel( gentity_t *ent, const char *newModel )
{
    if ( !ent || !ent->client || !newModel )
    {
        return;
    }
    
    G_RemovePlayerModel( ent );
    if ( ent->health >= 0 )
        /*Q_stricmp( "neoproxy", newModel ) == 0 ||
        Q_stricmp( "proxy", newModel ) == 0 ||
        Q_stricmp( "proxy2", newModel ) == 0
        )*/
    {
        NPC_ParseParms( ent->NPC_type, ent )    ;
        //G_InitPlayerFromCvars( ent );
        return;
    }

    //attempt to free the string (currently can't since it's always "player" )
    if( ent->NPC_type && gi.bIsFromZone(ent->NPC_type, TAG_G_ALLOC) ) {
        gi.Free(ent->NPC_type);
    }
    ent->NPC_type = G_NewString( newModel );
    G_RemoveWeaponModels( ent );

    if ( strchr(newModel,'|') )
    {
        char name[MAX_QPATH];
        strcpy(name, newModel);
        char *p = strchr(name, '|');
        *p=0;
        p++;

        G_SetG2PlayerModel( ent, name, p, NULL, NULL );
    }
    else
    {
        //FIXME: everything but force powers gets reset, those should, too...
        //        currently leaves them as is except where otherwise noted in the NPCs.cfg?
        //FIXME: remove all weapons?
        if ( NPC_ParseParms( ent->NPC_type, ent ) )
        {
            G_AddWeaponModels( ent );
            NPC_SetAnim( ent, SETANIM_LEGS, ent->client->ps.legsAnim, SETANIM_FLAG_NORMAL|SETANIM_FLAG_RESTART );
            NPC_SetAnim( ent, SETANIM_TORSO, ent->client->ps.torsoAnim, SETANIM_FLAG_NORMAL|SETANIM_FLAG_RESTART );
            ClientUserinfoChanged( ent->s.number );
        }
        else
        {
            gi.Printf( S_COLOR_RED"G_ChangePlayerModel: cannot find NPC %s\n", newModel );
            G_ChangePlayerModel( ent, "stormtrooper" );    //need a better fallback?
        }
    }
}
 
Smoo likes this
Link to comment
  • Solution

Update: create a new function for changing model of NPC not work much good. at the end i found an alternative.

i hope this solution can be useful for someone that need a coded mod when enemies change they appereance by code, without scripting, for deep gameplay purposes.

 

and so what you need to do is basically this:

 

1 create NPC file of new model with parms of force power, aggresssion, sound etc etc.

do: put this as changing code

 

traceEnt, if you to affect an enemy hit by telepathy \ forcelightning

self: for affected the playermodel itself of caster.

ent: for generical ent  NPC changing.

gripent: for changing model of a NPC gripped

drainent: for changing model of a npc drained

victim: for changing model of an npc hit by a saber

activator: this should affected enemy hitted by grenades-.

attacker\ attacked: rarely, but is possible to use also that in some conditions.

 

G_removeweaponmodels remove weapon model or saber model of NPC before morphing

npcparseparm read the NPC script and parse his information on model

reloadsaberdata reset saber information (if old NPC get dual sabers, this should be useful for avoid to New NPC to have again on left hand the old saber)

Addweaponmodel is necessary because if not the new saber is not visible and not do damage.

G_RemoveWeaponModels ( traceEnt );

                                    G_RemovePlayerModel( traceEnt );

                                    NPC_ParseParms( "neoproxy", traceEnt );

                                    G_ReloadSaberData( traceEnt );

                                    traceEnt->s.weapon = WP_SABER;

                                    G_AddWeaponModels( traceEnt );
Link to comment

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
×
×
  • Create New...