Merge pull request #526 from zsilencer/master

fix some sound issues
This commit is contained in:
Ted John 2014-10-16 19:43:58 +01:00
commit 0b8d13ef9d
10 changed files with 1786 additions and 1419 deletions

File diff suppressed because it is too large Load Diff

View File

@ -36,8 +36,6 @@ extern audio_device *gAudioDevices;
void audio_init();
void audio_quit();
void audio_get_devices();
void audio_init1();
void audio_init2(int device);
#include <dsound.h>
@ -63,9 +61,9 @@ typedef struct rct_sound {
} rct_sound;
typedef struct {
uint32 var_0;
uint32 playing; // 0x000
uint32 var_4;
char filename[MAX_PATH]; // 0x8
char filename[MAX_PATH]; // 0x008
uint32 var_10C;
uint32 var_110;
uint32 var_114;
@ -75,11 +73,11 @@ typedef struct {
MMCKINFO mmckinfo1; // 0x124
MMCKINFO mmckinfo2; // 0x138
LPDIRECTSOUNDBUFFER dsbuffer; // 0x14C
uint32 bufsize;
uint32 bufsize; // 0x150
uint32 playpos; // 0x154
uint32 var_158;
uint32 var_15C;
uint32 var_160;
uint32 stopped; // 0x160
uint32 var_164;
uint32 var_168;
} rct_sound_channel;
@ -92,7 +90,7 @@ typedef struct {
typedef struct {
uint16 id;
uint16 var_2;
sint16 volume; // 0x02
rct_sound sound1; // 0x04
uint16 sound1_id; // 0x18
sint16 sound1_volume; // 0x1A
@ -103,17 +101,17 @@ typedef struct {
sint16 sound2_volume; // 0x36
sint16 sound2_pan; // 0x38
uint16 sound2_freq; // 0x3A
// added to openrct2:
void* sound1_channel;
void* sound2_channel;
} rct_vehicle_sound;
typedef struct {
uint16 id;
sint16 pan; // 0x2
sint16 var_4;
sint16 panx; // 0x2
sint16 pany; // 0x4
uint16 frequency; // 0x6
sint16 var_8;
sint16 volume; // 0x8
uint16 var_A; // 0xA
} rct_vehicle_sound_params;
@ -140,8 +138,8 @@ typedef struct {
} rct_music_info2;
typedef struct {
uint8 var_0;
uint8 pad_1[0x7];
uint32 var_0;
uint32 var_4;
uint8 pathid; //0x8
uint8 var_9;
} rct_music_info3;
@ -151,53 +149,72 @@ extern rct_vehicle_sound_params gVehicleSoundParamsList[AUDIO_MAX_VEHICLE_SOUNDS
extern rct_vehicle_sound_params *gVehicleSoundParamsListEnd;
extern void* gMusicChannels[4];
int get_dsound_devices();
int dsound_create_primary_buffer(int a, int device, int channels, int samples, int bits);
void audio_timefunc(UINT uTimerID, UINT uMsg, DWORD_PTR dwUser, DWORD_PTR dw1, DWORD_PTR dw2, int channel);
int audio_release();
MMRESULT mmio_read(HMMIO hmmio, uint32 size, char* buffer, LPMMCKINFO mmckinfo, int* read);
MMRESULT mmio_seek(HMMIO* hmmio, LPMMCKINFO mmckinfo1, LPMMCKINFO mmckinfo2, int offset);
MMRESULT mmio_open(const char* filename, HMMIO* hmmio, HGLOBAL* hmem, LPMMCKINFO mmckinfo);
int CALLBACK audio_timer_callback(UINT uTimerID, UINT uMsg, DWORD_PTR dwUser, DWORD_PTR dw1, DWORD_PTR dw2);
int sub_40153B(int channel);
int sub_4015E7(int channel);
void sub_401AF3(int channel, const char* filename, int a3, int a4);
int sub_401B63(int channel);
void sub_6BC6D8();
int sound_channel_load_file(int channel, const char* filename, int offset);
int mmio_open_channel(int channel, char* filename, LONG offset);
int audio_create_timer();
int audio_remove_timer();
void audio_close();
LPVOID map_file(LPCSTR lpFileName, DWORD dwCreationDisposition, DWORD dwNumberOfBytesToMap);
int unmap_sound_effects();
int sound_prepare(int sound_id, rct_sound *sound, int channels, int software);
int sound_play_panned(int sound_id, int ebx, sint16 x, sint16 y, sint16 z);
int sound_play(rct_sound* sound, int looping, int volume, int pan, int frequency);
int sound_is_playing(rct_sound* sound);
int sound_set_frequency(rct_sound* sound, int frequency);
int sound_set_pan(rct_sound* sound, int pan);
int sound_set_volume(rct_sound* sound, int volume);
int sound_channel_load_file2(int channel, const char* filename, int offset);
int sound_channel_play(int channel, int a2, int volume, int pan, int frequency);
int sound_channel_stop(int channel);
int sound_channel_set_frequency(int channel, int frequency);
int sound_channel_set_pan(int channel, int pan);
int sound_channel_set_volume(int channel, int volume);
int sound_channel_load_file2(int channel, const char* filename, int offset);
int sound_channel_load_file(int channel, const char* filename, int offset);
void sound_channel_free(HMMIO* hmmio, HGLOBAL* hmem);
void sub_401AF3(int channel, const char* filename, int a3, int a4);
int sub_401B46(int channel);
int sound_channel_is_playing(int channel);
int audio_release();
int map_sound_effects(const char* filename);
int unmap_sound_effects();
int sound_prepare(int sound_id, rct_sound *sound, int channels, int software);
int sound_duplicate(rct_sound* newsound, rct_sound* sound);
int sound_stop(rct_sound *sound);
int sound_stop_all();
int unmap_file(LPCVOID base);
int sound_channel_stop(int channel);
rct_sound* sound_add(rct_sound* sound);
rct_sound* sound_remove(rct_sound* sound);
void sound_bufferlost_check();
int sound_is_playing(rct_sound* sound);
int sound_play(rct_sound* sound, int looping, int volume, int pan, int frequency);
int sound_set_frequency(rct_sound* sound, int frequency);
int sound_set_pan(rct_sound* sound, int pan);
int sound_set_volume(rct_sound* sound, int volume);
int sound_load3dparameters();
int sound_load3dposition();
BOOL CALLBACK dsound_enum_callback_count(LPGUID lpGuid, LPCSTR lpcstrDescription, LPCSTR lpcstrModule, LPVOID lpContext);
int dsound_count_devices();
BOOL CALLBACK dsound_enum_callback(LPGUID lpGuid, LPCSTR lpcstrDescription, LPCSTR lpcstrModule, LPVOID lpContext);
int sound_effect_loadvars(rct_sound_effect* sound_effect, LPWAVEFORMATEX* waveformat, char** data, DWORD* buffersize);
int sound_fill_buffer(LPDIRECTSOUNDBUFFER dsbuffer, char* src, DWORD size);
rct_sound* sound_begin();
rct_sound* sound_next(rct_sound* sound);
void pause_sounds();
rct_sound* sound_add(rct_sound* sound);
rct_sound* sound_remove(rct_sound* sound);
int sound_bufferlost_restore(rct_sound* sound);
rct_sound_effect* sound_get_effect(uint16 sound_id);
MMRESULT mmio_open(const char* filename, HMMIO* hmmio, HGLOBAL* hmem, LPMMCKINFO mmckinfo);
MMRESULT mmio_read(HMMIO hmmio, uint32 size, char* buffer, LPMMCKINFO mmckinfo, int* read);
void sound_channel_free(HMMIO* hmmio, HGLOBAL* hmem);
MMRESULT mmio_seek(HMMIO* hmmio, LPMMCKINFO mmckinfo1, LPMMCKINFO mmckinfo2, int offset);
LPVOID map_file(LPCSTR lpFileName, DWORD dwCreationDisposition, DWORD dwNumberOfBytesToMap);
int unmap_file(LPCVOID base);
int dsound_create_primary_buffer(int a, int device, int channels, int samples, int bits);
int get_dsound_devices();
int sound_play_panned(int sound_id, int ebx, sint16 x, sint16 y, sint16 z);
void stop_completed_sounds();
void start_title_music();
void stop_other_sounds();
void stop_vehicle_sounds();
void stop_ride_music();
void stop_crowd_sound();
void stop_title_music();
void start_title_music();
void audio_init1();
void audio_init2(int device);
void audio_close();
void pause_sounds();
void unpause_sounds();
void stop_vehicle_sounds();
void sub_6BC348();
void sub_6BC6D8();
// 0x009AF59C probably does the same job
// once it's confirmed and calls in pause_sounds() are reversed, it can be used instead of this

View File

@ -201,8 +201,10 @@ Channel::Channel()
resampler = 0;
SetRate(1);
SetVolume(SDL_MIX_MAXVOLUME);
oldvolume = 0;
SetPan(0.5f);
done = true;
stopping = false;
}
Channel::~Channel()
@ -287,7 +289,8 @@ void Mixer::Close()
{
Lock();
while (channels.begin() != channels.end()) {
Stop(*(*channels.begin()));
delete *(channels.begin());
channels.erase(channels.begin());
}
Unlock();
SDL_CloseAudioDevice(deviceid);
@ -311,6 +314,7 @@ Channel* Mixer::Play(Stream& stream, int loop, bool deleteondone)
if (newchannel) {
newchannel->Play(stream, loop);
newchannel->deleteondone = deleteondone;
newchannel->stopping = false;
channels.push_back(newchannel);
}
Unlock();
@ -320,8 +324,7 @@ Channel* Mixer::Play(Stream& stream, int loop, bool deleteondone)
void Mixer::Stop(Channel& channel)
{
Lock();
channels.remove(&channel);
delete &channel;
channel.stopping = true;
Unlock();
}
@ -346,7 +349,7 @@ void SDLCALL Mixer::Callback(void* arg, uint8* stream, int length)
std::list<Channel*>::iterator i = mixer->channels.begin();
while (i != mixer->channels.end()) {
mixer->MixChannel(*(*i), stream, length);
if ((*i)->done && (*i)->deleteondone) {
if (((*i)->done && (*i)->deleteondone) || (*i)->stopping) {
delete (*i);
i = mixer->channels.erase(i);
} else {
@ -358,9 +361,6 @@ void SDLCALL Mixer::Callback(void* arg, uint8* stream, int length)
void Mixer::MixChannel(Channel& channel, uint8* data, int length)
{
if (channel.stream && !channel.done) {
if (!channel.resampler) {
channel.resampler = speex_resampler_init(format.channels, format.freq, format.freq, 0, 0);
}
AudioFormat channelformat = *channel.stream->Format();
int loaded = 0;
SDL_AudioCVT cvt;
@ -410,6 +410,9 @@ void Mixer::MixChannel(Channel& channel, uint8* data, int length)
if (rate != 1 && format.format == AUDIO_S16SYS) {
int in_len = (int)(ceil((double)lengthloaded / samplesize));
int out_len = samples + 20; // needs some extra, otherwise resampler sometimes doesn't process all the input samples
if (!channel.resampler) {
channel.resampler = speex_resampler_init(format.channels, format.freq, format.freq, 0, 0);
}
speex_resampler_set_rate(channel.resampler, format.freq, (int)(format.freq * (1 / rate)));
speex_resampler_process_interleaved_int(channel.resampler, (const spx_int16_t*)tomix, (spx_uint32_t*)&in_len, (spx_int16_t*)effectbuffer, (spx_uint32_t*)&out_len);
effectbufferloaded = true;
@ -438,14 +441,38 @@ void Mixer::MixChannel(Channel& channel, uint8* data, int length)
mixlength = length - loaded;
}
SDL_MixAudioFormat(&data[loaded], tomix, format.format, mixlength, volume);
int startvolume = channel.oldvolume;
int endvolume = channel.volume;
if (channel.stopping) {
endvolume = 0;
}
int mixvolume = volume;
if (startvolume != endvolume) {
// fade between volume levels to smooth out sound and minimize clicks from sudden volume changes
if (!effectbufferloaded) {
memcpy(effectbuffer, tomix, lengthloaded);
effectbufferloaded = true;
tomix = effectbuffer;
}
mixvolume = SDL_MIX_MAXVOLUME; // set to max since we are adjusting the volume ourselves
int fadelength = mixlength / format.BytesPerSample();
switch (format.format) {
case AUDIO_S16SYS:
EffectFadeS16((sint16*)effectbuffer, fadelength, startvolume, endvolume);
break;
case AUDIO_U8:
EffectFadeU8((uint8*)effectbuffer, fadelength, startvolume, endvolume);
break;
}
}
SDL_MixAudioFormat(&data[loaded], tomix, format.format, mixlength, mixvolume);
if (dataconverted) {
delete[] dataconverted;
}
channel.offset += readfromstream;
}
loaded += lengthloaded;
@ -456,7 +483,9 @@ void Mixer::MixChannel(Channel& channel, uint8* data, int length)
}
channel.offset = 0;
}
} while(loaded < length && channel.loop != 0);
} while(loaded < length && channel.loop != 0 && !channel.stopping);
channel.oldvolume = channel.volume;
if (channel.loop == 0 && channel.offset >= channel.stream->Length()) {
channel.done = true;
}
@ -483,6 +512,26 @@ void Mixer::EffectPanU8(Channel& channel, uint8* data, int length)
}
}
void Mixer::EffectFadeS16(sint16* data, int length, int startvolume, int endvolume)
{
float startvolume_f = (float)startvolume / SDL_MIX_MAXVOLUME;
float endvolume_f = (float)endvolume / SDL_MIX_MAXVOLUME;
for (int i = 0; i < length; i++) {
float t = (float)i / length;
data[i] = (sint16)(data[i] * ((1 - t) * startvolume_f + t * endvolume_f));
}
}
void Mixer::EffectFadeU8(uint8* data, int length, int startvolume, int endvolume)
{
float startvolume_f = (float)startvolume / SDL_MIX_MAXVOLUME;
float endvolume_f = (float)endvolume / SDL_MIX_MAXVOLUME;
for (int i = 0; i < length; i++) {
float t = (float)i / length;
data[i] = (uint8)(data[i] * ((1 - t) * startvolume_f + t * endvolume_f));
}
}
bool Mixer::MustConvert(Stream& stream)
{
const AudioFormat* streamformat = stream.Format();

View File

@ -106,6 +106,8 @@ private:
float pan;
bool done;
bool deleteondone;
bool stopping;
int oldvolume;
SpeexResamplerState* resampler;
Stream* stream;
};
@ -129,6 +131,8 @@ private:
void MixChannel(Channel& channel, uint8* buffer, int length);
void EffectPanS16(Channel& channel, sint16* data, int length);
void EffectPanU8(Channel& channel, uint8* data, int length);
void EffectFadeS16(sint16* data, int length, int startvolume, int endvolume);
void EffectFadeU8(uint8* data, int length, int startvolume, int endvolume);
bool MustConvert(Stream& stream);
bool Convert(SDL_AudioCVT& cvt, const uint8* data, unsigned long length, uint8** dataout);
SDL_AudioDeviceID deviceid;

View File

@ -152,6 +152,75 @@ void gfx_transpose_palette(int pal, unsigned char product)
osinterface_update_palette((char*)0x01424680, 10, 236);//Odd would have expected dest_pointer
}
/**
*
* rct2: 0x006EC9CE
* @param x (ax)
* @param y (cx)
* @param base_height (di)
* @param clearance_height (si)
*/
void gfx_invalidate_scrollingtext(int x, int y, int base_height, int clearance_height)
{
x += 16;
y += 16;
int left, top, right, bottom;
switch (RCT2_GLOBAL(RCT2_ADDRESS_CURRENT_ROTATION, uint32)) {
case 0:
left = (-x + y) - 32;
right = (-x + y) + 32;
top = ((y + x) / 2) - 32 - clearance_height;
bottom = ((y + x) / 2) + 32 - base_height;
break;
case 1:
left = (-x - y) - 32;
right = (-x - y) + 32;
top = ((y - x) / 2) - 32 - clearance_height;
bottom = ((y - x) / 2) + 32 - base_height;
break;
case 2:
left = (x - y) - 32;
right = (x - y) + 32;
top = ((-y - x) / 2) - 32 - clearance_height;
bottom = ((-y - x) / 2) + 32 - base_height;
break;
case 3:
left = (x + y) - 32;
right = (x + y) + 32;
top = ((-y + x) / 2) - 32 - clearance_height;
bottom = ((-y + x) / 2) + 32 - base_height;
break;
}
rct_viewport** viewport_p = RCT2_ADDRESS(RCT2_ADDRESS_NEW_VIEWPORT_PTR, rct_viewport*);
while (*viewport_p) {
rct_viewport* viewport = *viewport_p;
if (viewport->zoom < 1) {
if (right > viewport->view_x && bottom > viewport->view_y && left < viewport->view_x + viewport->view_width) {
if (left < viewport->view_x) {
left = viewport->view_x;
}
if (right > viewport->view_x + viewport->view_width) {
right = viewport->view_x + viewport->view_width;
}
if (top < viewport->view_y + viewport->view_height) {
if (top < viewport->view_y) {
top = viewport->view_y;
}
if (bottom > viewport->view_y + viewport->view_height) {
bottom = viewport->view_y + viewport->view_height;
}
left = ((left - viewport->view_x) >> viewport->zoom) + viewport->x;
top = ((top - viewport->view_y) >> viewport->zoom) + viewport->y;
right = ((right - viewport->view_x) >> viewport->zoom) + viewport->x;
bottom = ((bottom - viewport->view_y) >> viewport->zoom) + viewport->y;
gfx_set_dirty_blocks(left, top, right, bottom);
}
}
}
viewport_p++;
}
}
/**
*
* rct2: 0x006ED7E5

View File

@ -70,6 +70,7 @@ rct_drawpixelinfo* clip_drawpixelinfo(rct_drawpixelinfo* dpi, int left, int widt
void gfx_set_dirty_blocks(int left, int top, int right, int bottom);
void gfx_draw_all_dirty_blocks();
void gfx_redraw_screen_rect(short left, short top, short right, short bottom);
void gfx_invalidate_scrollingtext(int x, int y, int base_height, int clearance_height);
void gfx_invalidate_screen();
// palette

View File

@ -141,7 +141,9 @@ typedef struct {
uint32 var_118;
uint8 pad_11C[0x02];
uint8 var_11E;
uint8 pad_11F[0x05];
uint8 var_11F;
sint16 var_120;
sint16 var_122;
sint16 var_124;
sint16 var_126;
sint16 var_128;
@ -153,7 +155,10 @@ typedef struct {
sint16 var_134;
sint16 var_136;
money16 price; // 0x138
uint8 pad_13A[0x06];
sint16 var_13A;
sint16 var_13C;
uint8 var_13E;
uint8 var_13F;
union {
rating_tuple ratings; // 0x140
struct {
@ -163,7 +168,7 @@ typedef struct {
};
};
uint16 reliability; // 0x146
uint16 pad_148;
uint16 var_148;
uint16 var_14A;
uint8 pad_14C;
uint8 var_14D;
@ -173,9 +178,12 @@ typedef struct {
uint16 var_158;
uint8 pad_15A;
uint8 num_riders; // 0x15B
uint8 pad_15C[2];
uint16 maze_tiles;
uint8 pad_160[0x20];
uint8 var_15C;
uint8 var_15D;
uint16 maze_tiles; // 0x15E
uint8 pad_160[0x16];
uint8 var_176;
uint8 pad_177[0x9];
sint16 build_date; // 0x180
money16 upkeep_cost; // 0x182
uint16 race_winner; // 0x184

View File

@ -36,9 +36,11 @@ void vehicle_update_sound_params(rct_vehicle* vehicle)
{
if (!(RCT2_GLOBAL(RCT2_ADDRESS_SCREEN_FLAGS, uint8) & 2) && (!(RCT2_GLOBAL(RCT2_ADDRESS_SCREEN_FLAGS, uint8) & 4) || RCT2_GLOBAL(0x0141F570, uint8) == 6)) {
if (vehicle->sound1_id != (uint8)-1 || vehicle->sound2_id != (uint8)-1) {
if (vehicle->var_16.width != 0x8000) {
RCT2_GLOBAL(0x009AF5A0, rct_widthheight) = vehicle->var_16;
RCT2_GLOBAL(0x009AF5A4, rct_widthheight) = vehicle->view;
if (vehicle->var_16 != 0x8000) {
RCT2_GLOBAL(0x009AF5A0, sint16) = vehicle->var_16;
RCT2_GLOBAL(0x009AF5A2, sint16) = vehicle->var_18;
RCT2_GLOBAL(0x009AF5A4, sint16) = vehicle->var_1A;
RCT2_GLOBAL(0x009AF5A6, sint16) = vehicle->var_1C;
sint16 v4 = RCT2_GLOBAL(0x00F438A4, rct_viewport*)->view_x;
sint16 v5 = RCT2_GLOBAL(0x00F438A4, rct_viewport*)->view_y;
sint16 v6 = RCT2_GLOBAL(0x00F438A4, rct_viewport*)->view_width / 4;
@ -47,14 +49,14 @@ void vehicle_update_sound_params(rct_vehicle* vehicle)
v4 -= v6;
v5 -= v7;
}
if (v4 < RCT2_GLOBAL(0x009AF5A4, rct_widthheight).width && v5 < RCT2_GLOBAL(0x009AF5A4, rct_widthheight).height) {
if (v4 < RCT2_GLOBAL(0x009AF5A4, sint16) && v5 < RCT2_GLOBAL(0x009AF5A6, sint16)) {
sint16 t8 = RCT2_GLOBAL(0x00F438A4, rct_viewport*)->view_width + v4;
sint16 t9 = RCT2_GLOBAL(0x00F438A4, rct_viewport*)->view_height + v5;
if (!RCT2_GLOBAL(0x00F438A8, rct_window*)->classification) {
t8 += v6 + v6;
t9 += v7 + v7;
}
if (t8 >= RCT2_GLOBAL(0x009AF5A0, rct_widthheight).width && t9 >= RCT2_GLOBAL(0x009AF5A0, rct_widthheight).height) {
if (t8 >= RCT2_GLOBAL(0x009AF5A0, sint16) && t9 >= RCT2_GLOBAL(0x009AF5A2, sint16)) {
uint16 v9 = sub_6BC2F3(vehicle);
rct_vehicle_sound_params* i;
//for (i = RCT2_ADDRESS(0x00F438B4, rct_vehicle_sound_params); i < RCT2_GLOBAL(0x00F438B0, rct_vehicle_sound_params*) && v9 <= i->var_A; i++);
@ -74,28 +76,26 @@ void vehicle_update_sound_params(rct_vehicle* vehicle)
*(j + 1) = *j;
}
i->var_A = v9;
rct_widthheight v12;
v12.height = vehicle->var_16.height;
v12.width = ((uint16)RCT2_GLOBAL(0x009AF5A0, rct_widthheight).width / 2) + ((uint16)RCT2_GLOBAL(0x009AF5A4, rct_widthheight).width / 2) - RCT2_GLOBAL(0x00F438A4, rct_viewport*)->view_x;
v12.width >>= RCT2_GLOBAL(0x00F438A4, rct_viewport*)->zoom;
v12.width += RCT2_GLOBAL(0x00F438A4, rct_viewport*)->x;
int panx = (RCT2_GLOBAL(0x009AF5A0, sint16) / 2) + (RCT2_GLOBAL(0x009AF5A4, sint16) / 2) - RCT2_GLOBAL(0x00F438A4, rct_viewport*)->view_x;
panx >>= RCT2_GLOBAL(0x00F438A4, rct_viewport*)->zoom;
panx += RCT2_GLOBAL(0x00F438A4, rct_viewport*)->x;
uint16 v14 = RCT2_GLOBAL(RCT2_ADDRESS_SCREEN_WIDTH, uint16);
if (v14 < 64) {
v14 = 64;
uint16 screenwidth = RCT2_GLOBAL(RCT2_ADDRESS_SCREEN_WIDTH, uint16);
if (screenwidth < 64) {
screenwidth = 64;
}
rct_widthheight v15;
i->pan = (((((uint32)v12.width << 16) / v14) - 0x8000) >> 4);
v15.width = 0;
v15.height = (RCT2_GLOBAL(0x009AF5A0, rct_widthheight).height / 2) + (RCT2_GLOBAL(0x009AF5A4, rct_widthheight).height / 2) - RCT2_GLOBAL(0x00F438A4, rct_viewport*)->view_y;
v15.height >>= RCT2_GLOBAL(0x00F438A4, rct_viewport*)->zoom;
v15.height += RCT2_GLOBAL(0x00F438A4, rct_viewport*)->y;
i->panx = ((((panx << 16) / screenwidth) - 0x8000) >> 4);
uint16 v18 = RCT2_GLOBAL(RCT2_ADDRESS_SCREEN_HEIGHT, uint16);
if (v18 < 64) {
v18 = 64;
int pany = (RCT2_GLOBAL(0x009AF5A2, sint16) / 2) + (RCT2_GLOBAL(0x009AF5A6, sint16) / 2) - RCT2_GLOBAL(0x00F438A4, rct_viewport*)->view_y;
pany >>= RCT2_GLOBAL(0x00F438A4, rct_viewport*)->zoom;
pany += RCT2_GLOBAL(0x00F438A4, rct_viewport*)->y;
uint16 screenheight = RCT2_GLOBAL(RCT2_ADDRESS_SCREEN_HEIGHT, uint16);
if (screenheight < 64) {
screenheight = 64;
}
i->var_4 = (sint16)(((v15.both / v18) - 0x8000) >> 4);
i->pany = ((((pany << 16) / screenheight) - 0x8000) >> 4);
sint32 v19 = vehicle->velocity;
int testaddr = (vehicle->var_31 * 0x65);
@ -115,14 +115,13 @@ void vehicle_update_sound_params(rct_vehicle* vehicle)
v19 += 16 * vehicle->var_BF;
i->frequency = (uint16)v19;
i->id = vehicle->sprite_index;
i->var_8 = 0;
i->volume = 0;
if (vehicle->x != 0x8000) {
uint16 v22 = (vehicle->y & 0xFFE0) << 8;
v22 |= (vehicle->x & 0xFFE0 | v22) & 0xFFFF;
int tile_idx = (((vehicle->y & 0xFFE0) * 256) + (vehicle->x & 0xFFE0)) / 32;
rct_map_element* map_element;
for (map_element = RCT2_ADDRESS(RCT2_ADDRESS_TILE_MAP_ELEMENT_POINTERS, rct_map_element*)[v22 >> 3]; map_element->type & MAP_ELEMENT_TYPE_MASK; map_element++);
if (map_element->base_height * 8 > vehicle->z) {
i->var_8 = 0x30;
for (map_element = RCT2_ADDRESS(RCT2_ADDRESS_TILE_MAP_ELEMENT_POINTERS, rct_map_element*)[tile_idx]; map_element->type & MAP_ELEMENT_TYPE_MASK; map_element++);
if (map_element->base_height * 8 > vehicle->z) { // vehicle underground
i->volume = 0x30;
}
}
}
@ -149,7 +148,8 @@ int sub_6BC2F3(rct_vehicle* vehicle)
v4 = -v4;
}
result += ((uint16)v4) >> 13;
rct_vehicle_sound* vehicle_sound = &gVehicleSoundList[0];//RCT2_ADDRESS(RCT2_ADDRESS_VEHICLE_SOUND_LIST, rct_vehicle_sound);
rct_vehicle_sound* vehicle_sound = &gVehicleSoundList[0];
//rct_vehicle_sound* vehicle_sound = RCT2_ADDRESS(RCT2_ADDRESS_VEHICLE_SOUND_LIST, rct_vehicle_sound);
while (vehicle_sound->id != vehicle->sprite_index) {
vehicle_sound++;
//if (vehicle_sound >= RCT2_GLOBAL(0x009AF42C, rct_vehicle_sound*)) {
@ -194,8 +194,6 @@ void vehicle_sounds_update()
for (uint16 i = RCT2_GLOBAL(RCT2_ADDRESS_SPRITES_START_VEHICLE, uint16); i != SPRITE_INDEX_NULL; i = g_sprite_list[i].vehicle.next) {
vehicle_update_sound_params(&g_sprite_list[i].vehicle);
}
//printf("vehicle sounds: %d\n", (gVehicleSoundParamsListEnd - &gVehicleSoundParamsList[0]));
//RCT2_ADDRESS_VEHICLE_SOUND_LIST;
//for (rct_vehicle_sound* vehicle_sound = &RCT2_GLOBAL(RCT2_ADDRESS_VEHICLE_SOUND_LIST, rct_vehicle_sound); vehicle_sound != &RCT2_GLOBAL(0x009AF42C, rct_vehicle_sound); vehicle_sound++) {
for(int i = 0; i < countof(gVehicleSoundList); i++){
rct_vehicle_sound* vehicle_sound = &gVehicleSoundList[i];
@ -239,43 +237,43 @@ void vehicle_sounds_update()
}
uint8 vol1 = 0xFF;
uint8 vol2 = 0xFF;
sint16 v = vehicle_sound_params->var_4;
if (v < 0) {
v = -v;
sint16 pany = vehicle_sound_params->pany;
if (pany < 0) {
pany = -pany;
}
if (v > 0xFFF) {
v = 0xFFF;
if (pany > 0xFFF) {
pany = 0xFFF;
}
v -= 0x800;
if (v > 0) {
v -= 0x400;
v = -v;
v = (uint16)v / 4;
vol1 = LOBYTE(v);
if (HIBYTE(v) != 0) {
pany -= 0x800;
if (pany > 0) {
pany -= 0x400;
pany = -pany;
pany = pany / 4;
vol1 = LOBYTE(pany);
if ((sint8)HIBYTE(pany) != 0) {
vol1 = 0xFF;
if (HIBYTE(v) < 0) {
if ((sint8)HIBYTE(pany) < 0) {
vol1 = 0;
}
}
}
sint16 w = vehicle_sound_params->pan;
if (w < 0) {
w = -w;
sint16 panx = vehicle_sound_params->panx;
if (panx < 0) {
panx = -panx;
}
if (w > 0xFFF) {
w = 0xFFF;
if (panx > 0xFFF) {
panx = 0xFFF;
}
w -= 0x800;
if (w > 0) {
w -= 0x400;
w = -w;
w = (uint16)w / 4;
vol2 = LOBYTE(w);
if (HIBYTE(w) != 0) {
panx -= 0x800;
if (panx > 0) {
panx -= 0x400;
panx = -panx;
panx = panx / 4;
vol2 = LOBYTE(panx);
if ((sint8)HIBYTE(panx) != 0) {
vol2 = 0xFF;
if (HIBYTE(w) < 0) {
if ((sint8)HIBYTE(panx) < 0) {
vol2 = 0;
}
}
@ -290,17 +288,19 @@ void vehicle_sounds_update()
vol1 = vol1 - RCT2_GLOBAL(RCT2_ADDRESS_VOLUME_ADJUST_ZOOM, uint8);
}
rct_vehicle_sound* vehicle_sound = &gVehicleSoundList[0];//&RCT2_GLOBAL(RCT2_ADDRESS_VEHICLE_SOUND_LIST, rct_vehicle_sound);
rct_vehicle_sound* vehicle_sound = &gVehicleSoundList[0];
//rct_vehicle_sound* vehicle_sound = &RCT2_GLOBAL(RCT2_ADDRESS_VEHICLE_SOUND_LIST, rct_vehicle_sound);
while (vehicle_sound_params->id != vehicle_sound->id) {
vehicle_sound++;
vehicle_sound++; // went here 2x
//if (vehicle_sound >= &RCT2_GLOBAL(0x009AF42C, rct_vehicle_sound)) {
if (vehicle_sound >= &gVehicleSoundList[countof(gVehicleSoundList)]) {
vehicle_sound = &gVehicleSoundList[0];//&RCT2_GLOBAL(RCT2_ADDRESS_VEHICLE_SOUND_LIST, rct_vehicle_sound);
//vehicle_sound = &RCT2_GLOBAL(RCT2_ADDRESS_VEHICLE_SOUND_LIST, rct_vehicle_sound);
vehicle_sound = &gVehicleSoundList[0];
int i = 0;
while (vehicle_sound->id != (uint16)-1) {
vehicle_sound++;
i++;
if (i >= countof(gVehicleSoundList)/*RCT2_GLOBAL(0x009AAC75, uint8)*/) {
if (i >= countof(gVehicleSoundList)/*i >= RCT2_GLOBAL(0x009AAC75, uint8)*/) {
vehicle_sound_params = (rct_vehicle_sound_params*)((int)vehicle_sound_params + 10);
goto label28;
}
@ -308,31 +308,31 @@ void vehicle_sounds_update()
vehicle_sound->id = vehicle_sound_params->id;
vehicle_sound->sound1_id = (uint16)-1;
vehicle_sound->sound2_id = (uint16)-1;
vehicle_sound->var_2 = 0x30;
vehicle_sound->volume = 0x30;
break;
}
}
uint8 v21 = vehicle_sound_params->var_8 & 0xFF;
uint8 v22 = vehicle_sound->var_2 & 0xFF;
if (v22 != v21) {
if (v22 < v21) {
v22 += 4;
int tempvolume = vehicle_sound->volume;
if (tempvolume != vehicle_sound_params->volume) {
if (tempvolume < vehicle_sound_params->volume) {
tempvolume += 4;
} else {
v22 -= 4;
tempvolume -= 4;
}
}
vehicle_sound->var_2 = v22;
if (vol1 < v22) {
vehicle_sound->volume = tempvolume;
if (vol1 < tempvolume) {
vol1 = 0;
} else {
vol1 = vol1 - v22;
vol1 = vol1 - tempvolume;
}
// do sound1 stuff, track noise
rct_sprite* sprite = &g_sprite_list[vehicle_sound_params->id];
sint16 volume = sprite->vehicle.sound1_volume;
int volume = sprite->vehicle.sound1_volume;
volume *= vol1;
volume = (uint16)volume / 8;
volume = volume / 8;
volume -= 0x1FFF;
if (volume < -10000) {
volume = -10000;
@ -367,7 +367,7 @@ void vehicle_sounds_update()
sound_prepare(sprite->vehicle.sound1_id, &vehicle_sound->sound1, 1, RCT2_GLOBAL(RCT2_ADDRESS_CONFIG_SOUND_SW_BUFFER, uint32));
RCT2_GLOBAL(0x014241BC, uint32) = 0;
#endif
vehicle_sound->sound1_pan = vehicle_sound_params->pan;
vehicle_sound->sound1_pan = vehicle_sound_params->panx;
vehicle_sound->sound1_volume = volume;
vehicle_sound->sound1_freq = vehicle_sound_params->frequency;
uint16 frequency = vehicle_sound_params->frequency;
@ -375,7 +375,7 @@ void vehicle_sounds_update()
frequency = (frequency / 2) + 4000;
}
uint8 looping = RCT2_ADDRESS(0x009AF51E, uint8)[2 * sprite->vehicle.sound1_id];
int pan = vehicle_sound_params->pan;
int pan = vehicle_sound_params->panx;
if (!RCT2_GLOBAL(0x009AAC6D, uint8)) {
pan = 0;
}
@ -398,14 +398,14 @@ void vehicle_sounds_update()
RCT2_GLOBAL(0x014241BC, uint32) = 0;
#endif
}
if (vehicle_sound_params->pan != vehicle_sound->sound1_pan) {
vehicle_sound->sound1_pan = vehicle_sound_params->pan;
if (vehicle_sound_params->panx != vehicle_sound->sound1_pan) {
vehicle_sound->sound1_pan = vehicle_sound_params->panx;
if (RCT2_GLOBAL(0x009AAC6D, uint8)) {
#ifdef USE_MIXER
Mixer_Channel_Pan(vehicle_sound->sound1_channel, DStoMixerPan(vehicle_sound_params->pan));
Mixer_Channel_Pan(vehicle_sound->sound1_channel, DStoMixerPan(vehicle_sound_params->panx));
#else
RCT2_GLOBAL(0x014241BC, uint32) = 1;
sound_set_pan(&vehicle_sound->sound1, vehicle_sound_params->pan);
sound_set_pan(&vehicle_sound->sound1, vehicle_sound_params->panx);
RCT2_GLOBAL(0x014241BC, uint32) = 0;
#endif
}
@ -464,7 +464,7 @@ void vehicle_sounds_update()
sound_prepare(sprite->vehicle.sound2_id, &vehicle_sound->sound2, 1, RCT2_GLOBAL(RCT2_ADDRESS_CONFIG_SOUND_SW_BUFFER, uint32));
RCT2_GLOBAL(0x014241BC, uint32) = 0;
#endif
vehicle_sound->sound2_pan = vehicle_sound_params->pan;
vehicle_sound->sound2_pan = vehicle_sound_params->panx;
vehicle_sound->sound2_volume = volume;
vehicle_sound->sound2_freq = vehicle_sound_params->frequency;
uint16 frequency = vehicle_sound_params->frequency;
@ -476,7 +476,7 @@ void vehicle_sounds_update()
frequency = 25700;
}
uint8 looping = RCT2_ADDRESS(0x009AF51E, uint8)[2 * sprite->vehicle.sound2_id];
int pan = vehicle_sound_params->pan;
int pan = vehicle_sound_params->panx;
if (!RCT2_GLOBAL(0x009AAC6D, uint8)) {
pan = 0;
}
@ -499,14 +499,14 @@ void vehicle_sounds_update()
#endif
vehicle_sound->sound2_volume = volume;
}
if (vehicle_sound_params->pan != vehicle_sound->sound2_pan) {
vehicle_sound->sound2_pan = vehicle_sound_params->pan;
if (vehicle_sound_params->panx != vehicle_sound->sound2_pan) {
vehicle_sound->sound2_pan = vehicle_sound_params->panx;
if (RCT2_GLOBAL(0x009AAC6D, uint8)) {
#ifdef USE_MIXER
Mixer_Channel_Pan(vehicle_sound->sound2_channel, DStoMixerPan(vehicle_sound_params->pan));
Mixer_Channel_Pan(vehicle_sound->sound2_channel, DStoMixerPan(vehicle_sound_params->panx));
#else
RCT2_GLOBAL(0x014241BC, uint32) = 1;
sound_set_pan(&vehicle_sound->sound2, vehicle_sound_params->pan);
sound_set_pan(&vehicle_sound->sound2, vehicle_sound_params->panx);
RCT2_GLOBAL(0x014241BC, uint32) = 0;
#endif
}

View File

@ -23,14 +23,6 @@
#include "../common.h"
typedef union {
struct {
sint16 width;
sint16 height;
};
sint32 both;
} rct_widthheight;
typedef struct {
uint8 sprite_identifier; // 0x00
uint8 pad_01[0x03];
@ -44,8 +36,10 @@ typedef struct {
sint16 y; // 0x10
sint16 z; // 0x12
uint8 pad_14[0x02];
rct_widthheight var_16;
rct_widthheight view; // 0x1A
sint16 var_16;
sint16 var_18;
sint16 var_1A;
sint16 var_1C;
uint16 var_1E;
uint8 pad_20[0x08];
sint32 velocity; // 0x28

View File

@ -476,11 +476,11 @@ static void window_options_dropdown()
audio_init2(dropdownIndex);
if (dropdownIndex < gAudioDeviceCount) {
#ifdef USE_MIXER
int devicenum = dropdownIndex;
if (devicenum == 0) {
devicenum = 1;
if (dropdownIndex == 0) {
Mixer_Init(NULL);
} else {
Mixer_Init(gAudioDevices[dropdownIndex].name);
}
Mixer_Init(gAudioDevices[devicenum].name);
#endif
}
/*#ifdef _MSC_VER