void SoftwareCursorChangedCB( IConVar *pVar, const char *pOldValue, float fOldValue ) { ConVar *pConVar = (ConVar *)pVar; vgui::surface()->SetSoftwareCursor( pConVar->GetBool() || UseVR() ); }
//----------------------------------------------------------------------------- // Purpose: ApplyMouse -- applies mouse deltas to CUserCmd // Input : viewangles - // *cmd - // mouse_x - // mouse_y - //----------------------------------------------------------------------------- void CInput::ApplyMouse( int nSlot, QAngle& viewangles, CUserCmd *cmd, float mouse_x, float mouse_y ) { PerUserInput_t &user = GetPerUser( nSlot ); //roll the view angles so roll is 0 (the HL2 assumed state) and mouse adjustments are relative to the screen. //Assuming roll is unchanging, we want mouse left to translate to screen left at all times (same for right, up, and down) if ( !((in_strafe.GetPerUser( nSlot ).state & 1) || lookstrafe.GetInt()) ) { if ( CAM_IsThirdPerson() && thirdperson_platformer.GetInt() ) { if ( mouse_x ) { // use the mouse to orbit the camera around the player, and update the idealAngle user.m_vecCameraOffset[ YAW ] -= m_yaw.GetFloat() * mouse_x; cam_idealyaw.SetValue( user.m_vecCameraOffset[ YAW ] - viewangles[ YAW ] ); // why doesn't this work??? CInput::AdjustYaw is why //cam_idealyaw.SetValue( cam_idealyaw.GetFloat() - m_yaw.GetFloat() * mouse_x ); } } else { // Otherwize, use mouse to spin around vertical axis { viewangles[YAW] -= m_yaw.GetFloat() * mouse_x; } } } else { // If holding strafe key or mlooking and have lookstrafe set to true, then apply // horizontal mouse movement to sidemove. cmd->sidemove += m_side.GetFloat() * mouse_x; } // If mouselooking and not holding strafe key, then use vertical mouse // to adjust view pitch. if (!(in_strafe.GetPerUser( nSlot ).state & 1)) { if ( CAM_IsThirdPerson() && thirdperson_platformer.GetInt() ) { if ( mouse_y ) { // use the mouse to orbit the camera around the player, and update the idealAngle user.m_vecCameraOffset[ PITCH ] += m_pitch->GetFloat() * mouse_y; cam_idealpitch.SetValue( user.m_vecCameraOffset[ PITCH ] - viewangles[ PITCH ] ); // why doesn't this work??? CInput::AdjustYaw is why //cam_idealpitch.SetValue( cam_idealpitch.GetFloat() + m_pitch->GetFloat() * mouse_y ); } } else { { viewangles[PITCH] += m_pitch->GetFloat() * mouse_y; } // Check pitch bounds if (viewangles[PITCH] > cl_pitchdown.GetFloat()) { viewangles[PITCH] = cl_pitchdown.GetFloat(); } if (viewangles[PITCH] < -cl_pitchup.GetFloat()) { viewangles[PITCH] = -cl_pitchup.GetFloat(); } } } else { // Otherwise if holding strafe key and noclipping, then move upward /* if ((in_strafe.state & 1) && IsNoClipping() ) { cmd->upmove -= m_forward.GetFloat() * mouse_y; } else */ { // Default is to apply vertical mouse movement as a forward key press. cmd->forwardmove -= m_forward.GetFloat() * mouse_y; } } // Finally, add mouse state to usercmd. // NOTE: Does rounding to int cause any issues? ywb 1/17/04 cmd->mousedx = (int)mouse_x; cmd->mousedy = (int)mouse_y; }
void CASW_Weapon_Assault_Shotgun::SecondaryAttack() { // Only the player fires this way so we can cast CASW_Player *pPlayer = GetCommander(); if (!pPlayer) return; CASW_Marine *pMarine = GetMarine(); if (!pMarine) return; //Must have ammo bool bUsesSecondary = UsesSecondaryAmmo(); bool bUsesClips = UsesClipsForAmmo2(); int iAmmoCount = pMarine->GetAmmoCount(m_iSecondaryAmmoType); bool bInWater = ( pMarine->GetWaterLevel() == 3 ); if ( (bUsesSecondary && ( ( bUsesClips && m_iClip2 <= 0) || ( !bUsesClips && iAmmoCount<=0 ) ) ) || bInWater || m_bInReload ) { SendWeaponAnim( ACT_VM_DRYFIRE ); BaseClass::WeaponSound( EMPTY ); m_flNextSecondaryAttack = gpGlobals->curtime + 0.5f; return; } BaseClass::WeaponSound( SPECIAL1 ); #ifndef CLIENT_DLL pMarine->GetMarineSpeech()->Chatter(CHATTER_GRENADE); Vector vecSrc = pMarine->Weapon_ShootPosition(); Vector vecThrow; // check for turning on lag compensation if (pPlayer && pMarine->IsInhabited()) { CASW_Lag_Compensation::RequestLagCompensation( pPlayer, pPlayer->GetCurrentUserCommand() ); } vecThrow = UTIL_LaunchVector(vecSrc, pPlayer->GetCrosshairTracePos(), asw_vindicator_grenade_gravity.GetFloat()) * 8.0f * asw_vindicator_grenade_velocity.GetFloat(); QAngle angAiming = pPlayer->EyeAnglesWithCursorRoll(); float fGrenadeDamage = MarineSkills()->GetSkillBasedValueByMarine(pMarine, ASW_MARINE_SKILL_GRENADES, ASW_MARINE_SUBSKILL_GRENADE_INCENDIARY_DMG); float fGrenadeRadius = MarineSkills()->GetSkillBasedValueByMarine(pMarine, ASW_MARINE_SKILL_GRENADES, ASW_MARINE_SUBSKILL_GRENADE_RADIUS); if (asw_debug_marine_damage.GetBool()) { Msg("Grenade damage = %f radius = %f\n", fGrenadeDamage, fGrenadeRadius); } // check the grenade fits where we want to spawn it Ray_t ray; trace_t pm; ray.Init( pMarine->WorldSpaceCenter(), vecSrc, -Vector(4,4,4), Vector(4,4,4) ); UTIL_TraceRay( ray, MASK_SOLID, pMarine, COLLISION_GROUP_PROJECTILE, &pm ); if (pm.fraction < 1.0f) vecSrc = pm.endpos; CASW_Grenade_Vindicator::Vindicator_Grenade_Create( fGrenadeDamage, fGrenadeRadius, vecSrc, angAiming, vecThrow, AngularImpulse(0,0,0), pMarine, this ); pMarine->OnWeaponFired( this, 1, true ); #endif SendWeaponAnim( GetPrimaryAttackActivity() ); pMarine->DoAnimationEvent( PLAYERANIMEVENT_FIRE_GUN_PRIMARY ); // Decrease ammo if ( bUsesClips ) { m_iClip2 -= 1; } else { pMarine->RemoveAmmo( 1, m_iSecondaryAmmoType ); } #ifndef CLIENT_DLL ASWFailAdvice()->OnMarineUsedSecondary(); CEffectData data; data.m_vOrigin = GetAbsOrigin(); //data.m_vNormal = dir; //data.m_flScale = (float)amount; CPASFilter filter( data.m_vOrigin ); filter.SetIgnorePredictionCull(true); DispatchParticleEffect( "muzzleflash_grenadelauncher_main", PATTACH_POINT_FOLLOW, this, "muzzle", false, -1, &filter ); #endif // Can shoot again immediately m_flNextPrimaryAttack = gpGlobals->curtime + 0.5f; // Can blow up after a short delay (so have time to release mouse button) m_flNextSecondaryAttack = gpGlobals->curtime + 1.0f; }
void UpdateDebugOverlayFonts() { if (hFontFG == vgui::INVALID_FONT || bFGDirty) { DevMsg("UpdateDebugOverlayFonts: regenerating FG font\n"); hFontFG = g_pVGuiSurface->CreateFont(); const char *name = cvar_fg_name.GetString(); int tall = cvar_fg_tall.GetInt(); int weight = cvar_fg_weight.GetInt(); int blur = cvar_fg_blur.GetInt(); int scanlines = cvar_fg_scanlines.GetInt(); int flags = vgui::ISurface::FONTFLAG_NONE; if (cvar_fg_italic .GetBool()) flags |= vgui::ISurface::FONTFLAG_ITALIC; if (cvar_fg_underline .GetBool()) flags |= vgui::ISurface::FONTFLAG_UNDERLINE; if (cvar_fg_strikeout .GetBool()) flags |= vgui::ISurface::FONTFLAG_STRIKEOUT; if (cvar_fg_antialias .GetBool()) flags |= vgui::ISurface::FONTFLAG_ANTIALIAS; if (cvar_fg_dropshadow.GetBool()) flags |= vgui::ISurface::FONTFLAG_DROPSHADOW; if (cvar_fg_outline .GetBool()) flags |= vgui::ISurface::FONTFLAG_OUTLINE; bool bFGOK = g_pVGuiSurface->SetFontGlyphSet(hFontFG, name, tall, weight, blur, scanlines, flags); DevMsg("UpdateDebugOverlayFonts: FG: %-3s %08lx\n", (bFGOK ? "OK" : "BAD"), hFontFG); bFGDirty = false; } if (hFontBG == vgui::INVALID_FONT || bBGDirty) { DevMsg("UpdateDebugOverlayFonts: regenerating BG font\n"); hFontBG = g_pVGuiSurface->CreateFont(); const char *name = cvar_bg_name.GetString(); int tall = cvar_bg_tall.GetInt(); int weight = cvar_bg_weight.GetInt(); int blur = cvar_bg_blur.GetInt(); int scanlines = cvar_bg_scanlines.GetInt(); int flags = vgui::ISurface::FONTFLAG_NONE; if (cvar_bg_italic .GetBool()) flags |= vgui::ISurface::FONTFLAG_ITALIC; if (cvar_bg_underline .GetBool()) flags |= vgui::ISurface::FONTFLAG_UNDERLINE; if (cvar_bg_strikeout .GetBool()) flags |= vgui::ISurface::FONTFLAG_STRIKEOUT; if (cvar_bg_antialias .GetBool()) flags |= vgui::ISurface::FONTFLAG_ANTIALIAS; if (cvar_bg_dropshadow.GetBool()) flags |= vgui::ISurface::FONTFLAG_DROPSHADOW; if (cvar_bg_outline .GetBool()) flags |= vgui::ISurface::FONTFLAG_OUTLINE; bool bBGOK = g_pVGuiSurface->SetFontGlyphSet(hFontBG, name, tall, weight, blur, scanlines, flags); DevMsg("UpdateDebugOverlayFonts: BG: %-3s %08lx\n", (bBGOK ? "OK" : "BAD"), hFontBG); bBGDirty = false; } }
void RoundInit (void) { // this is called at the start of each round g_roundEnded = false; // check team economics g_botManager->CheckTeamEconomics (TEAM_TERRORIST); g_botManager->CheckTeamEconomics (TEAM_COUNTER); for (int i = 0; i < engine->GetMaxClients (); i++) { if (g_botManager->GetBot (i)) g_botManager->GetBot (i)->NewRound (); g_radioSelect[i] = 0; } g_waypoint->SetBombPosition (true); g_waypoint->ClearGoalScore (); g_bombSayString = false; g_timeBombPlanted = 0.0f; g_timeNextBombUpdate = 0.0f; g_leaderChoosen[TEAM_COUNTER] = false; g_leaderChoosen[TEAM_TERRORIST] = false; g_lastRadioTime[0] = 0.0f; g_lastRadioTime[1] = 0.0f; g_botsCanPause = false; // SyPB Pro P.15 char *Plugin_INI = FormatBuffer("%s/addons/amxmodx/configs/plugins-dmkd.ini", GetModName()); if (TryFileOpen(Plugin_INI)) { if (CVAR_GET_FLOAT("HsK_Deathmatch_Plugin_load_SyPB") == 1) sypb_gamemod.SetInt(1); else sypb_gamemod.SetInt(0); } // SyPB Pro P.2 // SyPB Pro P.15 Plugin_INI = FormatBuffer("%s/addons/amxmodx/configs/plugins-zplague.ini", GetModName()); if (TryFileOpen(Plugin_INI)) // Getting GameMod { float delayTime = (CVAR_GET_FLOAT("zp_delay") > 0) ? CVAR_GET_FLOAT("zp_delay") : CVAR_GET_FLOAT("zp_gamemode_delay"); if (delayTime > 0) { sypb_gamemod.SetInt(2); sypb_walkallow.SetInt(0); //g_DelayTimer = engine->GetTime() + delayTime + 6.0f; // SyPB Pro P.34 - ZP TIME FIXED g_DelayTimer = engine->GetTime() + delayTime + 1.99f; } } // SyPB Pro P.11 Plugin_INI = FormatBuffer("%s/addons/amxmodx/configs/zombiehell.cfg", GetModName()); if (TryFileOpen(Plugin_INI) && CVAR_GET_FLOAT("zh_zombie_maxslots") > 0) { sypb_gamemod.SetInt(4); sypb_walkallow.SetInt(0); extern ConVar sypb_quota; sypb_quota.SetInt(static_cast <int> (CVAR_GET_FLOAT("zh_zombie_maxslots"))); } // SyPB Pro P.29 - Support CSBTE Final Plugin_INI = FormatBuffer("%s/addons/amxmodx/configs/bte_player.ini", GetModName()); if (TryFileOpen(Plugin_INI)) { const int Const_GameModes = 12; int bteGameModAi[Const_GameModes] = { 0, 0, 1, 3, 0, 2, 2, 2, 2, 4, 2, 3 };//n, t, d, d, g, g, z, z, z, z, z, n char *bteGameINI[Const_GameModes] = { "plugins-none", "plugins-td", "plugins-dm", "plugins-dr", "plugins-gd", "plugins-ghost", "plugins-zb1", "plugins-zb3", "plugins-zb4", "plugins-ze", "plugins-zse", "plugins-npc" }; for (int i = 0; i < Const_GameModes; i++) { if (TryFileOpen(FormatBuffer("%s/addons/amxmodx/configs/%s.ini", GetModName(), bteGameINI[i]))) { sypb_gamemod.SetInt(bteGameModAi[i]); if (bteGameModAi[i] == 2 && i != 5) { sypb_walkallow.SetInt(0); g_DelayTimer = engine->GetTime() + 20.0f + CVAR_GET_FLOAT("mp_freezetime"); } ServerPrint("*** CS:BTE [%s] - GameMod Setting [%d] ***", bteGameINI[i], bteGameModAi[i]); ServerPrint("*** CS:BTE [%s] - GameMod Setting [%d] ***", bteGameINI[i], bteGameModAi[i]); ServerPrint("*** CS:BTE [%s] - GameMod Setting [%d] ***", bteGameINI[i], bteGameModAi[i]); if (i == 3 || i == 9 || i == 10) { ServerPrint("***** SyPB not support the mode now :( *****"); ServerPrint("***** SyPB not support the mode now :( *****"); ServerPrint("***** SyPB not support the mode now :( *****"); ServerPrint("***** SyPB not support the mode now :( *****"); ServerPrint("***** SyPB not support the mode now :( *****"); } break; } } } // SyPB Pro P.25 - Zombie Ai if (GetGameMod() == 2 || GetGameMod() == 4) g_mapType |= MAP_DE; g_exp.UpdateGlobalKnowledge (); // update experience data on round start // calculate the round mid/end in world time g_timeRoundStart = engine->GetTime () + engine->GetFreezeTime (); g_timeRoundMid = g_timeRoundStart + engine->GetRoundTime () * 60 / 2; g_timeRoundEnd = g_timeRoundStart + engine->GetRoundTime () * 60; }
void CASWHudCrosshair::Paint( void ) { VPROF_BUDGET( "CASWHudCrosshair::Paint", VPROF_BUDGETGROUP_ASW_CLIENT ); if ( !crosshair.GetBool() ) return; if ( engine->IsDrawingLoadingImage() || engine->IsPaused() || !engine->IsActiveApp() ) return; C_ASW_Player* pPlayer = C_ASW_Player::GetLocalASWPlayer(); if ( !pPlayer ) return; if ( pPlayer->GetFlags() & FL_FROZEN ) return; if ( pPlayer->entindex() != render->GetViewEntity() ) return; m_curViewAngles = CurrentViewAngles(); m_curViewOrigin = CurrentViewOrigin(); C_ASW_Marine *pMarine = pPlayer->GetViewMarine(); bool bControllingTurret = (pMarine && pMarine->IsControllingTurret()); if ( bControllingTurret ) { PaintTurretTextures(); return; // don't draw the normal cross hair in addition } int x, y; GetCurrentPos( x, y ); int nCrosshair = GetCurrentCrosshair( x, y ); if ( nCrosshair == m_nCrosshairTexture ) { if ( pPlayer->IsSniperScopeActive() ) { DrawSniperScope( x, y ); } else { if ( pPlayer->GetASWControls() != 1 ) return; DrawDirectionalCrosshair( x, y, YRES( asw_crosshair_progress_size.GetInt() ) ); } } else if ( nCrosshair != -1 ) { const float fCrosshairScale = 1.0f; int w = YRES( 20 ) * fCrosshairScale; int h = YRES( 20 ) * fCrosshairScale; surface()->DrawSetColor( m_clrCrosshair ); surface()->DrawSetTexture( nCrosshair ); surface()->DrawTexturedRect( x - w, y - h, x + w, y + h ); } // icons attached to the cursor x += 32; y += 16; // move them down and to the right a bit if ( m_bShowGiveAmmo ) { // todo: this text should in the ammo report tooltip? const wchar_t *ammoName = g_pVGuiLocalize->Find(GetAmmoName(m_iShowGiveAmmoType)); DrawAttachedIcon(m_nGiveAmmoTexture, x, y, ammoName); } else if (m_bShowGiveHealth) { DrawAttachedIcon(m_nGiveHealthTexture, x, y); } }
void CASWHudCrosshair::OnThink() { C_ASW_Player* pPlayer = C_ASW_Player::GetLocalASWPlayer(); if ( !pPlayer ) return; PaintReloadProgressBar(); C_ASW_Marine *pMarine = pPlayer->GetViewMarine(); bool bControllingTurret = (pMarine && pMarine->IsControllingTurret()); if (!bControllingTurret) return; C_ASW_Remote_Turret *pTurret = pMarine->GetRemoteTurret(); if (!pTurret) return; Vector vecWeaponPos = pTurret->GetAbsOrigin(); QAngle angWeapon = pTurret->EyeAngles(); Vector vecWeaponDir; AngleVectors(angWeapon, &vecWeaponDir); // increase lock time of all targets and discard out of range/facing ones for (int k=0;k<ASW_MAX_TURRET_TARGETS;k++) { C_BaseEntity *pEnt = m_TurretTarget[k].Get(); if (pEnt) { // validate the target bool bValid = true; Vector diff = pEnt->GetAbsOrigin() - vecWeaponPos; if (diff.Length() > ASW_TURRET_TARGET_RANGE || !pEnt->ShouldDraw()) { bValid = false; } else { diff.NormalizeInPlace(); float flDot = diff.Dot(vecWeaponDir); if (flDot < asw_turret_dot.GetFloat()) bValid = false; } // fade it in or out appropriately if (bValid) { if (m_fTurretTargetLock[k] < 1.0f) { m_fTurretTargetLock[k] += gpGlobals->frametime * 2; if (m_fTurretTargetLock[k] > 1.0f) m_fTurretTargetLock[k] = 1.0f; } } else { if (m_fTurretTargetLock[k] <= 0) { m_TurretTarget[k] = NULL; } else { m_fTurretTargetLock[k] -= gpGlobals->frametime * 2; if (m_fTurretTargetLock[k] < 0.0f) m_fTurretTargetLock[k] = 0.0f; } } } } // check for adding new targets to the array for ( int i = 0; i < IASW_Client_Aim_Target::AutoList().Count(); i++ ) { IASW_Client_Aim_Target *pAimTarget = static_cast< IASW_Client_Aim_Target* >( IASW_Client_Aim_Target::AutoList()[ i ] ); C_BaseEntity *pEnt = pAimTarget->GetEntity(); if (!pEnt || !pAimTarget->IsAimTarget() || !pEnt->ShouldDraw()) continue; // check he's in range Vector vecAlienPos = pEnt->WorldSpaceCenter(); float flAlienDist = vecAlienPos.DistTo(vecWeaponPos); if (flAlienDist > ASW_TURRET_TARGET_RANGE) continue; // check it's in front of us Vector dir = vecAlienPos - vecWeaponPos; dir.NormalizeInPlace(); if (dir.Dot(vecWeaponDir) <= asw_turret_dot.GetFloat()) continue; // we've got a possible target, add him to the list if he's not in there already bool bAlreadyInArray = false; int iSpace = -1; for (int k=0;k<ASW_MAX_TURRET_TARGETS;k++) { if (m_TurretTarget[k].Get() == pEnt) { bAlreadyInArray = true; break; } if (iSpace == -1 && m_TurretTarget[k].Get() == NULL) iSpace = k; } if (bAlreadyInArray) continue; if (iSpace != -1) { m_TurretTarget[iSpace] = pEnt; m_fTurretTargetLock[iSpace] = 0; } } }
//----------------------------------------------------------------------------- // Draws the shader //----------------------------------------------------------------------------- void DrawSkin_DX9_Internal( CBaseVSShader *pShader, IMaterialVar** params, IShaderDynamicAPI *pShaderAPI, IShaderShadow* pShaderShadow, bool bHasFlashlight, VertexLitGeneric_DX9_Vars_t &info, VertexCompressionType_t vertexCompression, CBasePerMaterialContextData **pContextDataPtr ) { bool bHasBaseTexture = (info.m_nBaseTexture != -1) && params[info.m_nBaseTexture]->IsTexture(); bool bHasBump = (info.m_nBumpmap != -1) && params[info.m_nBumpmap]->IsTexture(); bool bHasBaseTextureWrinkle = bHasBaseTexture && (info.m_nWrinkle != -1) && params[info.m_nWrinkle]->IsTexture() && (info.m_nStretch != -1) && params[info.m_nStretch]->IsTexture(); bool bHasBumpWrinkle = bHasBump && (info.m_nNormalWrinkle != -1) && params[info.m_nNormalWrinkle]->IsTexture() && (info.m_nNormalStretch != -1) && params[info.m_nNormalStretch]->IsTexture(); bool bHasVertexColor = IS_FLAG_SET( MATERIAL_VAR_VERTEXCOLOR ); bool bHasVertexAlpha = IS_FLAG_SET( MATERIAL_VAR_VERTEXALPHA ); bool bIsAlphaTested = IS_FLAG_SET( MATERIAL_VAR_ALPHATEST ) != 0; bool bHasSelfIllum = IS_FLAG_SET( MATERIAL_VAR_SELFILLUM ) != 0; bool bHasSelfIllumFresnel = ( bHasSelfIllum ) && ( info.m_nSelfIllumFresnel != -1 ) && ( params[info.m_nSelfIllumFresnel]->GetIntValue() != 0 ); bool bHasSelfIllumMask = ( bHasSelfIllum ) && (info.m_nSelfIllumMask != -1) && params[info.m_nSelfIllumMask]->IsTexture(); // Tie these to specular bool bHasPhong = (info.m_nPhong != -1) && ( params[info.m_nPhong]->GetIntValue() != 0 ); bool bHasSpecularExponentTexture = (info.m_nPhongExponentTexture != -1) && params[info.m_nPhongExponentTexture]->IsTexture(); bool bHasPhongTintMap = bHasSpecularExponentTexture && (info.m_nPhongAlbedoTint != -1) && ( params[info.m_nPhongAlbedoTint]->GetIntValue() != 0 ); bool bHasDiffuseWarp = (info.m_nDiffuseWarpTexture != -1) && params[info.m_nDiffuseWarpTexture]->IsTexture(); bool bHasPhongWarp = (info.m_nPhongWarpTexture != -1) && params[info.m_nPhongWarpTexture]->IsTexture(); bool bHasNormalMapAlphaEnvmapMask = IS_FLAG_SET( MATERIAL_VAR_NORMALMAPALPHAENVMAPMASK ); #if !defined( _X360 ) bool bIsDecal = IS_FLAG_SET( MATERIAL_VAR_DECAL ); #endif // Rimlight must be set to non-zero to trigger rim light combo (also requires Phong) bool bHasRimLight = r_rimlight.GetBool() && bHasPhong && (info.m_nRimLight != -1) && ( params[info.m_nRimLight]->GetIntValue() != 0 ); bool bHasRimMaskMap = bHasSpecularExponentTexture && bHasRimLight && (info.m_nRimMask != -1) && ( params[info.m_nRimMask]->GetIntValue() != 0 ); int nDetailBlendMode = ( info.m_nDetailTextureCombineMode == -1 ) ? 0 : params[info.m_nDetailTextureCombineMode]->GetIntValue(); float fBlendFactor=( info.m_nDetailTextureBlendFactor == -1 )? 1 : params[info.m_nDetailTextureBlendFactor]->GetFloatValue(); BlendType_t nBlendType = pShader->EvaluateBlendRequirements( info.m_nBaseTexture, true ); bool bFullyOpaque = (nBlendType != BT_BLENDADD) && (nBlendType != BT_BLEND) && !bIsAlphaTested && !bHasFlashlight; //dest alpha is free for special use bool hasDetailTexture = ( info.m_nDetail != -1 ) && params[info.m_nDetail]->IsTexture(); CSkin_DX9_Context *pContextData = reinterpret_cast< CSkin_DX9_Context *> ( *pContextDataPtr ); if ( ! pContextData ) { pContextData = new CSkin_DX9_Context; *pContextDataPtr = pContextData; } if( pShader->IsSnapshotting() ) { // look at color and alphamod stuff. // Unlit generic never uses the flashlight bool bHasEnvmap = !bHasFlashlight && params[info.m_nEnvmap]->IsTexture(); bool bHasNormal = params[info.m_nBumpmap]->IsTexture(); bool bCanUseBaseAlphaPhongMaskFastPath = (info.m_nBaseMapAlphaPhongMask != -1) && ( params[info.m_nBaseMapAlphaPhongMask]->GetIntValue() != 0 ); if ( ! ( params[info.m_nBaseTexture]->GetTextureValue()->IsTranslucent() ) ) bCanUseBaseAlphaPhongMaskFastPath = true; pContextData->m_bFastPath = (! bHasBump ) && (! bHasSpecularExponentTexture ) && (! bHasPhongTintMap ) && (! bHasPhongWarp ) && (! bHasRimLight ) && (! hasDetailTexture ) && bCanUseBaseAlphaPhongMaskFastPath && (! bHasSelfIllum ); // Alpha test: FIXME: shouldn't this be handled in CBaseVSShader::SetInitialShadowState pShaderShadow->EnableAlphaTest( bIsAlphaTested ); if( info.m_nAlphaTestReference != -1 && params[info.m_nAlphaTestReference]->GetFloatValue() > 0.0f ) { pShaderShadow->AlphaFunc( SHADER_ALPHAFUNC_GEQUAL, params[info.m_nAlphaTestReference]->GetFloatValue() ); } const int nShadowFilterMode = g_pHardwareConfig->GetShadowFilterMode(); if( bHasFlashlight ) { if (params[info.m_nBaseTexture]->IsTexture()) { pShader->SetAdditiveBlendingShadowState( info.m_nBaseTexture, true ); } if( bIsAlphaTested ) { // disable alpha test and use the zfunc zequals since alpha isn't guaranteed to // be the same on both the regular pass and the flashlight pass. pShaderShadow->EnableAlphaTest( false ); pShaderShadow->DepthFunc( SHADER_DEPTHFUNC_EQUAL ); } pShaderShadow->EnableBlending( true ); pShaderShadow->EnableDepthWrites( false ); // Be sure not to write to dest alpha pShaderShadow->EnableAlphaWrites( false ); //nShadowFilterMode = g_pHardwareConfig->GetShadowFilterMode(); // Based upon vendor and device dependent formats } else // not flashlight pass { if (params[info.m_nBaseTexture]->IsTexture()) { pShader->SetDefaultBlendingShadowState( info.m_nBaseTexture, true ); } if ( bHasEnvmap ) { pShaderShadow->EnableTexture( SHADER_SAMPLER8, true ); // Cubic environment map if( g_pHardwareConfig->GetHDRType() == HDR_TYPE_NONE ) { pShaderShadow->EnableSRGBRead( SHADER_SAMPLER8, true ); } } } unsigned int flags = VERTEX_POSITION; if( bHasNormal ) { flags |= VERTEX_NORMAL; } int userDataSize = 0; // Always enable...will bind white if nothing specified... pShaderShadow->EnableTexture( SHADER_SAMPLER0, true ); // Base (albedo) map pShaderShadow->EnableSRGBRead( SHADER_SAMPLER0, true ); if ( bHasBaseTextureWrinkle || bHasBumpWrinkle ) { pShaderShadow->EnableTexture( SHADER_SAMPLER9, true ); // Base (albedo) compression map pShaderShadow->EnableSRGBRead( SHADER_SAMPLER9, true ); pShaderShadow->EnableTexture( SHADER_SAMPLER10, true ); // Base (albedo) expansion map pShaderShadow->EnableSRGBRead( SHADER_SAMPLER10, true ); } if( bHasDiffuseWarp ) { pShaderShadow->EnableTexture( SHADER_SAMPLER2, true ); // Diffuse warp texture } if( bHasPhongWarp ) { pShaderShadow->EnableTexture( SHADER_SAMPLER1, true ); // Specular warp texture } // Specular exponent map or dummy pShaderShadow->EnableTexture( SHADER_SAMPLER7, true ); // Specular exponent map if( bHasFlashlight ) { pShaderShadow->EnableTexture( SHADER_SAMPLER4, true ); // Shadow depth map pShaderShadow->SetShadowDepthFiltering( SHADER_SAMPLER4 ); pShaderShadow->EnableSRGBRead( SHADER_SAMPLER4, false ); pShaderShadow->EnableTexture( SHADER_SAMPLER6, true ); // Flashlight cookie userDataSize = 4; // tangent S } else { pShaderShadow->EnableTexture( SHADER_SAMPLER4, true ); // Shadow depth map pShaderShadow->SetShadowDepthFiltering( SHADER_SAMPLER4 ); pShaderShadow->EnableSRGBRead( SHADER_SAMPLER4, false ); } // Always enable, since flat normal will be bound pShaderShadow->EnableTexture( SHADER_SAMPLER3, true ); // Normal map userDataSize = 4; // tangent S pShaderShadow->EnableTexture( SHADER_SAMPLER5, true ); // Normalizing cube map if ( bHasBaseTextureWrinkle || bHasBumpWrinkle ) { pShaderShadow->EnableTexture( SHADER_SAMPLER11, true ); // Normal compression map pShaderShadow->EnableTexture( SHADER_SAMPLER12, true ); // Normal expansion map } if ( hasDetailTexture ) { pShaderShadow->EnableTexture( SHADER_SAMPLER13, true ); if ( nDetailBlendMode != 0 ) //Not Mod2X pShaderShadow->EnableSRGBRead( SHADER_SAMPLER13, true ); } if ( bHasSelfIllum ) { pShaderShadow->EnableTexture( SHADER_SAMPLER14, true ); } if( bHasVertexColor || bHasVertexAlpha ) { flags |= VERTEX_COLOR; } pShaderShadow->EnableSRGBWrite( true ); // texcoord0 : base texcoord, texcoord2 : decal hw morph delta int pTexCoordDim[3] = { 2, 0, 3 }; int nTexCoordCount = 1; #ifndef _X360 // Special morphed decal information if ( bIsDecal && g_pHardwareConfig->HasFastVertexTextures() ) { nTexCoordCount = 3; } #endif // This shader supports compressed vertices, so OR in that flag: flags |= VERTEX_FORMAT_COMPRESSED; pShaderShadow->VertexShaderVertexFormat( flags, nTexCoordCount, pTexCoordDim, userDataSize ); #ifndef _X360 //if ( !g_pHardwareConfig->SupportsShaderModel_3_0() ) if ( false ) #endif { DECLARE_STATIC_VERTEX_SHADER( sdk_skin_vs20 ); SET_STATIC_VERTEX_SHADER( sdk_skin_vs20 ); // Assume we're only going to get in here if we support 2b DECLARE_STATIC_PIXEL_SHADER( sdk_skin_ps20b ); SET_STATIC_PIXEL_SHADER_COMBO( FLASHLIGHT, bHasFlashlight ); SET_STATIC_PIXEL_SHADER_COMBO( SELFILLUM, bHasSelfIllum && !bHasFlashlight ); SET_STATIC_PIXEL_SHADER_COMBO( SELFILLUMFRESNEL, bHasSelfIllumFresnel && !bHasFlashlight ); SET_STATIC_PIXEL_SHADER_COMBO( LIGHTWARPTEXTURE, bHasDiffuseWarp && bHasPhong ); SET_STATIC_PIXEL_SHADER_COMBO( PHONGWARPTEXTURE, bHasPhongWarp && bHasPhong ); SET_STATIC_PIXEL_SHADER_COMBO( WRINKLEMAP, bHasBaseTextureWrinkle || bHasBumpWrinkle ); SET_STATIC_PIXEL_SHADER_COMBO( DETAILTEXTURE, hasDetailTexture ); SET_STATIC_PIXEL_SHADER_COMBO( DETAIL_BLEND_MODE, nDetailBlendMode ); SET_STATIC_PIXEL_SHADER_COMBO( RIMLIGHT, bHasRimLight ); SET_STATIC_PIXEL_SHADER_COMBO( CUBEMAP, bHasEnvmap ); SET_STATIC_PIXEL_SHADER_COMBO( FLASHLIGHTDEPTHFILTERMODE, nShadowFilterMode ); SET_STATIC_PIXEL_SHADER_COMBO( CONVERT_TO_SRGB, 0 ); SET_STATIC_PIXEL_SHADER_COMBO( FASTPATH_NOBUMP, pContextData->m_bFastPath ); SET_STATIC_PIXEL_SHADER( sdk_skin_ps20b ); } #ifndef _X360 else { const bool bFastVertexTextures = g_pHardwareConfig->HasFastVertexTextures(); // The vertex shader uses the vertex id stream if ( bFastVertexTextures ) SET_FLAGS2( MATERIAL_VAR2_USES_VERTEXID ); DECLARE_STATIC_VERTEX_SHADER( sdk_skin_vs30 ); SET_STATIC_VERTEX_SHADER_COMBO( DECAL, bIsDecal && bFastVertexTextures ); SET_STATIC_VERTEX_SHADER( sdk_skin_vs30 ); DECLARE_STATIC_PIXEL_SHADER( sdk_skin_ps30 ); SET_STATIC_PIXEL_SHADER_COMBO( FLASHLIGHT, bHasFlashlight ); SET_STATIC_PIXEL_SHADER_COMBO( SELFILLUM, bHasSelfIllum && !bHasFlashlight ); SET_STATIC_PIXEL_SHADER_COMBO( SELFILLUMFRESNEL, bHasSelfIllumFresnel && !bHasFlashlight ); SET_STATIC_PIXEL_SHADER_COMBO( LIGHTWARPTEXTURE, bHasDiffuseWarp && bHasPhong ); SET_STATIC_PIXEL_SHADER_COMBO( PHONGWARPTEXTURE, bHasPhongWarp && bHasPhong ); SET_STATIC_PIXEL_SHADER_COMBO( WRINKLEMAP, bHasBaseTextureWrinkle || bHasBumpWrinkle ); SET_STATIC_PIXEL_SHADER_COMBO( DETAILTEXTURE, hasDetailTexture ); SET_STATIC_PIXEL_SHADER_COMBO( DETAIL_BLEND_MODE, nDetailBlendMode ); SET_STATIC_PIXEL_SHADER_COMBO( RIMLIGHT, bHasRimLight ); SET_STATIC_PIXEL_SHADER_COMBO( CUBEMAP, bHasEnvmap ); //SET_STATIC_PIXEL_SHADER_COMBO( FLASHLIGHTDEPTHFILTERMODE, nShadowFilterMode ); SET_STATIC_PIXEL_SHADER_COMBO( CONVERT_TO_SRGB, 0 ); SET_STATIC_PIXEL_SHADER_COMBO( FASTPATH_NOBUMP, pContextData->m_bFastPath ); SET_STATIC_PIXEL_SHADER( sdk_skin_ps30 ); } #endif if( bHasFlashlight ) { pShader->FogToBlack(); } else { pShader->DefaultFog(); } // HACK HACK HACK - enable alpha writes all the time so that we have them for underwater stuff pShaderShadow->EnableAlphaWrites( bFullyOpaque ); } else // not snapshotting -- begin dynamic state { static CCommandBufferBuilder< CFixedCommandStorageBuffer< 2000 > > DynamicCmdsOut; DynamicCmdsOut.Reset(); bool bLightingOnly = mat_fullbright.GetInt() == 2 && !IS_FLAG_SET( MATERIAL_VAR_NO_DEBUG_OVERRIDE ); bool bHasEnvmap = !bHasFlashlight && params[info.m_nEnvmap]->IsTexture(); if ( bHasBaseTexture ) { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER0, info.m_nBaseTexture, info.m_nBaseTextureFrame ); } else { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER0, TEXTURE_WHITE ); } if ( bHasBaseTextureWrinkle ) { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER9, info.m_nWrinkle, info.m_nBaseTextureFrame ); DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER10, info.m_nStretch, info.m_nBaseTextureFrame ); } else if ( bHasBumpWrinkle ) { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER9, info.m_nBaseTexture, info.m_nBaseTextureFrame ); DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER10, info.m_nBaseTexture, info.m_nBaseTextureFrame ); } if( bHasDiffuseWarp && bHasPhong ) { if ( r_lightwarpidentity.GetBool() ) { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER2, TEXTURE_IDENTITY_LIGHTWARP ); } else { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER2, info.m_nDiffuseWarpTexture, -1 ); } } if( bHasPhongWarp ) { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER1, info.m_nPhongWarpTexture, -1 ); } if( bHasSpecularExponentTexture && bHasPhong ) { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER7, info.m_nPhongExponentTexture, -1 ); } else { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER7, TEXTURE_WHITE ); } if( !g_pConfig->m_bFastNoBump ) { if( bHasBump ) DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER3, info.m_nBumpmap, info.m_nBumpFrame ); else DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER3, TEXTURE_NORMALMAP_FLAT ); if ( bHasBumpWrinkle ) { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER11, info.m_nNormalWrinkle, info.m_nBumpFrame ); DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER12, info.m_nNormalStretch, info.m_nBumpFrame ); } else if ( bHasBaseTextureWrinkle ) { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER11, info.m_nBumpmap, info.m_nBumpFrame ); DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER12, info.m_nBumpmap, info.m_nBumpFrame ); } } else { if( bHasBump ) { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER3, TEXTURE_NORMALMAP_FLAT ); } if ( bHasBaseTextureWrinkle || bHasBumpWrinkle ) { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER11, TEXTURE_NORMALMAP_FLAT ); DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER12, TEXTURE_NORMALMAP_FLAT ); } } if ( hasDetailTexture ) { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER13, info.m_nDetail, info.m_nDetailFrame ); } if ( bHasSelfIllum ) { if ( bHasSelfIllumMask ) // Separate texture for self illum? { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER14, info.m_nSelfIllumMask, -1 ); // Bind it } else // else { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER14, TEXTURE_BLACK ); // Bind dummy } } float vRimBoost[4] = {1, 1, 1, 1}; ITexture *pCascadedDepthTexture = NULL; LightState_t lightState = { 0, false, false }; bool bFlashlightShadows = false; if ( bHasFlashlight ) { Assert( info.m_nFlashlightTexture >= 0 && info.m_nFlashlightTextureFrame >= 0 ); //DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER6, info.m_nFlashlightTexture, info.m_nFlashlightTextureFrame ); VMatrix worldToTexture; ITexture *pFlashlightDepthTexture; const FlashlightState_t &flashlightState = pShaderAPI->GetFlashlightStateEx( worldToTexture, &pFlashlightDepthTexture ); bFlashlightShadows = flashlightState.m_bEnableShadows; if ( pFlashlightDepthTexture && g_pConfig->ShadowDepthTexture() && flashlightState.m_bEnableShadows ) { pShader->BindTexture( SHADER_SAMPLER4, pFlashlightDepthTexture ); DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER5, TEXTURE_SHADOW_NOISE_2D ); } float atten[4], pos[4], tweaks[4]; SetFlashLightColorFromState( flashlightState, pShaderAPI, PSREG_FLASHLIGHT_COLOR ); //DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER6, info.m_nFlashlightTexture, info.m_nFlashlightTextureFrame ); pShader->BindTexture( SHADER_SAMPLER6, flashlightState.m_pSpotlightTexture, flashlightState.m_nSpotlightTextureFrame ); atten[0] = flashlightState.m_fConstantAtten; // Set the flashlight attenuation factors atten[1] = flashlightState.m_fLinearAtten; atten[2] = flashlightState.m_fQuadraticAtten; atten[3] = flashlightState.m_FarZ; DynamicCmdsOut.SetPixelShaderConstant( PSREG_FLASHLIGHT_ATTENUATION, atten, 1 ); pos[0] = flashlightState.m_vecLightOrigin[0]; // Set the flashlight origin pos[1] = flashlightState.m_vecLightOrigin[1]; pos[2] = flashlightState.m_vecLightOrigin[2]; DynamicCmdsOut.SetPixelShaderConstant( PSREG_FLASHLIGHT_POSITION_RIM_BOOST, pos, 1 ); // steps on rim boost DynamicCmdsOut.SetPixelShaderConstant( PSREG_FLASHLIGHT_TO_WORLD_TEXTURE, worldToTexture.Base(), 4 ); // Tweaks associated with a given flashlight tweaks[0] = ShadowFilterFromState( flashlightState ); tweaks[1] = ShadowAttenFromState( flashlightState ); pShader->HashShadow2DJitter( flashlightState.m_flShadowJitterSeed, &tweaks[2], &tweaks[3] ); DynamicCmdsOut.SetPixelShaderConstant( PSREG_ENVMAP_TINT__SHADOW_TWEAKS, tweaks, 1 ); // Dimensions of screen, used for screen-space noise map sampling float vScreenScale[4] = {1280.0f / 32.0f, 720.0f / 32.0f, 0, 0}; int nWidth, nHeight; pShaderAPI->GetBackBufferDimensions( nWidth, nHeight ); vScreenScale[0] = (float) nWidth / 32.0f; vScreenScale[1] = (float) nHeight / 32.0f; DynamicCmdsOut.SetPixelShaderConstant( PSREG_FLASHLIGHT_SCREEN_SCALE, vScreenScale, 1 ); if ( IsX360() ) { pShaderAPI->SetBooleanPixelShaderConstant( 0, &flashlightState.m_nShadowQuality, 1 ); } } else // no flashlight { if ( bHasEnvmap ) { DynamicCmdsOut.BindTexture( pShader, SHADER_SAMPLER8, info.m_nEnvmap, info.m_nEnvmapFrame ); } // GSTRINGMIGRATION pShaderAPI->GetDX9LightState( &lightState ); pCascadedDepthTexture = (ITexture*)pShaderAPI->GetIntRenderingParameter( INT_CASCADED_DEPTHTEXTURE ); if ( pCascadedDepthTexture != NULL ) { pShader->BindTexture( SHADER_SAMPLER4, pCascadedDepthTexture ); VMatrix *worldToTexture0 = (VMatrix*)pShaderAPI->GetIntRenderingParameter( INT_CASCADED_MATRIX_ADDRESS_0 ); DynamicCmdsOut.SetVertexShaderConstant( 240, worldToTexture0->Base(), 4 ); const Vector vecCascadedFwd = pShaderAPI->GetVectorRenderingParameter( VECTOR_RENDERPARM_GSTRING_CASCADED_FORWARD ); vRimBoost[0] = vecCascadedFwd.x; vRimBoost[1] = vecCascadedFwd.y; vRimBoost[2] = vecCascadedFwd.z; float vScreenScale[4] = {1280.0f / 32.0f, 720.0f / 32.0f, 0, 0}; int nWidth, nHeight; pShaderAPI->GetBackBufferDimensions( nWidth, nHeight ); vScreenScale[0] = (float) nWidth / 32.0f; vScreenScale[1] = (float) nHeight / 32.0f; DynamicCmdsOut.SetPixelShaderConstant( PSREG_FLASHLIGHT_SCREEN_SCALE, vScreenScale, 1 ); // We have to rebuild the lighting state by hand. Fading static lights are out of order! float vDirectionalLights[4] = { 0.0f }; SetCustomPixelLightingState( DynamicCmdsOut, lightState, pShaderAPI, PSREG_LIGHT_INFO_ARRAY ); SetCustomVertexLightingState( DynamicCmdsOut, lightState, pShaderAPI, 27, vDirectionalLights ); DynamicCmdsOut.SetPixelShaderConstant( PSREG_FLASHLIGHT_COLOR, vDirectionalLights ); const Vector vecCascadedStep = pShaderAPI->GetVectorRenderingParameter( VECTOR_RENDERPARM_GSTRING_CASCADED_STEP ); float vCascadedStep[4] = { XYZ( vecCascadedStep ) }; DynamicCmdsOut.SetPixelShaderConstant( PSREG_FLASHLIGHT_TO_WORLD_TEXTURE, vCascadedStep, 1 ); } } if ( pCascadedDepthTexture == NULL ) { DynamicCmdsOut.CommitPixelShaderLighting( PSREG_LIGHT_INFO_ARRAY ); } // END GSTRINGMIGRATION MaterialFogMode_t fogType = pShaderAPI->GetSceneFogMode(); int fogIndex = ( fogType == MATERIAL_FOG_LINEAR_BELOW_FOG_Z ) ? 1 : 0; int numBones = pShaderAPI->GetCurrentNumBones(); bool bWriteDepthToAlpha = false; bool bWriteWaterFogToAlpha = false; if( bFullyOpaque ) { bWriteDepthToAlpha = pShaderAPI->ShouldWriteDepthToDestAlpha(); bWriteWaterFogToAlpha = (fogType == MATERIAL_FOG_LINEAR_BELOW_FOG_Z); AssertMsg( !(bWriteDepthToAlpha && bWriteWaterFogToAlpha), "Can't write two values to alpha at the same time." ); } #ifndef _X360 //if ( !g_pHardwareConfig->SupportsShaderModel_3_0() ) if ( false ) #endif { DECLARE_DYNAMIC_VERTEX_SHADER( sdk_skin_vs20 ); SET_DYNAMIC_VERTEX_SHADER_COMBO( DOWATERFOG, fogIndex ); SET_DYNAMIC_VERTEX_SHADER_COMBO( SKINNING, numBones > 0 ); SET_DYNAMIC_VERTEX_SHADER_COMBO( LIGHTING_PREVIEW, pShaderAPI->GetIntRenderingParameter(INT_RENDERPARM_ENABLE_FIXED_LIGHTING)!=0); SET_DYNAMIC_VERTEX_SHADER_COMBO( COMPRESSED_VERTS, (int)vertexCompression ); SET_DYNAMIC_VERTEX_SHADER( sdk_skin_vs20 ); DECLARE_DYNAMIC_PIXEL_SHADER( sdk_skin_ps20b ); SET_DYNAMIC_PIXEL_SHADER_COMBO( NUM_LIGHTS, lightState.m_nNumLights ); SET_DYNAMIC_PIXEL_SHADER_COMBO( WRITEWATERFOGTODESTALPHA, bWriteWaterFogToAlpha ); SET_DYNAMIC_PIXEL_SHADER_COMBO( WRITE_DEPTH_TO_DESTALPHA, bWriteDepthToAlpha ); SET_DYNAMIC_PIXEL_SHADER_COMBO( PIXELFOGTYPE, pShaderAPI->GetPixelFogCombo() ); SET_DYNAMIC_PIXEL_SHADER_COMBO( FLASHLIGHTSHADOWS, bFlashlightShadows ); SET_DYNAMIC_PIXEL_SHADER( sdk_skin_ps20b ); } #ifndef _X360 else { const bool bFastVertexTextures = g_pHardwareConfig->HasFastVertexTextures(); const int iCascadedShadowCombo = ( pCascadedDepthTexture != NULL ) ? 1 : 0; if ( bFastVertexTextures ) pShader->SetHWMorphVertexShaderState( VERTEX_SHADER_SHADER_SPECIFIC_CONST_6, VERTEX_SHADER_SHADER_SPECIFIC_CONST_7, SHADER_VERTEXTEXTURE_SAMPLER0 ); DECLARE_DYNAMIC_VERTEX_SHADER( sdk_skin_vs30 ); SET_DYNAMIC_VERTEX_SHADER_COMBO( DOWATERFOG, fogIndex ); SET_DYNAMIC_VERTEX_SHADER_COMBO( SKINNING, numBones > 0 ); SET_DYNAMIC_VERTEX_SHADER_COMBO( LIGHTING_PREVIEW, pShaderAPI->GetIntRenderingParameter(INT_RENDERPARM_ENABLE_FIXED_LIGHTING)!=0); SET_DYNAMIC_VERTEX_SHADER_COMBO( MORPHING, pShaderAPI->IsHWMorphingEnabled() && bFastVertexTextures ); SET_DYNAMIC_VERTEX_SHADER_COMBO( COMPRESSED_VERTS, (int)vertexCompression ); SET_DYNAMIC_VERTEX_SHADER_COMBO( CASCADED_SHADOW, iCascadedShadowCombo ); SET_DYNAMIC_VERTEX_SHADER( sdk_skin_vs30 ); DECLARE_DYNAMIC_PIXEL_SHADER( sdk_skin_ps30 ); SET_DYNAMIC_PIXEL_SHADER_COMBO( NUM_LIGHTS, lightState.m_nNumLights ); SET_DYNAMIC_PIXEL_SHADER_COMBO( WRITEWATERFOGTODESTALPHA, bWriteWaterFogToAlpha ); SET_DYNAMIC_PIXEL_SHADER_COMBO( WRITE_DEPTH_TO_DESTALPHA, bWriteDepthToAlpha ); SET_DYNAMIC_PIXEL_SHADER_COMBO( PIXELFOGTYPE, pShaderAPI->GetPixelFogCombo() ); SET_DYNAMIC_PIXEL_SHADER_COMBO( FLASHLIGHTSHADOWS, bFlashlightShadows ); SET_DYNAMIC_PIXEL_SHADER_COMBO( CASCADED_SHADOW, iCascadedShadowCombo ); SET_DYNAMIC_PIXEL_SHADER( sdk_skin_ps30 ); if ( bFastVertexTextures ) { bool bUnusedTexCoords[3] = { false, false, !pShaderAPI->IsHWMorphingEnabled() || !bIsDecal }; pShaderAPI->MarkUnusedVertexFields( 0, 3, bUnusedTexCoords ); } } #endif DynamicCmdsOut.SetVertexShaderTextureTransform( VERTEX_SHADER_SHADER_SPECIFIC_CONST_0, info.m_nBaseTextureTransform ); if( bHasBump ) { DynamicCmdsOut.SetVertexShaderTextureTransform( VERTEX_SHADER_SHADER_SPECIFIC_CONST_2, info.m_nBumpTransform ); } if ( hasDetailTexture ) { if ( IS_PARAM_DEFINED( info.m_nDetailTextureTransform ) ) DynamicCmdsOut.SetVertexShaderTextureScaledTransform( VERTEX_SHADER_SHADER_SPECIFIC_CONST_4, info.m_nDetailTextureTransform, info.m_nDetailScale ); else DynamicCmdsOut.SetVertexShaderTextureScaledTransform( VERTEX_SHADER_SHADER_SPECIFIC_CONST_4, info.m_nBaseTextureTransform, info.m_nDetailScale ); } pShader->SetModulationPixelShaderDynamicState_LinearColorSpace( 1 ); DynamicCmdsOut.SetPixelShaderConstant_W( PSREG_SELFILLUMTINT, info.m_nSelfIllumTint, fBlendFactor ); bool bInvertPhongMask = ( info.m_nInvertPhongMask != -1 ) && ( params[info.m_nInvertPhongMask]->GetIntValue() != 0 ); float fInvertPhongMask = bInvertPhongMask ? 1 : 0; bool bHasBaseAlphaPhongMask = (info.m_nBaseMapAlphaPhongMask != -1) && ( params[info.m_nBaseMapAlphaPhongMask]->GetIntValue() != 0 ); float fHasBaseAlphaPhongMask = bHasBaseAlphaPhongMask ? 1 : 0; // Controls for lerp-style paths through shader code const float flMinLighting = pShaderAPI->GetFloatRenderingParameter( FLOAT_RENDERPARM_MINIMUMLIGHTING ); // GSTRINGMIGRATION float vShaderControls[4] = { fHasBaseAlphaPhongMask, flMinLighting, 0.0f, fInvertPhongMask }; // GSTRINGMIGRATION DynamicCmdsOut.SetPixelShaderConstant( PSREG_CONSTANT_27, vShaderControls, 1 ); if ( hasDetailTexture ) { #if 0 // needs constant change if ( info.m_nDetailTint != -1 ) pShader->SetPixelShaderConstantGammaToLinear( 10, info.m_nDetailTint ); else { float boring_tint[4]={1,1,1,1}; pShaderAPI->SetPixelShaderConstant( 10, boring_tint, 1 ); } #endif } if ( bHasSelfIllumFresnel && !bHasFlashlight ) { float vConstScaleBiasExp[4] = { 1.0f, 0.0f, 1.0f, 0.0f }; float flMin = IS_PARAM_DEFINED( info.m_nSelfIllumFresnelMinMaxExp ) ? params[info.m_nSelfIllumFresnelMinMaxExp]->GetVecValue()[0] : 0.0f; float flMax = IS_PARAM_DEFINED( info.m_nSelfIllumFresnelMinMaxExp ) ? params[info.m_nSelfIllumFresnelMinMaxExp]->GetVecValue()[1] : 1.0f; float flExp = IS_PARAM_DEFINED( info.m_nSelfIllumFresnelMinMaxExp ) ? params[info.m_nSelfIllumFresnelMinMaxExp]->GetVecValue()[2] : 1.0f; vConstScaleBiasExp[1] = ( flMax != 0.0f ) ? ( flMin / flMax ) : 0.0f; // Bias vConstScaleBiasExp[0] = 1.0f - vConstScaleBiasExp[1]; // Scale vConstScaleBiasExp[2] = flExp; // Exp vConstScaleBiasExp[3] = flMax; // Brightness DynamicCmdsOut.SetPixelShaderConstant( PSREG_SELFILLUM_SCALE_BIAS_EXP, vConstScaleBiasExp, 1 ); } DynamicCmdsOut.SetAmbientCubeDynamicStateVertexShader(); if( !bHasFlashlight ) { if ( g_pHardwareConfig->SupportsShaderModel_3_0() ) { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER5, TEXTURE_SHADOW_NOISE_2D ); } else { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER5, TEXTURE_NORMALIZATION_CUBEMAP_SIGNED ); } // Setting .x to 1 means to apply Fresnel to env map. Setting w to 1 means use separate selfillummask float vEnvMapFresnel_SelfIllumMask[4] = {0.0f, 0.0f, 0.0f, 0.0f}; vEnvMapFresnel_SelfIllumMask[3] = bHasSelfIllumMask ? 1.0f : 0.0f; if( bHasEnvmap ) { float vEnvMapTint_MaskControl[4] = {1.0f, 1.0f, 1.0f, 0.0f}; // If we have a tint, grab it if ( (info.m_nEnvmapTint != -1) && params[info.m_nEnvmapTint]->IsDefined() ) params[info.m_nEnvmapTint]->GetVecValue(vEnvMapTint_MaskControl, 3); // Set control for source of env map mask (normal alpha or base alpha) vEnvMapTint_MaskControl[3] = bHasNormalMapAlphaEnvmapMask ? 1.0f : 0.0f; if ( (info.m_nEnvmapFresnel != -1) && params[info.m_nEnvmapFresnel]->IsDefined() ) vEnvMapFresnel_SelfIllumMask[0] = params[info.m_nEnvmapFresnel]->GetFloatValue(); // Handle mat_fullbright 2 (diffuse lighting only with 50% gamma space basetexture) if( bLightingOnly ) { vEnvMapTint_MaskControl[0] = vEnvMapTint_MaskControl[1] = vEnvMapTint_MaskControl[2] = 0.0f; } DynamicCmdsOut.SetPixelShaderConstant( PSREG_ENVMAP_TINT__SHADOW_TWEAKS, vEnvMapTint_MaskControl, 1 ); } DynamicCmdsOut.SetPixelShaderConstant( PSREG_ENVMAP_FRESNEL__SELFILLUMMASK, vEnvMapFresnel_SelfIllumMask, 1 ); } DynamicCmdsOut.SetPixelShaderStateAmbientLightCube( PSREG_AMBIENT_CUBE ); //pShaderAPI->SetPixelShaderStateAmbientLightCube( PSREG_AMBIENT_CUBE, !lightState.m_bAmbientLight ); // Force to black if not bAmbientLight // Pack Phong exponent in with the eye position float vEyePos_SpecExponent[4], vFresnelRanges_SpecBoost[4] = {0, 0.5, 1, 1}; float vSpecularTint[4] = {1, 1, 1, 4}; pShaderAPI->GetWorldSpaceCameraPosition( vEyePos_SpecExponent ); if ( (info.m_nPhongExponent != -1) && params[info.m_nPhongExponent]->IsDefined() ) vEyePos_SpecExponent[3] = params[info.m_nPhongExponent]->GetFloatValue(); // This overrides the channel in the map else vEyePos_SpecExponent[3] = 0; // Use the alpha channel of the normal map for the exponent // Get the tint parameter if ( (info.m_nPhongTint != -1) && params[info.m_nPhongTint]->IsDefined() ) { params[info.m_nPhongTint]->GetVecValue(vSpecularTint, 3); } // Get the rim light power (goes in w of Phong tint) if ( bHasRimLight && (info.m_nRimLightPower != -1) && params[info.m_nRimLightPower]->IsDefined() ) { vSpecularTint[3] = params[info.m_nRimLightPower]->GetFloatValue(); vSpecularTint[3] = max(vSpecularTint[3], 1.0f); // Make sure this is at least 1 } // Get the rim boost (goes in w of flashlight position) if ( bHasRimLight && (info.m_nRimLightBoost != -1) && params[info.m_nRimLightBoost]->IsDefined() ) { vRimBoost[3] = params[info.m_nRimLightBoost]->GetFloatValue(); } if ( !bHasFlashlight ) { float vRimMaskControl[4] = {0, 0, 0, 0}; // Only x is relevant in shader code vRimMaskControl[0] = bHasRimMaskMap ? params[info.m_nRimMask]->GetFloatValue() : 0.0f; // Rim mask...if this is true, use alpha channel of spec exponent texture to mask the rim term DynamicCmdsOut.SetPixelShaderConstant( PSREG_FLASHLIGHT_ATTENUATION, vRimMaskControl, 1 ); } // If it's all zeros, there was no constant tint in the vmt if ( (vSpecularTint[0] == 0.0f) && (vSpecularTint[1] == 0.0f) && (vSpecularTint[2] == 0.0f) ) { if ( bHasPhongTintMap ) // If we have a map to use, tell the shader { vSpecularTint[0] = -1; } else // Otherwise, just tint with white { vSpecularTint[0] = 1.0f; vSpecularTint[1] = 1.0f; vSpecularTint[2] = 1.0f; } } // handle mat_fullbright 2 (diffuse lighting only) if( bLightingOnly ) { // BASETEXTURE if( bHasSelfIllum && !bHasFlashlight ) { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER0, TEXTURE_GREY_ALPHA_ZERO ); } else { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER0, TEXTURE_GREY ); } // DETAILTEXTURE if ( hasDetailTexture ) { DynamicCmdsOut.BindStandardTexture( SHADER_SAMPLER13, TEXTURE_GREY ); } // turn off specularity vSpecularTint[0] = vSpecularTint[1] = vSpecularTint[2] = 0.0f; } if ( (info.m_nPhongFresnelRanges != -1) && params[info.m_nPhongFresnelRanges]->IsDefined() ) params[info.m_nPhongFresnelRanges]->GetVecValue( vFresnelRanges_SpecBoost, 3 ); // Grab optional Fresnel range parameters if ( (info.m_nPhongBoost != -1 ) && params[info.m_nPhongBoost]->IsDefined()) // Grab optional Phong boost param vFresnelRanges_SpecBoost[3] = params[info.m_nPhongBoost]->GetFloatValue(); else vFresnelRanges_SpecBoost[3] = 1.0f; DynamicCmdsOut.SetPixelShaderConstant( PSREG_EYEPOS_SPEC_EXPONENT, vEyePos_SpecExponent, 1 ); DynamicCmdsOut.SetPixelShaderConstant( PSREG_FRESNEL_SPEC_PARAMS, vFresnelRanges_SpecBoost, 1 ); if ( !bHasFlashlight ) { DynamicCmdsOut.SetPixelShaderConstant( PSREG_FLASHLIGHT_POSITION_RIM_BOOST, vRimBoost, 1 ); // Rim boost in w on non-flashlight pass } DynamicCmdsOut.SetPixelShaderConstant( PSREG_SPEC_RIM_PARAMS, vSpecularTint, 1 ); DynamicCmdsOut.SetPixelShaderFogParams( PSREG_FOG_PARAMS ); DynamicCmdsOut.End(); pShaderAPI->ExecuteCommandBuffer( DynamicCmdsOut.Base() ); } pShader->Draw(); }
//----------------------------------------------------------------------------- // Purpose: Predicts a single movement command for player // Input : *moveHelper - // *player - // *u - //----------------------------------------------------------------------------- void CASW_Prediction::RunCommand( C_BasePlayer *player, CUserCmd *ucmd, IMoveHelper *moveHelper ) { #if !defined( NO_ENTITY_PREDICTION ) VPROF( "CPrediction::RunCommand" ); #if defined( _DEBUG ) char sz[ 32 ]; Q_snprintf( sz, sizeof( sz ), "runcommand%04d", ucmd->command_number ); PREDICTION_TRACKVALUECHANGESCOPE( sz ); #endif C_ASW_Player *pASWPlayer = (C_ASW_Player*)player; Assert( pASWPlayer ); StartCommand( player, ucmd ); pASWPlayer->SetHighlightEntity( C_BaseEntity::Instance( ucmd->crosshair_entity ) ); // Set globals appropriately gpGlobals->curtime = player->m_nTickBase * TICK_INTERVAL; gpGlobals->frametime = TICK_INTERVAL; g_pGameMovement->StartTrackPredictionErrors( player ); // TODO // TODO: Check for impulse predicted? // Do weapon selection if ( ucmd->weaponselect != 0 ) { C_BaseCombatWeapon *weapon = dynamic_cast< C_BaseCombatWeapon * >( CBaseEntity::Instance( ucmd->weaponselect ) ); if (weapon) { pASWPlayer->ASWSelectWeapon(weapon, 0); //ucmd->weaponsubtype); // asw - subtype var used for sending marine profile index instead } } // Latch in impulse. IClientVehicle *pVehicle = player->GetVehicle(); if ( ucmd->impulse ) { // Discard impulse commands unless the vehicle allows them. // FIXME: UsingStandardWeapons seems like a bad filter for this. // The flashlight is an impulse command, for example. if ( !pVehicle || player->UsingStandardWeaponsInVehicle() ) { player->m_nImpulse = ucmd->impulse; } } // Get button states player->UpdateButtonState( ucmd->buttons ); // TODO // CheckMovingGround( player, ucmd->frametime ); // TODO // g_pMoveData->m_vecOldAngles = player->pl.v_angle; // Copy from command to player unless game .dll has set angle using fixangle // if ( !player->pl.fixangle ) { player->SetLocalViewAngles( ucmd->viewangles ); } // Call standard client pre-think RunPreThink( player ); // Call Think if one is set RunThink( player, TICK_INTERVAL ); // Setup input. { SetupMove( player, ucmd, moveHelper, g_pMoveData ); } // Run regular player movement if we're not controlling a marine if ( asw_allow_detach.GetBool() ) { if ( !pVehicle ) { Assert( g_pGameMovement ); g_pGameMovement->ProcessMovement( player, g_pMoveData ); } else { pVehicle->ProcessMovement( player, g_pMoveData ); } } // if ( !asw_allow_detach.GetBool() && pASWPlayer->GetMarine() ) // { // g_pMoveData->SetAbsOrigin( pASWPlayer->GetMarine()->GetAbsOrigin() ); // } pASWPlayer->SetCrosshairTracePos( ucmd->crosshairtrace ); FinishMove( player, ucmd, g_pMoveData ); RunPostThink( player ); // let the player drive marine movement here pASWPlayer->DriveMarineMovement( ucmd, moveHelper ); g_pGameMovement->FinishTrackPredictionErrors( player ); FinishCommand( player ); player->m_nTickBase++; #endif }
void C_PlantedC4::ClientThink( void ) { BaseClass::ClientThink(); // If it's dormant, don't beep or anything.. if ( IsDormant() ) return; if ( !m_bBombTicking ) { // disbale C4 thinking if not armed SetNextClientThink( CLIENT_THINK_NEVER ); return; } if( gpGlobals->curtime > m_flNextBeep ) { // as it gets closer to going off, increase the radius CLocalPlayerFilter filter; float attenuation; float freq; //the percent complete of the bomb timer float fComplete = ( ( m_flC4Blow - gpGlobals->curtime ) / m_flTimerLength ); fComplete = clamp( fComplete, 0.0f, 1.0f ); attenuation = min( 0.3 + 0.6 * fComplete, 1.0 ); CSoundParameters params; if ( GetParametersForSound( "C4.PlantSound", params, NULL ) ) { EmitSound_t ep( params ); ep.m_SoundLevel = ATTN_TO_SNDLVL( attenuation ); ep.m_pOrigin = &GetAbsOrigin(); EmitSound( filter, SOUND_FROM_WORLD, ep ); } freq = max( 0.1 + 0.9 * fComplete, 0.15 ); m_flNextBeep = gpGlobals->curtime + freq; } if( gpGlobals->curtime > m_flNextGlow ) { int modelindex = modelinfo->GetModelIndex( "sprites/ledglow.vmt" ); float scale = 0.8f; Vector vPos = GetAbsOrigin(); const Vector offset( 0, 0, 4 ); // See if the c4 ended up underwater - we need to pull the flash up, or it won't get seen if ( enginetrace->GetPointContents( vPos ) & (CONTENTS_WATER|CONTENTS_SLIME) ) { C_CSPlayer *player = GetLocalOrInEyeCSPlayer(); if ( player ) { const Vector& eyes = player->EyePosition(); if ( ( enginetrace->GetPointContents( eyes ) & (CONTENTS_WATER|CONTENTS_SLIME) ) == 0 ) { // trace from the player to the water trace_t waterTrace; UTIL_TraceLine( eyes, vPos, (CONTENTS_WATER|CONTENTS_SLIME), player, COLLISION_GROUP_NONE, &waterTrace ); if( waterTrace.allsolid != 1 ) { // now trace from the C4 to the edge of the water (in case there was something solid in the water) trace_t solidTrace; UTIL_TraceLine( vPos, waterTrace.endpos, MASK_SOLID, this, COLLISION_GROUP_NONE, &solidTrace ); if( solidTrace.allsolid != 1 ) { float waterDist = (solidTrace.endpos - vPos).Length(); float remainingDist = (solidTrace.endpos - eyes).Length(); scale = scale * remainingDist / ( remainingDist + waterDist ); vPos = solidTrace.endpos; } } } } } vPos += offset; tempents->TempSprite( vPos, vec3_origin, scale, modelindex, kRenderTransAdd, 0, 1.0, 0.05, FTENT_SPRANIMATE | FTENT_SPRANIMATELOOP ); if( cl_c4dynamiclight.GetBool() ) { dlight_t *dl; dl = effects->CL_AllocDlight( entindex() ); if( dl ) { dl->origin = GetAbsOrigin() + offset; // can't use vPos because it might have been moved dl->color.r = 255; dl->color.g = 0; dl->color.b = 0; dl->radius = 64; dl->die = gpGlobals->curtime + 0.01; } } float freq = 0.1 + 0.9 * ( ( m_flC4Blow - gpGlobals->curtime ) / m_flTimerLength ); if( freq < 0.15 ) freq = 0.15; m_flNextGlow = gpGlobals->curtime + freq; } }
void VrController::update(float previousViewYaw) { if (_vrIO->getChannelCount() == 0) { //todo: check vrIO state Msg("Trackers not initialized properly, nothing to do here...\n"); return; } VRIO_Message message; _vrIO->think(); VRIO_Channel headChannel = HEAD; VRIO_Channel weaponChannel = WEAPON; if ( vr_swap_trackers.GetBool() ) { headChannel = WEAPON; weaponChannel = HEAD; } // HEAD ORIENTATION _vrIO->getOrientation(headChannel, message); _headAngle[PITCH] = message.pitch; _headAngle[ROLL] = message.roll; _headAngle[YAW] = message.yaw; float previousYaw = _previousYaw[HEAD]; float currentYaw = _headAngle[YAW]; float deltaYaw = currentYaw - previousYaw; _headAngle[YAW] = deltaYaw + previousViewYaw; _previousYaw[HEAD] = currentYaw; _totalAccumulatedYaw[HEAD] += deltaYaw; _headAngle -= _headCalibration; // BODY ORIENTATION VectorCopy(_headAngle, _bodyAngle); _bodyAngle[YAW] = previousViewYaw - _totalAccumulatedYaw[HEAD]; // this gives us the global original value // if uninitialized, set initial body calibration if (_bodyCalibration[YAW] < 0) { _bodyCalibration[YAW] = -_totalAccumulatedYaw[HEAD]; } _bodyAngle -= _bodyCalibration; // WEAPON ORIENTATION if (!hasWeaponTracking()) { VectorCopy(_headAngle, _weaponAngle); return; } _vrIO->getOrientation(weaponChannel, message); _weaponAngle[PITCH] = message.pitch; _weaponAngle[ROLL] = message.roll; _weaponAngle[YAW] = message.yaw; previousYaw = _previousYaw[WEAPON]; currentYaw = _weaponAngle[YAW]; deltaYaw = currentYaw - previousYaw; _previousYaw[WEAPON] = currentYaw; _totalAccumulatedYaw[WEAPON] += deltaYaw; _weaponAngle[YAW] = previousViewYaw + _totalAccumulatedYaw[WEAPON] - _totalAccumulatedYaw[HEAD]; _weaponAngle -= _weaponCalibration; };
bool CDODBipodWeapon::TestDeployAngle( CDODPlayer *pPlayer, float *flDeployedHeight, CBaseEntity **pDeployedOn, QAngle angles ) { // make sure we are deployed on the same entity at the same height trace_t tr; angles[PITCH] = 0; Vector forward, right, up; AngleVectors( angles, &forward, &right, &up ); // start at top of player bbox Vector vecStart = pPlayer->GetAbsOrigin(); float flForwardTraceDist = 32; // check us as ducking if we are ducked, or if were ducked when we were deployed bool bDucking = pPlayer->m_Shared.IsDucking() || ( IsDeployed() && m_bDuckedWhenDeployed ); if ( pPlayer->m_Shared.IsProne() ) { vecStart.z += VEC_PRONE_HULL_MAX[2]; flForwardTraceDist = 16; } else if ( bDucking ) { vecStart.z += VEC_DUCK_HULL_MAX[2]; } else { vecStart.z += 60; } int dim = 1; // dod_deploy_box_size.GetInt(); Vector vecDeployTraceBoxSize( dim, dim, dim ); vecStart.z -= vecDeployTraceBoxSize[2]; vecStart.z -= 4; // sandbags are around 50 units high. Shouldn't be able to deploy on anything a lot higher than that // optimal standing height ( for animation's sake ) is around 42 units // optimal ducking height is around 20 units ( 20 unit high object, plus 8 units of gun ) // Start one half box width away from the edge of the player hull Vector vecForwardStart = vecStart + forward * ( VEC_HULL_MAX[0] + vecDeployTraceBoxSize[0] ); int traceMask = MASK_SOLID; CBaseEntity *pDeployedOnPlayer = NULL; if ( m_hDeployedOnEnt && m_hDeployedOnEnt->IsPlayer() ) { pDeployedOnPlayer = m_hDeployedOnEnt.Get(); } CTraceFilterIgnorePlayersExceptFor deployedFilter( pDeployedOnPlayer, COLLISION_GROUP_NONE ); CTraceFilterSimple undeployedFilter( pPlayer, COLLISION_GROUP_NONE ); // if we're deployed, skip all players except for the deployed on player // if we're not, only skip ourselves ITraceFilter *filter; if ( IsDeployed() ) filter = &deployedFilter; else filter = &undeployedFilter; UTIL_TraceHull( vecForwardStart, vecForwardStart + forward * ( flForwardTraceDist - 2 * vecDeployTraceBoxSize[0] ), -vecDeployTraceBoxSize, vecDeployTraceBoxSize, traceMask, filter, &tr ); #ifndef CLIENT_DLL if ( dod_debugmgdeploy.GetBool() ) { NDebugOverlay::Line( vecForwardStart, vecForwardStart + forward * ( flForwardTraceDist - 2 * vecDeployTraceBoxSize[0] ), 0, 0, 255, true, 0.1 ); NDebugOverlay::Box( vecForwardStart, -vecDeployTraceBoxSize, vecDeployTraceBoxSize, 255, 0, 0, 128, 0.1 ); NDebugOverlay::Box( tr.endpos, -vecDeployTraceBoxSize, vecDeployTraceBoxSize, 0, 0, 255, 128, 0.1 ); } #endif // Test forward, are we trying to deploy into a solid object? if ( tr.fraction < 1.0 ) { return false; } // If we're prone, we can always deploy, don't do the ground test if ( pPlayer->m_Shared.IsProne() && !pPlayer->m_Shared.IsGettingUpFromProne() ) { // MATTTODO: do trace from *front* of player, not from the edge of crouch hull // this is sufficient *flDeployedHeight = PRONE_DEPLOY_HEIGHT; return true; } // fix prediction hitch when coming up from prone. client thinks we aren't // prone, but hull is still prone hull // assumes prone hull is shorter than duck hull! if ( pPlayer->WorldAlignMaxs().z <= VEC_PRONE_HULL_MAX.z ) return false; // Else trace down Vector vecDownTraceStart = vecStart + forward * ( VEC_HULL_MAX[0] + DEPLOY_DOWNTRACE_FORWARD_DIST ); int iTraceHeight = -( pPlayer->WorldAlignMaxs().z ); // search down from the forward trace // use the farthest point first. If that fails, move towards the player a few times // to see if they are trying to deploy on a thin railing bool bFound = false; int maxAttempts = 4; float flHighestTraceEnd = vecDownTraceStart.z + iTraceHeight; CBaseEntity *pBestDeployEnt = NULL; while( maxAttempts > 0 ) { UTIL_TraceHull( vecDownTraceStart, vecDownTraceStart + Vector(0,0,iTraceHeight), // trace forward one box width -vecDeployTraceBoxSize, vecDeployTraceBoxSize, traceMask, filter, &tr ); #ifndef CLIENT_DLL if ( dod_debugmgdeploy.GetBool() ) { NDebugOverlay::Line( vecDownTraceStart, tr.endpos, 255, 0, 0, true, 0.1 ); NDebugOverlay::Box( vecDownTraceStart, -vecDeployTraceBoxSize, vecDeployTraceBoxSize, 255, 0, 0, 128, 0.1 ); NDebugOverlay::Box( tr.endpos, -vecDeployTraceBoxSize, vecDeployTraceBoxSize, 0, 0, 255, 128, 0.1 ); } #endif bool bSuccess = ( tr.fraction < 1.0 ) && !tr.startsolid && !tr.allsolid; // if this is the first one found, set found flag if ( bSuccess && !bFound ) { bFound = true; } else if ( bFound == true && bSuccess == false ) { // it failed and we have some data. break here break; } // if this trace is better ( higher ) use this one if ( tr.endpos.z > flHighestTraceEnd ) { flHighestTraceEnd = tr.endpos.z; pBestDeployEnt = tr.m_pEnt; } --maxAttempts; // move towards the player, looking for a better height to deploy on vecDownTraceStart += forward * -4; } if ( bFound == false || pBestDeployEnt == NULL ) return false; *pDeployedOn = pBestDeployEnt; *flDeployedHeight = flHighestTraceEnd - vecDeployTraceBoxSize[0] + DEPLOY_DOWNTRACE_OFFSET - pPlayer->GetAbsOrigin().z; return true; }
//----------------------------------------------------------------------------- // Sets up the view parameters //----------------------------------------------------------------------------- void CViewRender::SetUpViews() { VPROF("CViewRender::SetUpViews"); // Initialize view structure with default values float farZ = GetZFar(); // Set up the mono/middle view. CViewSetup &view = m_View; view.zFar = farZ; view.zFarViewmodel = farZ; // UNDONE: Make this farther out? // closest point of approach seems to be view center to top of crouched box view.zNear = GetZNear(); view.zNearViewmodel = 1; view.fov = default_fov.GetFloat(); view.m_bOrtho = false; view.m_bViewToProjectionOverride = false; view.m_eStereoEye = STEREO_EYE_MONO; // Enable spatial partition access to edicts partition->SuppressLists( PARTITION_ALL_CLIENT_EDICTS, false ); C_BasePlayer *pPlayer = C_BasePlayer::GetLocalPlayer(); // You in-view weapon aim. bool bCalcViewModelView = false; Vector ViewModelOrigin; QAngle ViewModelAngles; if ( engine->IsHLTV() ) { HLTVCamera()->CalcView( view.origin, view.angles, view.fov ); } #if defined( REPLAY_ENABLED ) else if ( g_pEngineClientReplay->IsPlayingReplayDemo() ) { ReplayCamera()->CalcView( view.origin, view.angles, view.fov ); } #endif else { // FIXME: Are there multiple views? If so, then what? // FIXME: What happens when there's no player? if (pPlayer) { pPlayer->CalcView( view.origin, view.angles, view.zNear, view.zFar, view.fov ); // If we are looking through another entities eyes, then override the angles/origin for view int viewentity = render->GetViewEntity(); if ( !g_nKillCamMode && (pPlayer->entindex() != viewentity) ) { C_BaseEntity *ve = cl_entitylist->GetEnt( viewentity ); if ( ve ) { VectorCopy( ve->GetAbsOrigin(), view.origin ); VectorCopy( ve->GetAbsAngles(), view.angles ); } } // There is a viewmodel. bCalcViewModelView = true; ViewModelOrigin = view.origin; ViewModelAngles = view.angles; } else { view.origin.Init(); view.angles.Init(); } // Even if the engine is paused need to override the view // for keeping the camera control during pause. g_pClientMode->OverrideView( &view ); } // give the toolsystem a chance to override the view ToolFramework_SetupEngineView( view.origin, view.angles, view.fov ); if ( engine->IsPlayingDemo() ) { if ( cl_demoviewoverride.GetFloat() > 0.0f ) { // Retreive view angles from engine ( could have been set in IN_AdjustAngles above ) CalcDemoViewOverride( view.origin, view.angles ); } else { s_DemoView = view.origin; s_DemoAngle = view.angles; } } //Find the offset our current FOV is from the default value float fDefaultFov = default_fov.GetFloat(); float flFOVOffset = fDefaultFov - view.fov; //Adjust the viewmodel's FOV to move with any FOV offsets on the viewer's end view.fovViewmodel = g_pClientMode->GetViewModelFOV() - flFOVOffset; if ( g_pGstringGlobals && g_pGstringGlobals->IsSpaceMap() ) { view.fovViewmodel = v_viewmodel_fov_space.GetFloat(); } view.fovViewmodel = MAX(1, view.fovViewmodel); if ( UseVR() ) { // Let the headtracking read the status of the HMD, etc. // This call can go almost anywhere, but it needs to know the player FOV for sniper weapon zoom, etc if ( flFOVOffset == 0.0f ) { g_ClientVirtualReality.ProcessCurrentTrackingState ( 0.0f ); } else { g_ClientVirtualReality.ProcessCurrentTrackingState ( view.fov ); } HeadtrackMovementMode_t hmmOverrideMode = g_pClientMode->ShouldOverrideHeadtrackControl(); g_ClientVirtualReality.OverrideView( &m_View, &ViewModelOrigin, &ViewModelAngles, hmmOverrideMode ); // left and right stereo views should default to being the same as the mono/middle view m_ViewLeft = m_View; m_ViewRight = m_View; m_ViewLeft.m_eStereoEye = STEREO_EYE_LEFT; m_ViewRight.m_eStereoEye = STEREO_EYE_RIGHT; g_ClientVirtualReality.OverrideStereoView( &m_View, &m_ViewLeft, &m_ViewRight ); } else { // left and right stereo views should default to being the same as the mono/middle view m_ViewLeft = m_View; m_ViewRight = m_View; m_ViewLeft.m_eStereoEye = STEREO_EYE_LEFT; m_ViewRight.m_eStereoEye = STEREO_EYE_RIGHT; } if ( bCalcViewModelView ) { Assert ( pPlayer != NULL ); pPlayer->CalcViewModelView ( ViewModelOrigin, ViewModelAngles ); } // Disable spatial partition access partition->SuppressLists( PARTITION_ALL_CLIENT_EDICTS, true ); // Enable access to all model bones C_BaseAnimating::PopBoneAccess( "OnRenderStart->CViewRender::SetUpView" ); // pops the (true, false) bone access set in OnRenderStart C_BaseAnimating::PushAllowBoneAccess( true, true, "CViewRender::SetUpView->OnRenderEnd" ); // pop is in OnRenderEnd() // Compute the world->main camera transform // This is only done for the main "middle-eye" view, not for the various other views. ComputeCameraVariables( view.origin, view.angles, &g_vecVForward, &g_vecVRight, &g_vecVUp, &g_matCamInverse ); // set up the hearing origin... AudioState_t audioState; audioState.m_Origin = view.origin; audioState.m_Angles = view.angles; audioState.m_bIsUnderwater = pPlayer && pPlayer->AudioStateIsUnderwater( view.origin ); ToolFramework_SetupAudioState( audioState ); // TomF: I wonder when the audio tools modify this, if ever... Assert ( view.origin == audioState.m_Origin ); Assert ( view.angles == audioState.m_Angles ); view.origin = audioState.m_Origin; view.angles = audioState.m_Angles; engine->SetAudioState( audioState ); g_vecPrevRenderOrigin = g_vecRenderOrigin; g_vecPrevRenderAngles = g_vecRenderAngles; g_vecRenderOrigin = view.origin; g_vecRenderAngles = view.angles; #ifdef DBGFLAG_ASSERT s_DbgSetupOrigin = view.origin; s_DbgSetupAngles = view.angles; #endif }
//----------------------------------------------------------------------------- // Purpose: Moves the client pitch angle towards cl.idealpitch sent by the server. // If the user is adjusting pitch manually, either with lookup/lookdown, // mlook and mouse, or klook and keyboard, pitch drifting is constantly stopped. //----------------------------------------------------------------------------- void CViewRender::DriftPitch (void) { float delta, move; C_BasePlayer *player = C_BasePlayer::GetLocalPlayer(); if ( !player ) return; #if defined( REPLAY_ENABLED ) if ( engine->IsHLTV() || g_pEngineClientReplay->IsPlayingReplayDemo() || ( player->GetGroundEntity() == NULL ) || engine->IsPlayingDemo() ) #else if ( engine->IsHLTV() || ( player->GetGroundEntity() == NULL ) || engine->IsPlayingDemo() ) #endif { m_PitchDrift.driftmove = 0; m_PitchDrift.pitchvel = 0; return; } // Don't count small mouse motion if ( m_PitchDrift.nodrift ) { if ( fabs( input->GetLastForwardMove() ) < cl_forwardspeed.GetFloat() ) { m_PitchDrift.driftmove = 0; } else { m_PitchDrift.driftmove += gpGlobals->frametime; } if ( m_PitchDrift.driftmove > v_centermove.GetFloat() ) { StartPitchDrift (); } return; } // How far off are we delta = prediction->GetIdealPitch() - player->GetAbsAngles()[ PITCH ]; if ( !delta ) { m_PitchDrift.pitchvel = 0; return; } // Determine movement amount move = gpGlobals->frametime * m_PitchDrift.pitchvel; // Accelerate m_PitchDrift.pitchvel += gpGlobals->frametime * v_centerspeed.GetFloat(); // Move predicted pitch appropriately if (delta > 0) { if ( move > delta ) { m_PitchDrift.pitchvel = 0; move = delta; } player->SetLocalAngles( player->GetLocalAngles() + QAngle( move, 0, 0 ) ); } else if ( delta < 0 ) { if ( move > -delta ) { m_PitchDrift.pitchvel = 0; move = -delta; } player->SetLocalAngles( player->GetLocalAngles() - QAngle( move, 0, 0 ) ); } }
//----------------------------------------------------------------------------- // Step iteratively toward a destination position //----------------------------------------------------------------------------- AIMotorMoveResult_t CAI_Motor::MoveGroundStep( const Vector &newPos, CBaseEntity *pMoveTarget, float yaw, bool bAsFarAsCan, bool bTestZ, AIMoveTrace_t *pTraceResult ) { // By definition, this will produce different results than GroundMoveLimit() // because there's no guarantee that it will step exactly one step // See how far toward the new position we can step... // But don't actually test for ground geometric validity; // if it isn't valid, there's not much we can do about it AIMoveTrace_t moveTrace; unsigned testFlags = AITGM_IGNORE_FLOOR; if ( !bTestZ ) testFlags |= AITGM_2D; #ifdef DEBUG if ( ai_draw_motor_movement.GetBool() ) testFlags |= AITGM_DRAW_RESULTS; #endif GetMoveProbe()->TestGroundMove( GetLocalOrigin(), newPos, MASK_NPCSOLID, testFlags, &moveTrace ); if ( pTraceResult ) { *pTraceResult = moveTrace; } bool bHitTarget = (moveTrace.pObstruction && (pMoveTarget == moveTrace.pObstruction )); // Move forward either if there was no obstruction or if we're told to // move as far as we can, regardless bool bIsBlocked = IsMoveBlocked(moveTrace.fStatus); if ( !bIsBlocked || bAsFarAsCan || bHitTarget ) { #ifdef DEBUG if ( GetMoveProbe()->CheckStandPosition( GetLocalOrigin(), MASK_NPCSOLID ) && !GetMoveProbe()->CheckStandPosition( moveTrace.vEndPosition, MASK_NPCSOLID ) ) { DevMsg( 2, "Warning: AI motor probably given invalid instructions\n" ); } #endif // The true argument here causes it to touch all triggers // in the volume swept from the previous position to the current position UTIL_SetOrigin(GetOuter(), moveTrace.vEndPosition, true); // check to see if our ground entity has changed // NOTE: This is to detect changes in ground entity as the movement code has optimized out // ground checks. So now we have to do a simple recheck to make sure we detect when we've // stepped onto a new entity. if ( GetOuter()->GetFlags() & FL_ONGROUND ) { GetOuter()->PhysicsStepRecheckGround(); } // skip tiny steps, but notify the shadow object of any large steps if ( moveTrace.flStepUpDistance > 0.1f ) { float height = clamp( moveTrace.flStepUpDistance, 0, StepHeight() ); IPhysicsObject *pPhysicsObject = GetOuter()->VPhysicsGetObject(); if ( pPhysicsObject ) { IPhysicsShadowController *pShadow = pPhysicsObject->GetShadowController(); if ( pShadow ) { pShadow->StepUp( height ); } } } if ( yaw != -1 ) { QAngle angles = GetLocalAngles(); angles.y = yaw; SetLocalAngles( angles ); } if ( bHitTarget ) return AIM_PARTIAL_HIT_TARGET; if ( !bIsBlocked ) return AIM_SUCCESS; if ( moveTrace.fStatus == AIMR_BLOCKED_NPC ) return AIM_PARTIAL_HIT_NPC; return AIM_PARTIAL_HIT_WORLD; } return AIM_FAILED; }
void CASW_Prediction::CheckMarineError( int nSlot, int commands_acknowledged ) { C_ASW_Player *player; Vector origin; Vector delta; float len; static int pos = 0; // Not in the game yet if ( !engine->IsInGame() ) return; // Not running prediction if ( !cl_predict->GetInt() ) return; player = C_ASW_Player::GetLocalASWPlayer( nSlot ); if ( !player ) return; C_ASW_Marine* pMarine = player->GetMarine(); if (!pMarine) return; // Not predictable yet (flush entity packet?) if ( !pMarine->IsIntermediateDataAllocated() ) return; origin = pMarine->GetNetworkOrigin(); const void *slot = pMarine->GetPredictedFrame( commands_acknowledged - 1 ); if ( !slot ) return; if ( !m_bMarineOriginTypedescriptionSearched ) { m_bMarineOriginTypedescriptionSearched = true; const typedescription_t *td = CPredictionCopy::FindFlatFieldByName( "m_vecNetworkOrigin", pMarine->GetPredDescMap() ); if ( td ) { m_MarineOriginTypeDescription.AddToTail( td ); } } if ( !m_MarineOriginTypeDescription.Count() ) return; Vector predicted_origin; memcpy( (Vector *)&predicted_origin, (Vector *)( (byte *)slot + m_MarineOriginTypeDescription[ 0 ]->flatOffset[ TD_OFFSET_PACKED ] ), sizeof( Vector ) ); // Compare what the server returned with what we had predicted it to be VectorSubtract ( predicted_origin, origin, delta ); len = VectorLength( delta ); if (len > MAX_PREDICTION_ERROR ) { // A teleport or something, clear out error len = 0; } else { if ( len > MIN_PREDICTION_EPSILON ) { pMarine->NotePredictionError( delta ); if ( cl_showerror.GetInt() >= 1 ) { con_nprint_t np; np.fixed_width_font = true; np.color[0] = 1.0f; np.color[1] = 0.95f; np.color[2] = 0.7f; np.index = 20 + ( ++pos % 20 ); np.time_to_live = 2.0f; engine->Con_NXPrintf( &np, "marine pred error %6.3f units (%6.3f %6.3f %6.3f)", len, delta.x, delta.y, delta.z ); } } } }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- CObjectResupply::CObjectResupply() { m_iHealth = obj_resupply_health.GetInt(); UseClientSideAnimation(); }
void ModelPoseDebugInfo::AddInfoText( InfoText *x, ModelPoseDebugInfo *pOld ) { if ( x ) { // Try to set the proper flags on the info text x->m_uiFlags &= ~F_SEEN_LAST_FRAME; x->m_uiFlags |= F_SEEN_THIS_FRAME; } // If we have smth to compare against if ( pOld ) { // Search for the same activity/label in the other model pose debug info ModelPoseDebugInfo &o = *pOld; int k = o.m_iCurrentText; if ( x ) { for ( ; k < o.m_arrTxt.Count(); ++ k ) { InfoText &txt = o.m_arrTxt[k]; if ( ( txt.m_uiFlags & F_SEEN_THIS_FRAME ) && !stricmp( x->m_chActivity, txt.m_chActivity ) && !stricmp( x->m_chLabel, txt.m_chLabel ) && ( x->m_iActivity == txt.m_iActivity ) ) { x->m_flTimeAlive = txt.m_flTimeAlive; break; } } } else { k = o.m_arrTxt.Count(); } // Range of finished activities int iFinishedRange[2] = { o.m_iCurrentText, k }; // Check whether this is a new message if ( k == o.m_arrTxt.Count() ) { if ( !x ) { o.m_iCurrentText = k; } else { // Don't update the current when insertion happens and don't have finished commands iFinishedRange[1] = iFinishedRange[0]; } } else { o.m_iCurrentText = k + 1; if ( x ) { x->m_uiFlags |= F_SEEN_LAST_FRAME; x->m_flTimeAlive += gpGlobals->frametime; } } // Everything before finished for ( int iFinished = iFinishedRange[0]; iFinished < iFinishedRange[1]; ++ iFinished ) { InfoText &txtFinished = o.m_arrTxt[ iFinished ]; if ( txtFinished.m_uiFlags & F_SEEN_THIS_FRAME ) txtFinished.m_uiFlags |= F_SEEN_LAST_FRAME; txtFinished.m_uiFlags &= ~F_SEEN_THIS_FRAME; txtFinished.m_flTimeToLive -= gpGlobals->frametime; txtFinished.m_flTimeAlive += gpGlobals->frametime; if ( txtFinished.m_flTimeToLive >= 0.0f ) m_arrTxt.AddToTail( txtFinished ); } } if ( x ) { // Now add it to the array x->m_flTimeToLive = ui_posedebug_fade_out_time.GetFloat(); m_arrTxt.AddToTail( *x ); } }
void CASWHudCrosshair::PaintReloadProgressBar( void ) { if ( !engine->IsActiveApp() ) { m_pAmmoProgress->SetVisible( false ); m_pFastReloadBar->SetVisible( false ); return; } C_ASW_Player* pPlayer = C_ASW_Player::GetLocalASWPlayer(); if ( !pPlayer ) return; C_ASW_Marine* pMarine = pPlayer->GetMarine(); if ( !pMarine ) return; C_ASW_Weapon* pWeapon = pMarine->GetActiveASWWeapon(); if ( !pWeapon || !asw_crosshair_use_perspective.GetBool() ) { m_pAmmoProgress->SetVisible( false ); m_pFastReloadBar->SetVisible( false ); return; } int x, y; GetCurrentPos( x, y ); int nCrosshair = GetCurrentCrosshair( x, y ); if ( pWeapon && pWeapon->IsReloading() ) { m_bIsReloading = true; float flProgress = 0.0; float fStart = pWeapon->m_fReloadStart; float fNext = pWeapon->m_flNextPrimaryAttack; float fTotalTime = fNext - fStart; if (fTotalTime <= 0) fTotalTime = 0.1f; // if we're in single player, the progress code in the weapon doesn't run on the client because we aren't predicting if ( !cl_predict->GetInt() ) flProgress = RescaleProgessForArt( (gpGlobals->curtime - fStart) / fTotalTime ); else flProgress = RescaleProgessForArt( pWeapon->m_fReloadProgress ); if ((int(gpGlobals->curtime*10) % 2) == 0) m_pAmmoProgress->SetFgColor( Color( 215, 205, 80, 255) ); else m_pAmmoProgress->SetFgColor( Color( 175, 80, 80, 255) ); if ( asw_fast_reload_enabled.GetBool() ) { m_pFastReloadBar->SetFgColor( Color( 235, 235, 235, 100) ); m_pFastReloadBar->SetBgColor( Color( 0, 0, 0, 0 ) ); // fractions of ammo wide for fast reload start/end float fFastStart = RescaleProgessForArt( (pWeapon->m_fFastReloadStart - fStart) / fTotalTime ); float fFastEnd = RescaleProgessForArt( (pWeapon->m_fFastReloadEnd - fStart) / fTotalTime ); m_pFastReloadBar->SetStartProgress( fFastStart ); m_pFastReloadBar->SetProgress( fFastEnd ); m_pFastReloadBar->SetVisible( true ); } m_pAmmoProgress->SetProgress( flProgress ); m_pAmmoProgress->SetAlpha( 255 ); m_pAmmoProgress->SetBgColor( Color( 100, 100, 100, 160*m_pAmmoProgress->GetScale() ) ); m_pAmmoProgress->SetVisible( true ); } /*else if ( m_bIsReloading ) { m_bIsReloading = false; m_pAmmoProgress->SetFgColor( Color( 200, 200, 200, 255 ) ); m_pAmmoProgress->SetProgress( 1.0 ); vgui::GetAnimationController()->RunAnimationCommand( m_pAmmoProgress, "alpha", 0, 0, 0.5f, vgui::AnimationController::INTERPOLATOR_ACCEL ); } */ else { float flScale = m_pAmmoProgress->GetScale(); m_bIsReloading = false; m_pAmmoProgress->SetFgColor( Color( 220, 220, 220, 140*flScale ) ); m_pFastReloadBar->SetVisible( false ); int nClip1 = pWeapon->Clip1(); if ( nClip1 < 0 ) { m_pAmmoProgress->SetVisible( false ); return; } float flProgress = RescaleProgessForArt( float(nClip1) / float(pWeapon->GetMaxClip1()) ); m_pAmmoProgress->SetProgress( flProgress ); if ( flProgress < 0.25 && (int(gpGlobals->curtime*10) % 2) == 0 ) { m_pAmmoProgress->SetBgColor( Color( 130, 90, 50, 160*flScale ) ); } else { m_pAmmoProgress->SetBgColor( Color( 80, 80, 80, 130*flScale ) ); } m_pAmmoProgress->SetVisible( !pPlayer->IsSniperScopeActive() && nCrosshair == m_nCrosshairTexture ); } };
void ModelPoseDebugInfo::PrintPendingInfoText( int &rnPosPrint ) { con_nprint_s nxPrn = { 0 }; nxPrn.time_to_live = -1; nxPrn.color[0] = 1.0f, nxPrn.color[1] = 1.0f, nxPrn.color[2] = 1.0f; nxPrn.fixed_width_font = true; float const flFadeInTime = ui_posedebug_fade_in_time.GetFloat(); float const flFadeOutTime = ui_posedebug_fade_out_time.GetFloat(); // Now print all the accumulated spew for ( int k = m_iCurrentText; k < m_arrTxt.Count(); ++ k ) { InfoText &prntxt = m_arrTxt[k]; switch( prntxt.m_uiFlags & ( F_SEEN_LAST_FRAME | F_SEEN_THIS_FRAME ) ) { case ( F_SEEN_LAST_FRAME | F_SEEN_THIS_FRAME ) : nxPrn.color[0] = 1.f; nxPrn.color[1] = 1.f; nxPrn.color[2] = 1.f; if ( prntxt.m_flTimeAlive > flFadeInTime ) break; else NULL; // Fall-through to keep showing in green case F_SEEN_THIS_FRAME : if ( flFadeInTime > 0.f ) { nxPrn.color[0] = 1.f * prntxt.m_flTimeAlive / flFadeInTime; nxPrn.color[1] = 1.f; nxPrn.color[2] = 1.f * prntxt.m_flTimeAlive / flFadeInTime; } else { nxPrn.color[0] = ( prntxt.m_flTimeAlive > 0.0f ) ? 1.f : 0.f; nxPrn.color[1] = 1.f; nxPrn.color[2] = ( prntxt.m_flTimeAlive > 0.0f ) ? 1.f : 0.f; } break; case F_SEEN_LAST_FRAME : case 0: if ( flFadeOutTime > 0.f ) nxPrn.color[0] = 1.f * prntxt.m_flTimeToLive / flFadeOutTime; else nxPrn.color[0] = ( prntxt.m_flTimeToLive > 0.0f ) ? 1.f : 0.f; nxPrn.color[1] = 0.f; nxPrn.color[2] = 0.f; break; } nxPrn.index = ( rnPosPrint += 1 ); engine->Con_NXPrintf( &nxPrn, "%s", prntxt.m_chTextLines[0] ); for ( int iLine = 1; iLine < ModelPoseDebugInfo::InfoText::MAX_TEXT_LINES; ++ iLine) { if ( !prntxt.m_chTextLines[iLine][0] ) break; nxPrn.index = ( rnPosPrint += 1 ); engine->Con_NXPrintf( &nxPrn, "%s", prntxt.m_chTextLines[iLine] ); } } m_iCurrentText = m_arrTxt.Count(); }
void CASWHudCrosshair::DrawDirectionalCrosshair( int x, int y, int iSize ) { C_ASW_Player *local = C_ASW_Player::GetLocalASWPlayer(); if (!local) return; C_ASW_Marine *pMarine = local->GetMarine(); if (!pMarine) return; Vector MarinePos = pMarine->GetRenderOrigin(); Vector screenPos; debugoverlay->ScreenPosition( MarinePos + Vector( 0, 0, 45 ), screenPos ); int cx, cy, dx, dy; ASWInput()->ASW_GetWindowCenter(cx, cy); dx = x - cx; dy = y - cy; float flDistance = FastSqrt( dx * dx + dy * dy ); //CASWScriptCreatedItem *pItem = static_cast<CASWScriptCreatedItem*>( pMarine->GetActiveASWWeapon()->GetAttributeContainer()->GetItem() ); //if ( !m_bIsCastingSuitAbility )//pItem && pItem->IsMeleeWeapon() && //{ // here is where we do the crosshair scaling int iMax = YRES(54); int iMin = YRES(16); // clamp the min and max distance the cursor is from the marine on screen float flSizeDist = clamp( flDistance, iMin, iMax ); // this is the full percentage to scale by float flTemp = (flSizeDist - iMin) / ( iMax - iMin ); float flMinTexScale = 0.8; float flMaxTexScale = 1.0; // this is the final percentage to scale by based on the clamping we want for the min and max texture scaling float flAdjust = flTemp * (flMaxTexScale - flMinTexScale) + flMinTexScale; iSize *= flAdjust; m_pAmmoProgress->SetScale( flAdjust ); //} iSize *= 2; int iXHairHalfSize = iSize / 2; // draw a red pointing, potentially blinking, arrow //Vector vecFacing(screenPos.x - (ScreenWidth() * 0.5f), screenPos.y - (ScreenHeight() * 0.5f), 0); //float fFacingYaw = -UTIL_VecToYaw(vecFacing); Vector2D vXHairCenter( x , y ); Vector vecCornerTL(-iXHairHalfSize, -iXHairHalfSize, 0); Vector vecCornerTR(iXHairHalfSize, -iXHairHalfSize, 0); Vector vecCornerBR(iXHairHalfSize, iXHairHalfSize, 0); Vector vecCornerBL(-iXHairHalfSize, iXHairHalfSize, 0); Vector vecCornerTL_rotated, vecCornerTR_rotated, vecCornerBL_rotated, vecCornerBR_rotated; int current_posx = 0; int current_posy = 0; ASWInput()->GetSimulatedFullscreenMousePos( ¤t_posx, ¤t_posy ); Vector vecFacing( 0, 0, 0 ); vecFacing.x = screenPos.x - current_posx; vecFacing.y = screenPos.y - current_posy; float fFacingYaw = -UTIL_VecToYaw( vecFacing ); /* if ( ASWInput()->ControllerModeActive() ) { int current_posx = 0; int current_posy = 0; ASWInput()->GetSimulatedFullscreenMousePos( ¤t_posx, ¤t_posy ); vecFacing.x = screenPos.x - current_posx; vecFacing.y = screenPos.y - current_posy; fFacingYaw = -UTIL_VecToYaw( vecFacing ); } */ // rotate it by our facing yaw QAngle angFacing(0, -fFacingYaw + 90.0, 0); VectorRotate(vecCornerTL, angFacing, vecCornerTL_rotated); VectorRotate(vecCornerTR, angFacing, vecCornerTR_rotated); VectorRotate(vecCornerBR, angFacing, vecCornerBR_rotated); VectorRotate(vecCornerBL, angFacing, vecCornerBL_rotated); // float flAlpha = 245; // fade the crosshair out when it is very close to the marine float flAdjust2 = flDistance / YRES(28); flAdjust2 = clamp( flAdjust2, 0.1f, 1.0f ); bool bShotWarn = false; Color colorCross = Color(255,255,255,flAlpha*flAdjust2); C_ASW_Weapon* pWeapon = pMarine->GetActiveASWWeapon(); if ( pWeapon && pWeapon->IsOffensiveWeapon() ) { C_BaseEntity *pEnt = pWeapon->GetLaserTargetEntity(); if ( pEnt && pEnt->Classify() == CLASS_ASW_MARINE ) { bShotWarn = true; colorCross = Color(255,0,0,flAlpha*flAdjust2); } } surface()->DrawSetColor( colorCross ); if ( !asw_crosshair_use_perspective.GetBool() ) { surface()->DrawSetTexture( m_nDirectCrosshairTexture2 ); } else { if ( bShotWarn ) surface()->DrawSetTexture( m_nDirectCrosshairTextureX ); else surface()->DrawSetTexture( m_nDirectCrosshairTexture ); } Vertex_t points[4] = { Vertex_t( Vector2D(vXHairCenter.x + vecCornerTL_rotated.x, vXHairCenter.y + vecCornerTL_rotated.y), Vector2D(0,0) ), Vertex_t( Vector2D(vXHairCenter.x + vecCornerTR_rotated.x, vXHairCenter.y + vecCornerTR_rotated.y), Vector2D(1,0) ), Vertex_t( Vector2D(vXHairCenter.x + vecCornerBR_rotated.x, vXHairCenter.y + vecCornerBR_rotated.y), Vector2D(1,1) ), Vertex_t( Vector2D(vXHairCenter.x + vecCornerBL_rotated.x, vXHairCenter.y + vecCornerBL_rotated.y), Vector2D(0,1) ) }; surface()->DrawTexturedPolygon( 4, points ); // draw the center if ( !asw_crosshair_use_perspective.GetBool() ) { surface()->DrawSetColor( colorCross ); surface()->DrawSetTexture( m_nCrosshairTexture ); surface()->DrawTexturedRect(vXHairCenter.x - iXHairHalfSize, vXHairCenter.y - iXHairHalfSize, vXHairCenter.x + iXHairHalfSize, vXHairCenter.y + iXHairHalfSize); } }
void CGrenadeAR2::Spawn( void ) { Precache( ); SetSolid( SOLID_BBOX ); SetMoveType( MOVETYPE_FLYGRAVITY, MOVECOLLIDE_FLY_BOUNCE ); // Hits everything but debris SetCollisionGroup( COLLISION_GROUP_PROJECTILE ); SetModel( "models/Weapons/ar2_grenade.mdl"); UTIL_SetSize(this, Vector(-3, -3, -3), Vector(3, 3, 3)); // UTIL_SetSize(this, Vector(0, 0, 0), Vector(0, 0, 0)); SetUse( &CGrenadeAR2::DetonateUse ); SetTouch( &CGrenadeAR2::GrenadeAR2Touch ); SetThink( &CGrenadeAR2::GrenadeAR2Think ); SetNextThink( gpGlobals->curtime + 0.1f ); if( GetOwnerEntity() && GetOwnerEntity()->IsPlayer() ) { m_flDamage = sk_plr_dmg_smg1_grenade.GetFloat(); } else { m_flDamage = sk_npc_dmg_smg1_grenade.GetFloat(); } m_DmgRadius = sk_smg1_grenade_radius.GetFloat(); m_takedamage = DAMAGE_YES; m_bIsLive = true; m_iHealth = 1; SetGravity( UTIL_ScaleForGravity( 400 ) ); // use a lower gravity for grenades to make them easier to see SetFriction( 0.8 ); SetSequence( 0 ); m_fDangerRadius = 100; m_fSpawnTime = gpGlobals->curtime; // ------------- // Smoke trail. // ------------- if( g_CV_SmokeTrail.GetInt() && !IsXbox() ) { m_hSmokeTrail = SmokeTrail::CreateSmokeTrail(); if( m_hSmokeTrail ) { m_hSmokeTrail->m_SpawnRate = 48; m_hSmokeTrail->m_ParticleLifetime = 1; m_hSmokeTrail->m_StartColor.Init(0.1f, 0.1f, 0.1f); m_hSmokeTrail->m_EndColor.Init(0,0,0); m_hSmokeTrail->m_StartSize = 12; m_hSmokeTrail->m_EndSize = m_hSmokeTrail->m_StartSize * 4; m_hSmokeTrail->m_SpawnRadius = 4; m_hSmokeTrail->m_MinSpeed = 4; m_hSmokeTrail->m_MaxSpeed = 24; m_hSmokeTrail->m_Opacity = 0.2f; m_hSmokeTrail->SetLifetime(10.0f); m_hSmokeTrail->FollowEntity(this); } } }
//----------------------------------------------------------------------------- // Purpose: This takes the current place the NPC's trying to get to, figures out // what keys to press to get the vehicle to go there, and then sends // them to the vehicle. //----------------------------------------------------------------------------- void CNPC_CraneDriver::DriveVehicle( void ) { // No targets? if ( !GetEnemy() && m_vecDesiredPosition == vec3_origin ) return; Vector vecTarget = m_vecDesiredPosition; // Track our targets if ( m_hPickupTarget ) { vecTarget = m_hPickupTarget->GetAbsOrigin(); } else if ( !m_bForcedPickup && !m_bForcedDropoff && GetEnemy() ) { vecTarget = GetEnemy()->GetAbsOrigin(); } // Move the crane over the target // Use the crane type as a targeting point Vector vecCraneTip = m_hCrane->GetCraneTipPosition(); Vector2D vecCraneTip2D( vecCraneTip.x, vecCraneTip.y ); Vector2D vecTarget2D( vecTarget.x, vecTarget.y ); Vector2D vecOrigin2D( m_hCrane->GetAbsOrigin().x, m_hCrane->GetAbsOrigin().y ); if ( g_debug_vehicledriver.GetInt() ) { NDebugOverlay::Box( vecTarget, -Vector(50,50,50), Vector(50,50,50), 0,255,0, true, 0.1 ); NDebugOverlay::Box( vecCraneTip, -Vector(2,2,5000), Vector(2,2,5), 0,255,0, true, 0.1 ); NDebugOverlay::Box( vecTarget, -Vector(2,2,5), Vector(2,2,5000), 0,255,0, true, 0.1 ); } // Store off the distance to our target m_flDistanceToTarget = (vecTarget2D - vecCraneTip2D).Length(); // First determine whether we need to extend / retract the arm float flDistToTarget = (vecOrigin2D - vecTarget2D).LengthSqr(); float flDistToCurrent = (vecOrigin2D - vecCraneTip2D).LengthSqr(); float flDelta = fabs(flDistToTarget - flDistToCurrent); // Slow down as we get closer, but do it based upon our current extension rate float flMinDelta = 50 + (50 * fabs(m_hCrane->GetExtensionRate() / CRANE_EXTENSION_RATE_MAX)); flMinDelta *= flMinDelta; if ( flDelta > flMinDelta ) { if ( flDistToCurrent > flDistToTarget ) { // Retract m_pVehicleInterface->NPC_ThrottleReverse(); } else if ( flDistToCurrent < flDistToTarget ) { // Extend m_pVehicleInterface->NPC_ThrottleForward(); } } else { m_pVehicleInterface->NPC_ThrottleCenter(); } // Then figure out if we need to rotate. Do it all in 2D space. Vector vecRight, vecForward; m_hCrane->GetVectors( &vecForward, &vecRight, NULL ); vecRight.z = 0; vecForward.z = 0; VectorNormalize( vecRight ); VectorNormalize( vecForward ); Vector vecToTarget = ( vecTarget - m_hCrane->GetAbsOrigin() ); vecToTarget.z = 0; VectorNormalize( vecToTarget ); float flDotRight = DotProduct( vecRight, vecToTarget ); float flDotForward = DotProduct( vecForward, vecToTarget ); // Start slowing if we're going to hit the point soon float flTurnInDeg = RAD2DEG( acos(flDotForward) ); float flSpeed = m_hCrane->GetMaxTurnRate() * (flTurnInDeg / 15.0); flSpeed = min( m_hCrane->GetMaxTurnRate(), flSpeed ); if ( fabs(flSpeed) < 0.05 ) { // We're approaching the target, so stop turning m_pVehicleInterface->NPC_TurnCenter(); } else { if ( flDotRight < 0 ) { // Turn right m_pVehicleInterface->NPC_TurnRight( flSpeed ); } else if ( flDotRight > 0 ) { // Turn left m_pVehicleInterface->NPC_TurnLeft( flSpeed ); } } }
void CInput::CreateMove ( int sequence_number, float input_sample_frametime, bool active ) { CUserCmd *cmd = &m_pCommands[ sequence_number % MULTIPLAYER_BACKUP ]; CVerifiedUserCmd *pVerified = &m_pVerifiedCommands[ sequence_number % MULTIPLAYER_BACKUP ]; cmd->Reset(); cmd->command_number = sequence_number; cmd->tick_count = gpGlobals->tickcount; QAngle viewangles; if ( active || sv_noclipduringpause.GetInt() ) { // Determine view angles AdjustAngles ( input_sample_frametime ); // Determine sideways movement ComputeSideMove( cmd ); // Determine vertical movement ComputeUpwardMove( cmd ); // Determine forward movement ComputeForwardMove( cmd ); // Scale based on holding speed key or having too fast of a velocity based on client maximum // speed. ScaleMovements( cmd ); // Allow mice and other controllers to add their inputs ControllerMove( input_sample_frametime, cmd ); } else { // need to run and reset mouse input so that there is no view pop when unpausing if ( !m_fCameraInterceptingMouse && m_fMouseActive ) { float mx, my; GetAccumulatedMouseDeltasAndResetAccumulators( &mx, &my ); ResetMouse(); } } // Retreive view angles from engine ( could have been set in IN_AdjustAngles above ) engine->GetViewAngles( viewangles ); // Latch and clear impulse cmd->impulse = in_impulse; in_impulse = 0; // Latch and clear weapon selection if ( m_hSelectedWeapon != NULL ) { C_BaseCombatWeapon *weapon = m_hSelectedWeapon; cmd->weaponselect = weapon->entindex(); cmd->weaponsubtype = weapon->GetSubType(); // Always clear weapon selection m_hSelectedWeapon = NULL; } // Set button and flag bits cmd->buttons = GetButtonBits( 1 ); // Using joystick? if ( in_joystick.GetInt() ) { if ( cmd->forwardmove > 0 ) { cmd->buttons |= IN_FORWARD; } else if ( cmd->forwardmove < 0 ) { cmd->buttons |= IN_BACK; } } // Use new view angles if alive, otherwise user last angles we stored off. if ( g_iAlive ) { VectorCopy( viewangles, cmd->viewangles ); VectorCopy( viewangles, m_angPreviousViewAngles ); } else { VectorCopy( m_angPreviousViewAngles, cmd->viewangles ); } // Let the move manager override anything it wants to. if ( g_pClientMode->CreateMove( input_sample_frametime, cmd ) ) { // Get current view angles after the client mode tweaks with it engine->SetViewAngles( cmd->viewangles ); } m_flLastForwardMove = cmd->forwardmove; cmd->random_seed = MD5_PseudoRandom( sequence_number ) & 0x7fffffff; HLTVCamera()->CreateMove( cmd ); #if defined( HL2_CLIENT_DLL ) // copy backchannel data int i; for (i = 0; i < m_EntityGroundContact.Count(); i++) { cmd->entitygroundcontact.AddToTail( m_EntityGroundContact[i] ); } m_EntityGroundContact.RemoveAll(); #endif pVerified->m_cmd = *cmd; pVerified->m_crc = cmd->GetChecksum(); }
void CBaseVSShader::DrawFlashlight_dx90( IMaterialVar** params, IShaderDynamicAPI *pShaderAPI, IShaderShadow* pShaderShadow, DrawFlashlight_dx90_Vars_t &vars ) { // FLASHLIGHTFIXME: hack . . need to fix the vertex shader so that it can deal with and without bumps for vertexlitgeneric if( !vars.m_bLightmappedGeneric ) { vars.m_bBump = false; } bool bBump2 = vars.m_bWorldVertexTransition && vars.m_bBump && vars.m_nBumpmap2Var != -1 && params[vars.m_nBumpmap2Var]->IsTexture(); bool bSeamless = vars.m_fSeamlessScale != 0.0; bool bDetail = vars.m_bLightmappedGeneric && (vars.m_nDetailVar != -1) && params[vars.m_nDetailVar]->IsDefined() && (vars.m_nDetailScale != -1); int nDetailBlendMode = 0; if ( bDetail ) { nDetailBlendMode = GetIntParam( vars.m_nDetailTextureCombineMode, params ); ITexture *pDetailTexture = params[vars.m_nDetailVar]->GetTextureValue(); if ( pDetailTexture->GetFlags() & TEXTUREFLAGS_SSBUMP ) { if ( vars.m_bBump ) nDetailBlendMode = 10; // ssbump else nDetailBlendMode = 11; // ssbump_nobump } } if( pShaderShadow ) { SetInitialShadowState(); pShaderShadow->EnableDepthWrites( false ); pShaderShadow->EnableAlphaWrites( false ); // Alpha blend SetAdditiveBlendingShadowState( BASETEXTURE, true ); // Alpha test pShaderShadow->EnableAlphaTest( IS_FLAG_SET( MATERIAL_VAR_ALPHATEST ) ); if ( vars.m_nAlphaTestReference != -1 && params[vars.m_nAlphaTestReference]->GetFloatValue() > 0.0f ) { pShaderShadow->AlphaFunc( SHADER_ALPHAFUNC_GEQUAL, params[vars.m_nAlphaTestReference]->GetFloatValue() ); } // Spot sampler pShaderShadow->EnableTexture( SHADER_SAMPLER0, true ); // Base sampler pShaderShadow->EnableTexture( SHADER_SAMPLER1, true ); pShaderShadow->EnableSRGBRead( SHADER_SAMPLER1, true ); // Normalizing cubemap sampler pShaderShadow->EnableTexture( SHADER_SAMPLER2, true ); // Normalizing cubemap sampler2 or normal map sampler pShaderShadow->EnableTexture( SHADER_SAMPLER3, true ); // RandomRotation sampler pShaderShadow->EnableTexture( SHADER_SAMPLER5, true ); // Flashlight depth sampler pShaderShadow->EnableTexture( SHADER_SAMPLER7, true ); pShaderShadow->SetShadowDepthFiltering( SHADER_SAMPLER7 ); if( vars.m_bWorldVertexTransition ) { // $basetexture2 pShaderShadow->EnableTexture( SHADER_SAMPLER4, true ); pShaderShadow->EnableSRGBRead( SHADER_SAMPLER4, true ); } if( bBump2 ) { // Normalmap2 sampler pShaderShadow->EnableTexture( SHADER_SAMPLER6, true ); } if( bDetail ) { pShaderShadow->EnableTexture( SHADER_SAMPLER8, true ); // detail sampler if ( nDetailBlendMode == 1 ) pShaderShadow->EnableSRGBRead( SHADER_SAMPLER8, true ); } pShaderShadow->EnableSRGBWrite( true ); if( vars.m_bLightmappedGeneric ) { #ifndef _X360 if ( g_pHardwareConfig->HasFastVertexTextures() ) { DECLARE_STATIC_VERTEX_SHADER( lightmappedgeneric_flashlight_vs30 ); SET_STATIC_VERTEX_SHADER_COMBO( WORLDVERTEXTRANSITION, vars.m_bWorldVertexTransition ); SET_STATIC_VERTEX_SHADER_COMBO( NORMALMAP, vars.m_bBump ); SET_STATIC_VERTEX_SHADER_COMBO( SEAMLESS, bSeamless ); SET_STATIC_VERTEX_SHADER_COMBO( DETAIL, bDetail ); SET_STATIC_VERTEX_SHADER( lightmappedgeneric_flashlight_vs30 ); } else #endif { DECLARE_STATIC_VERTEX_SHADER( lightmappedgeneric_flashlight_vs20 ); SET_STATIC_VERTEX_SHADER_COMBO( WORLDVERTEXTRANSITION, vars.m_bWorldVertexTransition ); SET_STATIC_VERTEX_SHADER_COMBO( NORMALMAP, vars.m_bBump ); SET_STATIC_VERTEX_SHADER_COMBO( SEAMLESS, bSeamless ); SET_STATIC_VERTEX_SHADER_COMBO( DETAIL, bDetail ); SET_STATIC_VERTEX_SHADER( lightmappedgeneric_flashlight_vs20 ); } unsigned int flags = VERTEX_POSITION | VERTEX_NORMAL; if( vars.m_bBump ) { flags |= VERTEX_TANGENT_S | VERTEX_TANGENT_T; } int numTexCoords = 1; if( vars.m_bWorldVertexTransition ) { flags |= VERTEX_COLOR; numTexCoords = 2; // need lightmap texcoords to get alpha. } pShaderShadow->VertexShaderVertexFormat( flags, numTexCoords, 0, 0 ); } else { // Need a 3.0 vs here? DECLARE_STATIC_VERTEX_SHADER( vertexlitgeneric_flashlight_vs20 ); SET_STATIC_VERTEX_SHADER_COMBO( TEETH, vars.m_bTeeth ); SET_STATIC_VERTEX_SHADER( vertexlitgeneric_flashlight_vs20 ); unsigned int flags = VERTEX_POSITION | VERTEX_NORMAL; int numTexCoords = 1; pShaderShadow->VertexShaderVertexFormat( flags, numTexCoords, 0, vars.m_bBump ? 4 : 0 ); } int nBumpMapVariant = 0; if ( vars.m_bBump ) { nBumpMapVariant = ( vars.m_bSSBump ) ? 2 : 1; } #ifndef _X360 if ( g_pHardwareConfig->HasFastVertexTextures() ) { int nShadowFilterMode = g_pHardwareConfig->GetShadowFilterMode(); DECLARE_STATIC_PIXEL_SHADER( flashlight_ps30 ); SET_STATIC_PIXEL_SHADER_COMBO( NORMALMAP, nBumpMapVariant ); SET_STATIC_PIXEL_SHADER_COMBO( NORMALMAP2, bBump2 ); SET_STATIC_PIXEL_SHADER_COMBO( WORLDVERTEXTRANSITION, vars.m_bWorldVertexTransition ); SET_STATIC_PIXEL_SHADER_COMBO( SEAMLESS, bSeamless ); SET_STATIC_PIXEL_SHADER_COMBO( DETAILTEXTURE, bDetail ); SET_STATIC_PIXEL_SHADER_COMBO( DETAIL_BLEND_MODE, nDetailBlendMode ); SET_STATIC_PIXEL_SHADER_COMBO( FLASHLIGHTDEPTHFILTERMODE, nShadowFilterMode ); SET_STATIC_PIXEL_SHADER( flashlight_ps30 ); } else #endif if ( g_pHardwareConfig->SupportsPixelShaders_2_b() ) { int nShadowFilterMode = g_pHardwareConfig->GetShadowFilterMode(); DECLARE_STATIC_PIXEL_SHADER( flashlight_ps20b ); SET_STATIC_PIXEL_SHADER_COMBO( NORMALMAP, nBumpMapVariant ); SET_STATIC_PIXEL_SHADER_COMBO( NORMALMAP2, bBump2 ); SET_STATIC_PIXEL_SHADER_COMBO( WORLDVERTEXTRANSITION, vars.m_bWorldVertexTransition ); SET_STATIC_PIXEL_SHADER_COMBO( SEAMLESS, bSeamless ); SET_STATIC_PIXEL_SHADER_COMBO( DETAILTEXTURE, bDetail ); SET_STATIC_PIXEL_SHADER_COMBO( DETAIL_BLEND_MODE, nDetailBlendMode ); SET_STATIC_PIXEL_SHADER_COMBO( FLASHLIGHTDEPTHFILTERMODE, nShadowFilterMode ); SET_STATIC_PIXEL_SHADER( flashlight_ps20b ); } else { DECLARE_STATIC_PIXEL_SHADER( flashlight_ps20 ); SET_STATIC_PIXEL_SHADER_COMBO( NORMALMAP, nBumpMapVariant ); SET_STATIC_PIXEL_SHADER_COMBO( NORMALMAP2, bBump2 ); SET_STATIC_PIXEL_SHADER_COMBO( WORLDVERTEXTRANSITION, vars.m_bWorldVertexTransition ); SET_STATIC_PIXEL_SHADER_COMBO( SEAMLESS, bSeamless ); SET_STATIC_PIXEL_SHADER_COMBO( DETAILTEXTURE, bDetail ); SET_STATIC_PIXEL_SHADER_COMBO( DETAIL_BLEND_MODE, nDetailBlendMode ); SET_STATIC_PIXEL_SHADER( flashlight_ps20 ); } FogToBlack(); PI_BeginCommandBuffer(); PI_SetModulationPixelShaderDynamicState( PSREG_DIFFUSE_MODULATION ); PI_EndCommandBuffer(); } else { VMatrix worldToTexture; ITexture *pFlashlightDepthTexture; FlashlightState_t flashlightState = pShaderAPI->GetFlashlightStateEx( worldToTexture, &pFlashlightDepthTexture ); SetFlashLightColorFromState( flashlightState, pShaderAPI, false ); BindTexture( SHADER_SAMPLER0, flashlightState.m_pSpotlightTexture, flashlightState.m_nSpotlightTextureFrame ); pShaderAPI->BindStandardTexture( SHADER_SAMPLER5, TEXTURE_SHADOW_NOISE_2D ); if( pFlashlightDepthTexture && g_pConfig->ShadowDepthTexture() && flashlightState.m_bEnableShadows ) { BindTexture( SHADER_SAMPLER7, pFlashlightDepthTexture, 0 ); // Tweaks associated with a given flashlight float tweaks[4]; tweaks[0] = ShadowFilterFromState( flashlightState ); tweaks[1] = ShadowAttenFromState( flashlightState ); HashShadow2DJitter( flashlightState.m_flShadowJitterSeed, &tweaks[2], &tweaks[3] ); pShaderAPI->SetPixelShaderConstant( PSREG_ENVMAP_TINT__SHADOW_TWEAKS, tweaks, 1 ); // Dimensions of screen, used for screen-space noise map sampling float vScreenScale[4] = {1280.0f / 32.0f, 720.0f / 32.0f, 0, 0}; int nWidth, nHeight; pShaderAPI->GetBackBufferDimensions( nWidth, nHeight ); int nTexWidth, nTexHeight; pShaderAPI->GetStandardTextureDimensions( &nTexWidth, &nTexHeight, TEXTURE_SHADOW_NOISE_2D ); vScreenScale[0] = (float) nWidth / nTexWidth; vScreenScale[1] = (float) nHeight / nTexHeight; pShaderAPI->SetPixelShaderConstant( PSREG_FLASHLIGHT_SCREEN_SCALE, vScreenScale, 1 ); } else { pShaderAPI->BindStandardTexture( SHADER_SAMPLER7, TEXTURE_WHITE ); } if( params[BASETEXTURE]->IsTexture() && mat_fullbright.GetInt() != 2 ) { BindTexture( SHADER_SAMPLER1, BASETEXTURE, FRAME ); } else { pShaderAPI->BindStandardTexture( SHADER_SAMPLER1, TEXTURE_GREY ); } if( vars.m_bWorldVertexTransition ) { Assert( vars.m_nBaseTexture2Var >= 0 && vars.m_nBaseTexture2FrameVar >= 0 ); BindTexture( SHADER_SAMPLER4, vars.m_nBaseTexture2Var, vars.m_nBaseTexture2FrameVar ); } pShaderAPI->BindStandardTexture( SHADER_SAMPLER2, TEXTURE_NORMALIZATION_CUBEMAP ); if( vars.m_bBump ) { BindTexture( SHADER_SAMPLER3, vars.m_nBumpmapVar, vars.m_nBumpmapFrame ); } else { pShaderAPI->BindStandardTexture( SHADER_SAMPLER3, TEXTURE_NORMALIZATION_CUBEMAP ); } if( bDetail ) { BindTexture( SHADER_SAMPLER8, vars.m_nDetailVar ); } if( vars.m_bWorldVertexTransition ) { if( bBump2 ) { BindTexture( SHADER_SAMPLER6, vars.m_nBumpmap2Var, vars.m_nBumpmap2Frame ); } } if( vars.m_bLightmappedGeneric ) { #ifndef _X360 if ( g_pHardwareConfig->HasFastVertexTextures() ) { DECLARE_DYNAMIC_VERTEX_SHADER( lightmappedgeneric_flashlight_vs30 ); SET_DYNAMIC_VERTEX_SHADER( lightmappedgeneric_flashlight_vs30 ); } else #endif { DECLARE_DYNAMIC_VERTEX_SHADER( lightmappedgeneric_flashlight_vs20 ); SET_DYNAMIC_VERTEX_SHADER( lightmappedgeneric_flashlight_vs20 ); } if ( bSeamless ) { float const0[4]={ vars.m_fSeamlessScale,0,0,0}; pShaderAPI->SetVertexShaderConstant( VERTEX_SHADER_SHADER_SPECIFIC_CONST_6, const0 ); } if ( bDetail ) { float vDetailConstants[4] = {1,1,1,1}; if ( vars.m_nDetailTint != -1 ) { params[vars.m_nDetailTint]->GetVecValue( vDetailConstants, 3 ); } if ( vars.m_nDetailTextureBlendFactor != -1 ) { vDetailConstants[3] = params[vars.m_nDetailTextureBlendFactor]->GetFloatValue(); } pShaderAPI->SetPixelShaderConstant( 0, vDetailConstants, 1 ); } } else { DECLARE_DYNAMIC_VERTEX_SHADER( vertexlitgeneric_flashlight_vs20 ); SET_DYNAMIC_VERTEX_SHADER_COMBO( SKINNING, pShaderAPI->GetCurrentNumBones() > 0 ); SET_DYNAMIC_VERTEX_SHADER( vertexlitgeneric_flashlight_vs20 ); if( vars.m_bTeeth ) { Assert( vars.m_nTeethForwardVar >= 0 ); Assert( vars.m_nTeethIllumFactorVar >= 0 ); Vector4D lighting; params[vars.m_nTeethForwardVar]->GetVecValue( lighting.Base(), 3 ); lighting[3] = params[vars.m_nTeethIllumFactorVar]->GetFloatValue(); pShaderAPI->SetVertexShaderConstant( VERTEX_SHADER_SHADER_SPECIFIC_CONST_0, lighting.Base() ); } } pShaderAPI->SetPixelShaderFogParams( PSREG_FOG_PARAMS ); float vEyePos_SpecExponent[4]; pShaderAPI->GetWorldSpaceCameraPosition( vEyePos_SpecExponent ); vEyePos_SpecExponent[3] = 0.0f; pShaderAPI->SetPixelShaderConstant( PSREG_EYEPOS_SPEC_EXPONENT, vEyePos_SpecExponent, 1 ); #ifndef _X360 if ( g_pHardwareConfig->HasFastVertexTextures() ) { DECLARE_DYNAMIC_PIXEL_SHADER( flashlight_ps30 ); SET_DYNAMIC_PIXEL_SHADER_COMBO( FLASHLIGHTSHADOWS, flashlightState.m_bEnableShadows ); SET_DYNAMIC_PIXEL_SHADER_COMBO( UBERLIGHT, flashlightState.m_bUberlight ); SET_DYNAMIC_PIXEL_SHADER( flashlight_ps30 ); SetupUberlightFromState( pShaderAPI, flashlightState ); } else #endif if ( g_pHardwareConfig->SupportsPixelShaders_2_b() ) { DECLARE_DYNAMIC_PIXEL_SHADER( flashlight_ps20b ); SET_DYNAMIC_PIXEL_SHADER_COMBO( FLASHLIGHTSHADOWS, flashlightState.m_bEnableShadows ); SET_DYNAMIC_PIXEL_SHADER( flashlight_ps20b ); } else { DECLARE_DYNAMIC_PIXEL_SHADER( flashlight_ps20 ); SET_DYNAMIC_PIXEL_SHADER( flashlight_ps20 ); } float atten[4]; // Set the flashlight attenuation factors atten[0] = flashlightState.m_fConstantAtten; atten[1] = flashlightState.m_fLinearAtten; atten[2] = flashlightState.m_fQuadraticAtten; atten[3] = flashlightState.m_FarZAtten; s_pShaderAPI->SetPixelShaderConstant( PSREG_FLASHLIGHT_ATTENUATION, atten, 1 ); float pos[4]; // Set the flashlight origin pos[0] = flashlightState.m_vecLightOrigin[0]; pos[1] = flashlightState.m_vecLightOrigin[1]; pos[2] = flashlightState.m_vecLightOrigin[2]; pos[3] = flashlightState.m_FarZ; pShaderAPI->SetPixelShaderConstant( PSREG_FLASHLIGHT_POSITION_RIM_BOOST, pos, 1 ); // rim boost not really used here SetFlashlightVertexShaderConstants( vars.m_bBump, vars.m_nBumpTransform, bDetail, vars.m_nDetailScale, bSeamless ? false : true ); } Draw(); }
/* ============================== GetLookSpring ============================== */ float CInput::GetLookSpring( void ) { return lookspring.GetInt(); }
//----------------------------------------------------------------------------- // Purpose: MouseMove -- main entry point for applying mouse // Input : *cmd - //----------------------------------------------------------------------------- void CInput::MouseMove( int nSlot, CUserCmd *cmd ) { float mouse_x, mouse_y; float mx, my; QAngle viewangles; QAngle actual_viewangles; // Get view angles from engine engine->GetViewAngles( actual_viewangles ); PerUserInput_t perUser = GetPerUser(nSlot); if (m_cinematic.GetBool()) { viewangles = perUser.m_angCinematicSetpoint; } else { viewangles = actual_viewangles; } // Validate mouse speed/acceleration settings CheckMouseAcclerationVars(); // Don't drift pitch at all while mouselooking. view->StopPitchDrift (); //jjb - this disables normal mouse control if the user is trying to // move the camera, or if the mouse cursor is visible if ( !GetPerUser( nSlot ).m_fCameraInterceptingMouse && g_pInputStackSystem->IsTopmostEnabledContext( m_hInputContext ) ) { // Sample mouse one more time AccumulateMouse( nSlot ); // Latch accumulated mouse movements and reset accumulators GetAccumulatedMouseDeltasAndResetAccumulators( nSlot, &mx, &my ); // Filter, etc. the delta values and place into mouse_x and mouse_y GetMouseDelta( nSlot, mx, my, &mouse_x, &mouse_y ); // Apply scaling factor ScaleMouse( nSlot, &mouse_x, &mouse_y ); // Let the client mode at the mouse input before it's used GetClientMode()->OverrideMouseInput( &mouse_x, &mouse_y ); // Add mouse X/Y movement to cmd ApplyMouse( nSlot, viewangles, cmd, mouse_x, mouse_y ); // Re-center the mouse. ResetMouse(); } GetPerUser(nSlot).m_angCinematicSetpoint = viewangles; if (m_cinematic.GetBool()) { float k = m_cinematic_depth.GetFloat(); QAngle steering; steering.x = UTIL_AngleDiff(viewangles.x, actual_viewangles.x); steering.y = UTIL_AngleDiff(viewangles.y, actual_viewangles.y); steering.z = UTIL_AngleDiff(viewangles.z, actual_viewangles.z); actual_viewangles += steering * (1-k); } else { actual_viewangles = viewangles; } // Store out the new viewangles. engine->SetViewAngles( actual_viewangles ); }
/* ============================== ComputeUpwardMove ============================== */ void CInput::ComputeUpwardMove( CUserCmd *cmd ) { cmd->upmove += cl_upspeed.GetFloat() * KeyState (&in_up); cmd->upmove -= cl_upspeed.GetFloat() * KeyState (&in_down); }
//----------------------------------------------------------------------------- // Purpose: // Input : &inputdata - //----------------------------------------------------------------------------- void CAI_AllyManager::InputReplenish( inputdata_t &inputdata ) { // Count the number of allies with the player right now. int iCurrentAllies; int iCurrentMedics; CountAllies( &iCurrentAllies, &iCurrentMedics ); // TOTAL number of allies to be replaced. int iReplaceAllies = m_iMaxAllies - iCurrentAllies; // The number of total allies that should be medics. int iReplaceMedics = m_iMaxMedics - iCurrentMedics; if( iReplaceMedics > iReplaceAllies ) { // Clamp medics. iReplaceMedics = iReplaceAllies; } // Medics. if( m_iMaxMedics > 0 ) { if( iReplaceMedics > MAX_ALLIES ) { // This error is fatal now. (sjb) Msg("**ERROR! ai_allymanager - ReplaceMedics > MAX_ALLIES\n" ); return; } if ( ai_ally_manager_debug.GetBool() ) DevMsg( "Ally manager spawning %d medics\n", iReplaceMedics ); int i; for( i = 0 ; i < iReplaceMedics ; i++ ) { m_SpawnMedicAlly.FireOutput( this, this, 0 ); // Don't forget to count this guy against the number of // allies to be replenished. iReplaceAllies--; } } // Allies if( iReplaceAllies < 1 ) { return; } if( iReplaceAllies > MAX_ALLIES ) { Msg("**ERROR! ai_allymanager - ReplaceAllies > MAX_ALLIES\n" ); iReplaceAllies = MAX_ALLIES; } if ( ai_ally_manager_debug.GetBool() ) DevMsg( "Ally manager spawning %d regulars\n", iReplaceAllies ); int i; for( i = 0 ; i < iReplaceAllies ; i++ ) { m_SpawnAlly[ i ].FireOutput( this, this, 0 ); } }
//----------------------------------------------------------------------------- // Purpose: Render current view into specified rectangle // Input : *rect - is computed by CVideoMode_Common::GetClientViewRect() //----------------------------------------------------------------------------- void CViewRender::Render( vrect_t *rect ) { Assert(s_DbgSetupOrigin == m_View.origin); Assert(s_DbgSetupAngles == m_View.angles); VPROF_BUDGET( "CViewRender::Render", "CViewRender::Render" ); tmZone( TELEMETRY_LEVEL0, TMZF_NONE, "%s", __FUNCTION__ ); vrect_t vr = *rect; // Stub out the material system if necessary. CMatStubHandler matStub; engine->EngineStats_BeginFrame(); // Assume normal vis m_bForceNoVis = false; C_BasePlayer *pPlayer = C_BasePlayer::GetLocalPlayer(); // Set for console commands, etc. render->SetMainView ( m_View.origin, m_View.angles ); g_ShaderEditorSystem->InitialPreRender(); for( StereoEye_t eEye = GetFirstEye(); eEye <= GetLastEye(); eEye = (StereoEye_t)(eEye+1) ) { CViewSetup &view = GetView( eEye ); #if 0 && defined( CSTRIKE_DLL ) const bool bPlayingBackReplay = g_pEngineClientReplay && g_pEngineClientReplay->IsPlayingReplayDemo(); if ( pPlayer && !bPlayingBackReplay ) { C_BasePlayer *pViewTarget = pPlayer; if ( pPlayer->IsObserver() && pPlayer->GetObserverMode() == OBS_MODE_IN_EYE ) { pViewTarget = dynamic_cast<C_BasePlayer*>( pPlayer->GetObserverTarget() ); } if ( pViewTarget ) { float targetFOV = (float)pViewTarget->m_iFOV; if ( targetFOV == 0 ) { // FOV of 0 means use the default FOV targetFOV = g_pGameRules->DefaultFOV(); } float deltaFOV = view.fov - m_flLastFOV; float FOVDirection = targetFOV - pViewTarget->m_iFOVStart; // Clamp FOV changes to stop FOV oscillation if ( ( deltaFOV < 0.0f && FOVDirection > 0.0f ) || ( deltaFOV > 0.0f && FOVDirection < 0.0f ) ) { view.fov = m_flLastFOV; } // Catch case where FOV overshoots its target FOV if ( ( view.fov < targetFOV && FOVDirection <= 0.0f ) || ( view.fov > targetFOV && FOVDirection >= 0.0f ) ) { view.fov = targetFOV; } m_flLastFOV = view.fov; } } #endif static ConVarRef sv_restrict_aspect_ratio_fov( "sv_restrict_aspect_ratio_fov" ); float aspectRatio = engine->GetScreenAspectRatio() * 0.75f; // / (4/3) float limitedAspectRatio = aspectRatio; if ( ( sv_restrict_aspect_ratio_fov.GetInt() > 0 && engine->IsWindowedMode() && gpGlobals->maxClients > 1 ) || sv_restrict_aspect_ratio_fov.GetInt() == 2 ) { limitedAspectRatio = MIN( aspectRatio, 1.85f * 0.75f ); // cap out the FOV advantage at a 1.85:1 ratio (about the widest any legit user should be) } view.fov = ScaleFOVByWidthRatio( view.fov, limitedAspectRatio ); view.fovViewmodel = ScaleFOVByWidthRatio( view.fovViewmodel, aspectRatio ); // Let the client mode hook stuff. g_pClientMode->PreRender(&view); g_pClientMode->AdjustEngineViewport( vr.x, vr.y, vr.width, vr.height ); ToolFramework_AdjustEngineViewport( vr.x, vr.y, vr.width, vr.height ); float flViewportScale = mat_viewportscale.GetFloat(); view.m_nUnscaledX = vr.x; view.m_nUnscaledY = vr.y; view.m_nUnscaledWidth = vr.width; view.m_nUnscaledHeight = vr.height; switch( eEye ) { case STEREO_EYE_MONO: { #if 0 // Good test mode for debugging viewports that are not full-size. view.width = vr.width * flViewportScale * 0.75f; view.height = vr.height * flViewportScale * 0.75f; view.x = vr.x + view.width * 0.10f; view.y = vr.y + view.height * 0.20f; #else view.x = vr.x * flViewportScale; view.y = vr.y * flViewportScale; view.width = vr.width * flViewportScale; view.height = vr.height * flViewportScale; #endif float engineAspectRatio = engine->GetScreenAspectRatio(); view.m_flAspectRatio = ( engineAspectRatio > 0.0f ) ? engineAspectRatio : ( (float)view.width / (float)view.height ); } break; case STEREO_EYE_RIGHT: case STEREO_EYE_LEFT: { g_pSourceVR->GetViewportBounds( (ISourceVirtualReality::VREye)(eEye - 1 ), &view.x, &view.y, &view.width, &view.height ); view.m_nUnscaledWidth = view.width; view.m_nUnscaledHeight = view.height; view.m_nUnscaledX = view.x; view.m_nUnscaledY = view.y; } break; default: Assert ( false ); break; } // if we still don't have an aspect ratio, compute it from the view size if( view.m_flAspectRatio <= 0.f ) view.m_flAspectRatio = (float)view.width / (float)view.height; int nClearFlags = VIEW_CLEAR_DEPTH | VIEW_CLEAR_STENCIL; if( gl_clear_randomcolor.GetBool() ) { CMatRenderContextPtr pRenderContext( materials ); pRenderContext->ClearColor3ub( rand()%256, rand()%256, rand()%256 ); pRenderContext->ClearBuffers( true, false, false ); pRenderContext->Release(); } else if ( gl_clear.GetBool() ) { nClearFlags |= VIEW_CLEAR_COLOR; } else if ( IsPosix() ) { MaterialAdapterInfo_t adapterInfo; materials->GetDisplayAdapterInfo( materials->GetCurrentAdapter(), adapterInfo ); // On Posix, on ATI, we always clear color if we're antialiasing if ( adapterInfo.m_VendorID == 0x1002 ) { if ( g_pMaterialSystem->GetCurrentConfigForVideoCard().m_nAASamples > 0 ) { nClearFlags |= VIEW_CLEAR_COLOR; } } } // Determine if we should draw view model ( client mode override ) bool drawViewModel = g_pClientMode->ShouldDrawViewModel(); if ( cl_leveloverview.GetFloat() > 0 ) { SetUpOverView(); nClearFlags |= VIEW_CLEAR_COLOR; drawViewModel = false; } // Apply any player specific overrides if ( pPlayer ) { // Override view model if necessary if ( !pPlayer->m_Local.m_bDrawViewmodel ) { drawViewModel = false; } } int flags = 0; if( eEye == STEREO_EYE_MONO || eEye == STEREO_EYE_LEFT || ( g_ClientVirtualReality.ShouldRenderHUDInWorld() ) ) { flags = RENDERVIEW_DRAWHUD; } if ( drawViewModel ) { flags |= RENDERVIEW_DRAWVIEWMODEL; } if( eEye == STEREO_EYE_RIGHT ) { // we should use the monitor view from the left eye for both eyes flags |= RENDERVIEW_SUPPRESSMONITORRENDERING; } RenderView( view, nClearFlags, flags ); if ( UseVR() ) { bool bDoUndistort = ! engine->IsTakingScreenshot(); if ( bDoUndistort ) { g_ClientVirtualReality.PostProcessFrame( eEye ); } // logic here all cloned from code in viewrender.cpp around RenderHUDQuad: // figure out if we really want to draw the HUD based on freeze cam bool bInFreezeCam = ( pPlayer && pPlayer->GetObserverMode() == OBS_MODE_FREEZECAM ); // draw the HUD after the view model so its "I'm closer" depth queues work right. if( !bInFreezeCam && g_ClientVirtualReality.ShouldRenderHUDInWorld() ) { // TODO - a bit of a shonky test - basically trying to catch the main menu, the briefing screen, the loadout screen, etc. bool bTranslucent = !g_pMatSystemSurface->IsCursorVisible(); g_ClientVirtualReality.OverlayHUDQuadWithUndistort( view, bDoUndistort, g_pClientMode->ShouldBlackoutAroundHUD(), bTranslucent ); } } } // TODO: should these be inside or outside the stereo eye stuff? g_pClientMode->PostRender(); engine->EngineStats_EndFrame(); #if !defined( _X360 ) // Stop stubbing the material system so we can see the budget panel matStub.End(); #endif // Draw all of the UI stuff "fullscreen" // (this is not health, ammo, etc. Nor is it pre-game briefing interface stuff - this is the stuff that appears when you hit Esc in-game) // In stereo mode this is rendered inside of RenderView so it goes into the render target if( !g_ClientVirtualReality.ShouldRenderHUDInWorld() ) { CViewSetup view2d; view2d.x = rect->x; view2d.y = rect->y; view2d.width = rect->width; view2d.height = rect->height; render->Push2DView( view2d, 0, NULL, GetFrustum() ); render->VGui_Paint( PAINT_UIPANELS | PAINT_CURSOR ); render->PopView( GetFrustum() ); } }