⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 soundux.cpp

📁 SFC游戏模拟器 snes9x 1.43 的原代码
💻 CPP
📖 第 1 页 / 共 4 页
字号:
					{						ch->env_error &= FIXED_POINT_REMAINDER;						ch->envx += step << 1;						ch->envxx = ch->envx << ENVX_SHIFT;					}										if (ch->envx >= 126)					{						ch->envx = 127;						ch->envxx = 127 << ENVX_SHIFT;						ch->state = SOUND_GAIN;						ch->mode = MODE_GAIN;						S9xSetEnvRate (ch, 0, -1, 0);					}					break;									case SOUND_DECREASE_LINEAR:					ch->env_error &= FIXED_POINT_REMAINDER;					ch->envx -= step << 1;					ch->envxx = ch->envx << ENVX_SHIFT;					if (ch->envx <= 0)					{						S9xAPUSetEndOfSample (J, ch);						goto stereo_exit;					}					break;									case SOUND_DECREASE_EXPONENTIAL:					while (ch->env_error >= FIXED_POINT)					{						ch->envxx = (ch->envxx >> 8) * 255;						ch->env_error -= FIXED_POINT;					}					ch->envx = ch->envxx >> ENVX_SHIFT;					if (ch->envx <= 0)					{						S9xAPUSetEndOfSample (J, ch);						goto stereo_exit;					}					break;									case SOUND_GAIN:					S9xSetEnvRate (ch, 0, -1, 0);					break;		}		ch-> left_vol_level = (ch->envx * ch->volume_left) / 128;		ch->right_vol_level = (ch->envx * ch->volume_right) / 128;		VL = (ch->sample * ch-> left_vol_level) / 128;		VR = (ch->sample * ch->right_vol_level) / 128;		}		ch->count += freq;		if (ch->count >= FIXED_POINT)		{			VL = ch->count >> FIXED_POINT_SHIFT;			ch->sample_pointer += VL;			ch->count &= FIXED_POINT_REMAINDER;			ch->sample = ch->next_sample;			if (ch->sample_pointer >= SOUND_DECODE_LENGTH)			{				if (JUST_PLAYED_LAST_SAMPLE(ch))				{					S9xAPUSetEndOfSample (J, ch);					goto stereo_exit;				}				do				{					ch->sample_pointer -= SOUND_DECODE_LENGTH;					if (ch->last_block)					{						if (!ch->loop)						{							ch->sample_pointer = LAST_SAMPLE;							ch->next_sample = ch->sample;							break;						}						else						{							S9xAPUSetEndX (J);							ch->last_block = FALSE;							uint8 *dir = S9xGetSampleAddress (ch->sample_number);							ch->block_pointer = READ_WORD(dir + 2);						}					}					DecodeBlock (ch);				} while (ch->sample_pointer >= SOUND_DECODE_LENGTH);				if (!JUST_PLAYED_LAST_SAMPLE (ch))					ch->next_sample = ch->block [ch->sample_pointer];			}			else				ch->next_sample = ch->block [ch->sample_pointer];						if (ch->type == SOUND_SAMPLE)			{				if (Settings.InterpolatedSound && freq < FIXED_POINT && !mod)				{					ch->interpolate = ((ch->next_sample - ch->sample) * 					(long) freq) / (long) FIXED_POINT;					ch->sample = (int16) (ch->sample + (((ch->next_sample - ch->sample) * 					(long) (ch->count)) / (long) FIXED_POINT));				}		  				else					ch->interpolate = 0;			}			else			{				for (;VL > 0; VL--)					if ((so.noise_gen <<= 1) & 0x80000000L)						so.noise_gen ^= 0x0040001L;					ch->sample = (so.noise_gen << 17) >> 17;					ch->interpolate = 0;			}						VL = (ch->sample * ch-> left_vol_level) / 128;			VR = (ch->sample * ch->right_vol_level) / 128;		}		else		{			if (ch->interpolate)			{			int32 s = (int32) ch->sample + ch->interpolate;						 CLIP16(s);			 ch->sample = (int16) s;			 VL = (ch->sample * ch-> left_vol_level) / 128;			 VR = (ch->sample * ch->right_vol_level) / 128;			 }		}				if (pitch_mod & (1 << (J + 1)))			wave [I / 2] = ch->sample * ch->envx;				MixBuffer [I      ^ Settings.ReverseStereo] += VL;		MixBuffer [I + (1 ^ Settings.ReverseStereo)] += VR;		ch->echo_buf_ptr [I      ^ Settings.ReverseStereo] += VL;		ch->echo_buf_ptr [I + (1 ^ Settings.ReverseStereo)] += VR;        }stereo_exit: ;    }}#ifdef __DJGPPEND_OF_FUNCTION(MixStereo);#endifvoid MixMono (int sample_count){    static int wave[SOUND_BUFFER_SIZE];    int pitch_mod = SoundData.pitch_mod & (~APU.DSP[APU_NON]);	    for (uint32 J = 0; J < NUM_CHANNELS; J++)     {		Channel *ch = &SoundData.channels[J];		unsigned long freq0 = ch->frequency;				if (ch->state == SOUND_SILENT || !(so.sound_switch & (1 << J)))			continue;				//	freq0 = (unsigned long) ((double) freq0 * 0.985);				bool8 mod = pitch_mod & (1 << J);				if (ch->needs_decode) 		{			DecodeBlock(ch);			ch->needs_decode = FALSE;			ch->sample = ch->block[0];			ch->sample_pointer = freq0 >> FIXED_POINT_SHIFT;			if (ch->sample_pointer == 0)				ch->sample_pointer = 1;			if (ch->sample_pointer > SOUND_DECODE_LENGTH)				ch->sample_pointer = SOUND_DECODE_LENGTH - 1;			ch->next_sample = ch->block[ch->sample_pointer];			ch->interpolate = 0;						if (Settings.InterpolatedSound && freq0 < FIXED_POINT && !mod)				ch->interpolate = ((ch->next_sample - ch->sample) * 				(long) freq0) / (long) FIXED_POINT;		}		int32 V = (ch->sample * ch->left_vol_level) / 128;				for (uint32 I = 0; I < (uint32) sample_count; I++)		{			unsigned long freq = freq0;						if (mod)				freq = PITCH_MOD(freq, wave [I]);						ch->env_error += ch->erate;			if (ch->env_error >= FIXED_POINT) 			{				uint32 step = ch->env_error >> FIXED_POINT_SHIFT;								switch (ch->state)				{				case SOUND_ATTACK:					ch->env_error &= FIXED_POINT_REMAINDER;					ch->envx += step << 1;					ch->envxx = ch->envx << ENVX_SHIFT;										if (ch->envx >= 126)					{						ch->envx = 127;						ch->envxx = 127 << ENVX_SHIFT;						ch->state = SOUND_DECAY;						if (ch->sustain_level != 8) 						{							S9xSetEnvRate (ch, ch->decay_rate, -1,								(MAX_ENVELOPE_HEIGHT * ch->sustain_level)								>> 3);							break;						}						ch->state = SOUND_SUSTAIN;						S9xSetEnvRate (ch, ch->sustain_rate, -1, 0);					}					break;									case SOUND_DECAY:					while (ch->env_error >= FIXED_POINT)					{						ch->envxx = (ch->envxx >> 8) * 255;						ch->env_error -= FIXED_POINT;					}					ch->envx = ch->envxx >> ENVX_SHIFT;					if (ch->envx <= ch->envx_target)					{						if (ch->envx <= 0)						{							S9xAPUSetEndOfSample (J, ch);							goto mono_exit;						}						ch->state = SOUND_SUSTAIN;						S9xSetEnvRate (ch, ch->sustain_rate, -1, 0);					}					break;									case SOUND_SUSTAIN:					while (ch->env_error >= FIXED_POINT)					{						ch->envxx = (ch->envxx >> 8) * 255;						ch->env_error -= FIXED_POINT;					}					ch->envx = ch->envxx >> ENVX_SHIFT;					if (ch->envx <= 0)					{						S9xAPUSetEndOfSample (J, ch);						goto mono_exit;					}					break;									case SOUND_RELEASE:					while (ch->env_error >= FIXED_POINT)					{						ch->envxx -= (MAX_ENVELOPE_HEIGHT << ENVX_SHIFT) / 256;						ch->env_error -= FIXED_POINT;					}					ch->envx = ch->envxx >> ENVX_SHIFT;					if (ch->envx <= 0)					{						S9xAPUSetEndOfSample (J, ch);						goto mono_exit;					}					break;									case SOUND_INCREASE_LINEAR:					ch->env_error &= FIXED_POINT_REMAINDER;					ch->envx += step << 1;					ch->envxx = ch->envx << ENVX_SHIFT;										if (ch->envx >= 126)					{						ch->envx = 127;						ch->envxx = 127 << ENVX_SHIFT;						ch->state = SOUND_GAIN;						ch->mode = MODE_GAIN;						S9xSetEnvRate (ch, 0, -1, 0);					}					break;									case SOUND_INCREASE_BENT_LINE:					if (ch->envx >= (MAX_ENVELOPE_HEIGHT * 3) / 4)					{						while (ch->env_error >= FIXED_POINT)						{							ch->envxx += (MAX_ENVELOPE_HEIGHT << ENVX_SHIFT) / 256;							ch->env_error -= FIXED_POINT;						}						ch->envx = ch->envxx >> ENVX_SHIFT;					}					else					{						ch->env_error &= FIXED_POINT_REMAINDER;						ch->envx += step << 1;						ch->envxx = ch->envx << ENVX_SHIFT;					}										if (ch->envx >= 126)					{						ch->envx = 127;						ch->envxx = 127 << ENVX_SHIFT;						ch->state = SOUND_GAIN;						ch->mode = MODE_GAIN;						S9xSetEnvRate (ch, 0, -1, 0);					}					break;									case SOUND_DECREASE_LINEAR:					ch->env_error &= FIXED_POINT_REMAINDER;					ch->envx -= step << 1;					ch->envxx = ch->envx << ENVX_SHIFT;					if (ch->envx <= 0)					{						S9xAPUSetEndOfSample (J, ch);						goto mono_exit;					}					break;									case SOUND_DECREASE_EXPONENTIAL:					while (ch->env_error >= FIXED_POINT)					{						ch->envxx = (ch->envxx >> 8) * 255;						ch->env_error -= FIXED_POINT;					}					ch->envx = ch->envxx >> ENVX_SHIFT;					if (ch->envx <= 0)					{						S9xAPUSetEndOfSample (J, ch);						goto mono_exit;					}					break;									case SOUND_GAIN:					S9xSetEnvRate (ch, 0, -1, 0);					break;		}		ch->left_vol_level = (ch->envx * ch->volume_left) / 128;		V = (ch->sample * ch->left_vol_level) / 128;		}				ch->count += freq;		if (ch->count >= FIXED_POINT)		{			V = ch->count >> FIXED_POINT_SHIFT;			ch->sample_pointer += V;			ch->count &= FIXED_POINT_REMAINDER;						ch->sample = ch->next_sample;			if (ch->sample_pointer >= SOUND_DECODE_LENGTH)			{				if (JUST_PLAYED_LAST_SAMPLE(ch))				{					S9xAPUSetEndOfSample (J, ch);					goto mono_exit;				}				do				{					ch->sample_pointer -= SOUND_DECODE_LENGTH;					if (ch->last_block)					{						if (!ch->loop)						{							ch->sample_pointer = LAST_SAMPLE;							ch->next_sample = ch->sample;							break;						}						else						{							ch->last_block = FALSE;							uint8 *dir = S9xGetSampleAddress (ch->sample_number);							ch->block_pointer = READ_WORD(dir + 2);							S9xAPUSetEndX (J);						}					}					DecodeBlock (ch);				} while (ch->sample_pointer >= SOUND_DECODE_LENGTH);				if (!JUST_PLAYED_LAST_SAMPLE (ch))					ch->next_sample = ch->block [ch->sample_pointer];			}			else				ch->next_sample = ch->block [ch->sample_pointer];						if (ch->type == SOUND_SAMPLE)			{				if (Settings.InterpolatedSound && freq < FIXED_POINT && !mod)				{					ch->interpolate = ((ch->next_sample - ch->sample) * 						(long) freq) / (long) FIXED_POINT;					ch->sample = (int16) (ch->sample + (((ch->next_sample - ch->sample) * 						(long) (ch->count)) / (long) FIXED_POINT));				}		  				else					ch->interpolate = 0;			}			else			{				for (;V > 0; V--)					if ((so.noise_gen <<= 1) & 0x80000000L)						so.noise_gen ^= 0x0040001L;					ch->sample = (so.noise_gen << 17) >> 17;					ch->interpolate = 0;			}			V = (ch->sample * ch-> left_vol_level) / 128;		}		else		{			if (ch->interpolate)			{				int32 s = (int32) ch->sample + ch->interpolate;								CLIP16(s);				ch->sample = (int16) s;				V = (ch->sample * ch-> left_vol_level) / 128;			}		}				MixBuffer [I] += V;		ch->echo_buf_ptr [I] += V;				if (pitch_mod & (1 << (J + 1)))			wave [I] = ch->sample * ch->envx;        }mono_exit: ;    }}#ifdef __DJGPPEND_OF_FUNCTION(MixMono);#endif#ifdef __sunextern uint8 int2ulaw (int);#endif// For backwards compatibility with older port specific codevoid S9xMixSamplesO (uint8 *buffer, int sample_count, int byte_offset){    S9xMixSamples (buffer+byte_offset, sample_count);}#ifdef __DJGPPEND_OF_FUNCTION(S9xMixSamplesO);#endifvoid S9xMixSamples (uint8 *buffer, int sample_count){    int J;    int I;	    if (!so.mute_sound)    {		memset (MixBuffer, 0, sample_count * sizeof (MixBuffer [0]));		if (SoundData.echo_enable)			memset (EchoBuffer, 0, sample_count * sizeof (EchoBuffer [0]));				if (so.stereo)			MixStereo (sample_count);		else			MixMono (sample_count);    }	    /* Mix and convert waveforms */    if (so.sixteen_bit)    {		int byte_count = sample_count << 1;				// 16-bit sound		if (so.mute_sound)		{            memset (buffer, 0, byte_count);		}		else		{			if (SoundData.echo_enable && SoundData.echo_buffer_size)			{				if (so.stereo)				{					// 16-bit stereo sound with echo enabled ...					if (SoundData.no_filter)					{						// ... but no filter defined.						for (J = 0; J < sample_count; J++)						{							int E = Echo [SoundData.echo_ptr];														Echo [SoundData.echo_ptr] = (E * SoundData.echo_feedback) / 128 +								EchoBuffer [J];														if ((SoundData.echo_ptr += 1) >= SoundData.echo_buffer_size)								SoundData.echo_ptr = 0;														I = (MixBuffer [J] * 								SoundData.master_volume [J & 1] +								E * SoundData.echo_volume [J & 1]) / VOL_DIV16;														CLIP16(I);							((signed short *) buffer)[J] = I;						}					}					else					{						// ... with filter defined.						for (J = 0; J < sample_count; J++)						{							int E = Echo [SoundData.echo_ptr];														Loop [(Z - 0) & 15] = E;							E =  E                    * FilterTaps [0];							E += Loop [(Z -  2) & 15] * FilterTaps [1];							E += Loop [(Z -  4) & 15] * FilterTaps [2];							E += Loop [(Z -  6) & 15] * FilterTaps [3];							E += Loop [(Z -  8) & 15] * FilterTaps [4];

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -