END_DEFAULTS bool APainElemental::Massacre () { if (Super::Massacre ()) { FState *deadstate; A_NoBlocking (this); // [RH] Use this instead of A_PainDie deadstate = DeathState; if (deadstate != NULL) { while (deadstate->GetNextState() != NULL) deadstate = deadstate->GetNextState(); SetState (deadstate); } return true; } return false; }
void gl_RenderFrameModels( const FSpriteModelFrame *smf, const FState *curState, const int curTics, const PClass *ti, Matrix3x4 *normaltransform, int translation) { // [BB] Frame interpolation: Find the FSpriteModelFrame smfNext which follows after smf in the animation // and the scalar value inter ( element of [0,1) ), both necessary to determine the interpolated frame. FSpriteModelFrame * smfNext = nullptr; double inter = 0.; if( gl_interpolate_model_frames && !(smf->flags & MDL_NOINTERPOLATION) ) { FState *nextState = curState->GetNextState( ); if( curState != nextState && nextState ) { // [BB] To interpolate at more than 35 fps we take tic fractions into account. float ticFraction = 0.; // [BB] In case the tic counter is frozen we have to leave ticFraction at zero. if ( ConsoleState == c_up && menuactive != MENU_On && !(level.flags2 & LEVEL2_FROZEN) ) { float time = GetTimeFloat(); ticFraction = (time - static_cast<int>(time)); } inter = static_cast<double>(curState->Tics - curTics - ticFraction)/static_cast<double>(curState->Tics); // [BB] For some actors (e.g. ZPoisonShroom) spr->actor->tics can be bigger than curState->Tics. // In this case inter is negative and we need to set it to zero. if ( inter < 0. ) inter = 0.; else { // [BB] Workaround for actors that use the same frame twice in a row. // Most of the standard Doom monsters do this in their see state. if ( (smf->flags & MDL_INTERPOLATEDOUBLEDFRAMES) ) { const FState *prevState = curState - 1; if ( (curState->sprite == prevState->sprite) && ( curState->Frame == prevState->Frame) ) { inter /= 2.; inter += 0.5; } if ( (curState->sprite == nextState->sprite) && ( curState->Frame == nextState->Frame) ) { inter /= 2.; nextState = nextState->GetNextState( ); } } if ( inter != 0.0 ) smfNext = gl_FindModelFrame(ti, nextState->sprite, nextState->Frame, false); } } } for(int i=0; i<MAX_MODELS_PER_FRAME; i++) { if (smf->modelIDs[i] != -1) { FModel * mdl = Models[smf->modelIDs[i]]; FTexture *tex = smf->skinIDs[i].isValid()? TexMan(smf->skinIDs[i]) : nullptr; mdl->BuildVertexBuffer(); gl_RenderState.SetVertexBuffer(mdl->mVBuf); mdl->PushSpriteMDLFrame(smf, i); if ( smfNext && smf->modelframes[i] != smfNext->modelframes[i] ) mdl->RenderFrame(tex, smf->modelframes[i], smfNext->modelframes[i], inter, translation); else mdl->RenderFrame(tex, smf->modelframes[i], smf->modelframes[i], 0.f, translation); gl_RenderState.SetVertexBuffer(GLRenderer->mVBO); } } }