Esempio n. 1
0
/*
 * S_PlaySample
 */
void S_PlaySample(const vec3_t org, int ent_num, s_sample_t *sample, int atten) {
	s_channel_t *ch;
	int i;

	if (!s_env.initialized)
		return;

	if (!sample)
		return;

	if (sample->name[0] == '*')
		sample = S_LoadModelSample(&cl.entities[ent_num].current, sample->name);

	if (!sample->chunk)
		return;

	if ((i = S_AllocChannel()) == -1)
		return;

	ch = &s_env.channels[i];

	if (org) { // positioned sound
		VectorCopy(org, ch->org);
		ch->ent_num = -1;
	} else
		// entity sound
		ch->ent_num = ent_num;

	ch->atten = atten;
	ch->sample = sample;

	S_SpatializeChannel(ch);

	Mix_PlayChannel(i, ch->sample->chunk, 0);
}
Esempio n. 2
0
/*
 * S_LoopSample
 */
void S_LoopSample(const vec3_t org, s_sample_t *sample) {
	s_channel_t *ch;
	vec3_t delta;
	int i;

	if (!sample || !sample->chunk)
		return;

	ch = NULL;

	for (i = 0; i < MAX_CHANNELS; i++) { // find existing loop sound

		if (s_env.channels[i].ent_num != -1)
			continue;

		if (s_env.channels[i].sample == sample) {

			VectorSubtract(s_env.channels[i].org, org, delta);

			if (VectorLength(delta) < 512.0) {
				ch = &s_env.channels[i];
				break;
			}
		}
	}

	if (ch) { // update existing loop sample
		ch->count++;

		VectorMix(ch->org, org, 1.0 / ch->count, ch->org);
	} else { // or allocate a new one

		if ((i = S_AllocChannel()) == -1)
			return;

		ch = &s_env.channels[i];

		VectorCopy(org, ch->org);
		ch->ent_num = -1;
		ch->count = 1;
		ch->atten = ATTN_IDLE;
		ch->sample = sample;

		Mix_PlayChannel(i, ch->sample->chunk, 0);
	}

	S_SpatializeChannel(ch);
}
Esempio n. 3
0
static void
I_OGGMus_PlayNext (int looping)
{
	const char *track;
	sfx_t      *cd_sfx, *sfx;
	wavinfo_t  *info = 0;

	if (!play_list)
		return;
	if (PL_Type (play_list) == QFString) {
		track = PL_String (play_list);
		play_pos = 0;
	} else {
		play_pos++;
		if (play_pos >= PL_A_NumObjects (play_list))
			play_pos = 0;
		track = PL_String (PL_ObjectAtIndex (play_list, play_pos));
		looping = 0;
	}

	if (cd_channel) {
		S_ChannelStop (cd_channel);
		cd_channel = 0;
	}

	if (!(cd_channel = S_AllocChannel ()))
		return;

	if (!(cd_sfx = S_LoadSound (track)) || !(sfx = cd_sfx->open (cd_sfx))) {
		S_ChannelStop (cd_channel);
		cd_channel = 0;
		return;
	}
	Sys_Printf ("Playing: %s.\n", track);
	if (sfx->wavinfo)
		info = sfx->wavinfo (sfx);
	if (info) {
		if (looping == true)
			info->loopstart = 0;
		else
			info->loopstart = -1;
	}
	cd_channel->sfx = sfx;
	set_volume ();

	playing = true;
}
Esempio n. 4
0
/**
 * @brief Adds a loop sample for e.g. ambient sounds
 */
