void CAI_Senses::Listen( void ) { m_iAudibleList = SOUNDLIST_EMPTY; int iSoundMask = GetOuter()->GetSoundInterests(); if ( iSoundMask != SOUND_NONE && !(GetOuter()->HasSpawnFlags(SF_NPC_WAIT_TILL_SEEN)) ) { int iSound = CSoundEnt::ActiveList(); while ( iSound != SOUNDLIST_EMPTY ) { CSound *pCurrentSound = CSoundEnt::SoundPointerForIndex( iSound ); if ( pCurrentSound && (iSoundMask & pCurrentSound->SoundType()) && CanHearSound( pCurrentSound ) ) { // the npc cares about this sound, and it's close enough to hear. pCurrentSound->m_iNextAudible = m_iAudibleList; m_iAudibleList = iSound; } iSound = pCurrentSound->NextSound(); } } GetOuter()->OnListened(); }
//----------------------------------------------------------------------------- // Purpose: Listens for sounds and updates the value of the SoundLevel output. //----------------------------------------------------------------------------- void CEnvMicrophone::Think(void) { int nSound = CSoundEnt::ActiveList(); bool fHearSound = false; float flMaxVolume = 0; // // Find the loudest sound that this microphone cares about. // while (nSound != SOUNDLIST_EMPTY) { CSound *pCurrentSound = CSoundEnt::SoundPointerForIndex(nSound); if (pCurrentSound) { if (m_nSoundMask & pCurrentSound->SoundType()) { float flVolume = 0; if (CanHearSound(pCurrentSound, flVolume) && (flVolume > flMaxVolume)) { flMaxVolume = flVolume; fHearSound = true; } } } nSound = pCurrentSound->NextSound(); } if( fHearSound ) { m_OnHeardSound.FireOutput( this, this ); } if (flMaxVolume != m_SoundLevel.Get()) { // // Don't smooth if we are within an epsilon. This allows the output to stop firing // much more quickly. // if (fabs(flMaxVolume - m_SoundLevel.Get()) < MICROPHONE_SETTLE_EPSILON) { m_SoundLevel.Set(flMaxVolume, this, this); } else { m_SoundLevel.Set(flMaxVolume * (1 - m_flSmoothFactor) + m_SoundLevel.Get() * m_flSmoothFactor, this, this); } } SetNextThink( gpGlobals->curtime + 0.1f ); }
//----------------------------------------------------------------------------- // Purpose: Hook for the sound system to tell us when a sound's been played //----------------------------------------------------------------------------- MicrophoneResult_t CEnvMicrophone::SoundPlayed( int entindex, const char *soundname, soundlevel_t soundlevel, float flVolume, int iFlags, int iPitch, const Vector *pOrigin, float soundtime, CUtlVector< Vector >& soundorigins ) { if ( m_bAvoidFeedback ) return MicrophoneResult_Ok; // Don't hear sounds that have already been heard by a microphone to avoid feedback! if ( iFlags & SND_SPEAKER ) return MicrophoneResult_Ok; #ifdef DEBUG_MICROPHONE Msg("%s heard %s: ", STRING(GetEntityName()), soundname ); #endif if ( !CanHearSound( entindex, soundlevel, flVolume, pOrigin ) ) return MicrophoneResult_Ok; // We've heard it. Play it out our speaker. If our speaker's gone away, we're done. if ( !m_hSpeaker ) { // First time, find our speaker. Done here, because finding it in Activate() wouldn't // find players, and we need to be able to specify !player for a speaker. if ( m_iszSpeakerName != NULL_STRING ) { m_hSpeaker = gEntList.FindEntityByName(NULL, STRING(m_iszSpeakerName) ); if ( !m_hSpeaker ) { Warning( "EnvMicrophone %s specifies a non-existent speaker name: %s\n", STRING(GetEntityName()), STRING(m_iszSpeakerName) ); m_iszSpeakerName = NULL_STRING; } } if ( !m_hSpeaker ) { return MicrophoneResult_Remove; } } m_bAvoidFeedback = true; // Add the speaker flag. Detected at playback and applies the speaker filter. iFlags |= SND_SPEAKER; CPASAttenuationFilter filter( m_hSpeaker ); EmitSound_t ep; ep.m_nChannel = CHAN_STATIC; ep.m_pSoundName = soundname; ep.m_flVolume = flVolume; ep.m_SoundLevel = soundlevel; ep.m_nFlags = iFlags; ep.m_nPitch = iPitch; ep.m_pOrigin = &m_hSpeaker->GetAbsOrigin(); ep.m_flSoundTime = soundtime; ep.m_nSpeakerEntity = entindex; CBaseEntity::EmitSound( filter, m_hSpeaker->entindex(), ep ); Q_strncpy( m_szLastSound, soundname, sizeof(m_szLastSound) ); m_OnRoutedSound.FireOutput( this, this, 0 ); m_bAvoidFeedback = false; // Copy emitted origin to soundorigins array for ( int i = 0; i < ep.m_UtlVecSoundOrigin.Count(); ++i ) { soundorigins.AddToTail( ep.m_UtlVecSoundOrigin[ i ] ); } // Do we want to allow the original sound to play? if ( m_spawnflags & SF_MICROPHONE_SWALLOW_ROUTED_SOUNDS ) { return MicrophoneResult_Swallow; } return MicrophoneResult_Ok; }