void S_LoopSample (const vec3_t org, s_sample_t* sample, float relVolume, float attenuation)
{
	s_channel_t* ch;
	int i;

	if (!sample || !sample->chunk)
		return;

	ch = nullptr;

	for (i = 0; i < MAX_CHANNELS; i++){  /* find existing loop sound */
		if (s_env.channels[i].sample == sample) {
			vec3_t delta;
			VectorSubtract(s_env.channels[i].org, org, delta);
			if (VectorLength(delta) < 255.0) {
				ch = &s_env.channels[i];
				break;
			}
		}
	}

	if (ch) {  /* update existing loop sample */
		ch->count++;

		VectorMix(ch->org, org, 1.0 / ch->count, ch->org);
	} else {  /* or allocate a new one */
		float volume;

		if ((i = S_AllocChannel()) == -1)
			return;

		ch = &s_env.channels[i];

		sample->lastPlayed = CL_Milliseconds();
		VectorCopy(org, ch->org);
		ch->count = 1;
		ch->atten = attenuation;
		ch->sample = sample;

		volume = snd_volume->value * relVolume * MIX_MAX_VOLUME;
		Mix_VolumeChunk(ch->sample->chunk, volume);
		Mix_PlayChannel(i, ch->sample->chunk, 0);
	}

	S_SpatializeChannel(ch);
}
Esempio n. 5
0
/**
 * @brief Validates the parms and queues the sound up
 * @param[in] origin if this is @c nullptr, the sound will be dynamically sourced from the entity
 * @param[in] sample The soundfile to play
 * @param[in] atten Attenuation of sound to be played (for example, @c fireAttenuation
 * or @c impactAttenuation from @c fireDef_s).
 * @param[in] relVolume Max mixer volume factor (0.0 - 1.0)
 * @sa S_StartLocalSample
 * @sa S_SetVolume
 */
void S_PlaySample (const vec3_t origin, s_sample_t* sample, float atten, float relVolume)
{
	s_channel_t* ch;
	int i;
	float volume;

	if (!s_env.initialized)
		return;

	if (!sample)
		return;

	/* if the last mix of this particular sample is less than half a second ago, skip it */
	if (sample->lastPlayed > CL_Milliseconds() - s_env.sampleRepeatRate)
		return;

	if ((i = S_AllocChannel()) == -1)
		return;

	sample->lastPlayed = CL_Milliseconds();
	ch = &s_env.channels[i];

	ch->atten = atten;
	ch->sample = sample;

	if (origin != nullptr) {
		VectorCopy(origin, ch->org);
		S_SpatializeChannel(ch);
	}

	volume = snd_volume->value * relVolume * MIX_MAX_VOLUME;
	Com_DPrintf(DEBUG_SOUND, "%i: Playing sample '%s' at volume %f at channel %i\n",
			CL_Milliseconds(), sample->name, volume, i);
	Mix_VolumeChunk(ch->sample->chunk, volume);
	Mix_PlayChannel(i, ch->sample->chunk, 0);
}
Esempio n. 6
0
/**
 * @brief
 */
void S_AddSample(const s_play_sample_t *play) {

	if (!s_env.initialized) {
		return;
	}

	if (!s_volume->value) {
		return;
	}

	if (!play) {
		return;
	}

	if (!play->sample) {
		return;
	}

	if (play->entity >= MAX_ENTITIES) {
		return;
	}

	switch (s_ambient->integer) {
		case 0:
			if (play->flags & S_PLAY_AMBIENT) {
				return;
			}
			break;
		case 2:
			if (!(play->flags & S_PLAY_AMBIENT)) {
				return;
			}
			break;
		default:
			break;

	}

	const s_sample_t *sample = play->sample;

	const char *name = sample->media.name;
	if (name[0] == '*') {
		if (play->entity != -1) {
			const entity_state_t *ent = &cl.entities[play->entity].current;
			sample = S_LoadEntitySample(ent, sample->media.name);
			if (sample == NULL) {
				Com_Debug(DEBUG_SOUND, "Failed to load player model sound %s\n", name);
				return;
			}
		} else {
			Com_Warn("Player model sound %s requested without entity\n", name);
			return;
		}
	}

	// for sounds added every frame, if an instance of the sound already exists, cull this one

	if (play->flags & S_PLAY_FRAME) {
		s_channel_t *ch = s_env.channels;
		for (int32_t i = 0; i < MAX_CHANNELS; i++, ch++) {
			if (ch->sample && (ch->play.flags & S_PLAY_FRAME)) {
				if (memcmp(play, &ch->play, sizeof(*play)) == 0) {
					ch->frame = cl.frame.frame_num;
					return;
				}
			}
		}
	}

	const int32_t i = S_AllocChannel();
	if (i != -1) {
		s_env.channels[i].play = *play;
		s_env.channels[i].sample = sample;
		s_env.channels[i].frame = cl.frame.frame_num;
	}
}