From aba523d14e16d5bcca0e29f29ad9ecf3562093cf Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Fri, 22 May 2020 17:23:04 +0300 Subject: [PATCH 01/14] submodules --- .gitmodules | 12 ++++++++++++ ogg | 1 + opus | 1 + opusfile | 1 + 4 files changed, 15 insertions(+) create mode 160000 ogg create mode 160000 opus create mode 160000 opusfile diff --git a/.gitmodules b/.gitmodules index fec30cac..bf1e33a5 100644 --- a/.gitmodules +++ b/.gitmodules @@ -1,3 +1,15 @@ [submodule "librw"] path = librw url = https://github.com/aap/librw +[submodule "opus"] + path = opus + url = https://github.com/xiph/opus.git + branch = master +[submodule "opusfile"] + path = opusfile + url = https://github.com/xiph/opusfile.git + branch = master +[submodule "ogg"] + path = ogg + url = https://github.com/xiph/ogg.git + branch = master diff --git a/ogg b/ogg new file mode 160000 index 00000000..1e8d7cce --- /dev/null +++ b/ogg @@ -0,0 +1 @@ +Subproject commit 1e8d7cce266df61afc9d35db0283bbacc0237aba diff --git a/opus b/opus new file mode 160000 index 00000000..8aa77672 --- /dev/null +++ b/opus @@ -0,0 +1 @@ +Subproject commit 8aa7767207b1e3633004c26aecbb67d1c5118485 diff --git a/opusfile b/opusfile new file mode 160000 index 00000000..eb252537 --- /dev/null +++ b/opusfile @@ -0,0 +1 @@ +Subproject commit eb252537f374e30f7b68b84223c5a2303c05eca2 From 0af4d57408842d501af2fce4617e19a3bf9466eb Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Fri, 22 May 2020 17:40:19 +0300 Subject: [PATCH 02/14] opus support --- premake5.lua | 29 ++++++++++ src/audio/oal/stream.cpp | 110 +++++++++++++++++++++++++++++++++++++- src/audio/sampman.h | 37 +++++++++++++ src/audio/sampman_oal.cpp | 64 ++++++++++++++++++++-- 4 files changed, 235 insertions(+), 5 deletions(-) diff --git a/premake5.lua b/premake5.lua index c8494884..c6551a21 100644 --- a/premake5.lua +++ b/premake5.lua @@ -17,6 +17,11 @@ newoption { description = "Build and use librw from this solution" } +newoption { + trigger = "with-opus", + description = "Build with opus" +} + if(_OPTIONS["with-librw"]) then Librw = "librw" else @@ -185,8 +190,25 @@ project "re3" includedirs { "milessdk/include" } includedirs { "eax" } + + includedirs { "openal-soft/include" } + includedirs { "mpg123/include" } + includedirs { "libsndfile/include" } + includedirs { "ogg/include" } + includedirs { "opus/include" } + includedirs { "opusfile/include" } libdirs { "milessdk/lib" } + libdirs { "openal-soft/libs/Win32" } + libdirs { "mpg123/lib" } + libdirs { "libsndfile/lib" } + if _OPTIONS["with-opus"] then + filter "platforms:win*" + libdirs { "ogg/win32/VS2015/Win32/%{cfg.buildcfg}" } + libdirs { "opus/win32/VS2015/Win32/%{cfg.buildcfg}" } + libdirs { "opusfile/win32/VS2015/Win32/Release-NoHTTP" } + filter {} + end if(os.getenv("GTA_III_RE_DIR")) then setpaths("$(GTA_III_RE_DIR)/", "%(cfg.buildtarget.name)", "") @@ -202,6 +224,13 @@ project "re3" filter "platforms:linux*" defines { "OPENAL" } links { "openal", "mpg123", "sndfile", "pthread" } + + if _OPTIONS["with-opus"] then + filter {} + links { "libogg" } + links { "opus" } + links { "opusfile" } + end filter "platforms:*RW33*" staticruntime "on" diff --git a/src/audio/oal/stream.cpp b/src/audio/oal/stream.cpp index 5a9c7d7d..21e4d8c6 100644 --- a/src/audio/oal/stream.cpp +++ b/src/audio/oal/stream.cpp @@ -4,8 +4,9 @@ #include "common.h" #include "sampman.h" -#include -#include +#ifdef AUDIO_OPUS +#include +#else #ifdef _WIN32 typedef long ssize_t; #pragma comment( lib, "libsndfile-1.lib" ) @@ -13,7 +14,11 @@ typedef long ssize_t; #else #include "crossplatform.h" #endif +#include +#include +#endif +#ifndef AUDIO_OPUS class CSndFile : public IDecoder { SNDFILE *m_pfSound; @@ -170,15 +175,111 @@ public: return size; } }; +#else +class COpusFile : public IDecoder +{ + OggOpusFile *m_FileH; + bool m_bOpened; + uint32 m_nRate; + uint32 m_nChannels; +public: + _declspec(noinline) COpusFile(const char *path) : m_FileH(nil), + m_bOpened(false), + m_nRate(0), + m_nChannels(0) + { + int ret; + m_FileH = op_open_file(path, &ret); + + if (m_FileH) { + m_nChannels = op_head(m_FileH, 0)->channel_count; + m_nRate = op_head(m_FileH, 0)->input_sample_rate; + auto tags = op_tags(m_FileH, 0); + for (int i = 0; i < tags->comments; i++) { + if (strncmp(tags->user_comments[i], "SAMPLERATE", sizeof("SAMPLERATE")-1) == 0) + { + sscanf(tags->user_comments[i], "SAMPLERATE=%i", &m_nRate); + break; + } + } + + m_bOpened = true; + } + } + + ~COpusFile() + { + if (m_FileH) + { + op_free(m_FileH); + m_FileH = nil; + } + } + + bool IsOpened() + { + return m_bOpened; + } + + uint32 GetSampleSize() + { + return sizeof(uint16); + } + + uint32 GetSampleCount() + { + if ( !IsOpened() ) return 0; + return op_pcm_total(m_FileH, 0); + } + + uint32 GetSampleRate() + { + return m_nRate; + } + + uint32 GetChannels() + { + return m_nChannels; + } + + void Seek(uint32 milliseconds) + { + if ( !IsOpened() ) return; + op_pcm_seek(m_FileH, ms2samples(milliseconds) * GetSampleSize()); + } + + uint32 Tell() + { + if ( !IsOpened() ) return 0; + return samples2ms(op_pcm_tell(m_FileH)/GetSampleSize()); + } + + uint32 Decode(void *buffer) + { + if ( !IsOpened() ) return 0; + + int size = op_read(m_FileH, (opus_int16 *)buffer, GetBufferSamples(), NULL); + + if (size < 0) + return 0; + + return size * m_nChannels * GetSampleSize(); + } +}; +#endif void CStream::Initialise() { +#ifndef AUDIO_OPUS mpg123_init(); +#endif } void CStream::Terminate() { +#ifndef AUDIO_OPUS mpg123_exit(); +#endif } CStream::CStream(char *filename, ALuint &source, ALuint (&buffers)[NUM_STREAMBUFFERS]) : @@ -213,10 +314,15 @@ CStream::CStream(char *filename, ALuint &source, ALuint (&buffers)[NUM_STREAMBUF DEV("Stream %s\n", m_aFilename); +#ifndef AUDIO_OPUS if (!strcasecmp(&m_aFilename[strlen(m_aFilename) - strlen(".mp3")], ".mp3")) m_pSoundFile = new CMP3File(m_aFilename); else if (!strcasecmp(&m_aFilename[strlen(m_aFilename) - strlen(".wav")], ".wav")) m_pSoundFile = new CSndFile(m_aFilename); +#else + if (!strcasecmp(&m_aFilename[strlen(m_aFilename) - strlen(".opus")], ".opus")) + m_pSoundFile = new COpusFile(m_aFilename); +#endif else m_pSoundFile = nil; ASSERT(m_pSoundFile != nil); diff --git a/src/audio/sampman.h b/src/audio/sampman.h index d3c82943..3eeff476 100644 --- a/src/audio/sampman.h +++ b/src/audio/sampman.h @@ -144,6 +144,42 @@ public: extern cSampleManager SampleManager; extern uint32 BankStartOffset[MAX_SAMPLEBANKS]; +#ifdef AUDIO_OPUS +static char StreamedNameTable[][25] = { + "AUDIO\\HEAD.OPUS", "AUDIO\\CLASS.OPUS", "AUDIO\\KJAH.OPUS", "AUDIO\\RISE.OPUS", "AUDIO\\LIPS.OPUS", "AUDIO\\GAME.OPUS", + "AUDIO\\MSX.OPUS", "AUDIO\\FLASH.OPUS", "AUDIO\\CHAT.OPUS", "AUDIO\\HEAD.OPUS", "AUDIO\\POLICE.OPUS", "AUDIO\\CITY.OPUS", + "AUDIO\\WATER.OPUS", "AUDIO\\COMOPEN.OPUS", "AUDIO\\SUBOPEN.OPUS", "AUDIO\\JB.OPUS", "AUDIO\\BET.OPUS", "AUDIO\\L1_LG.OPUS", + "AUDIO\\L2_DSB.OPUS", "AUDIO\\L3_DM.OPUS", "AUDIO\\L4_PAP.OPUS", "AUDIO\\L5_TFB.OPUS", "AUDIO\\J0_DM2.OPUS", "AUDIO\\J1_LFL.OPUS", + "AUDIO\\J2_KCL.OPUS", "AUDIO\\J3_VH.OPUS", "AUDIO\\J4_ETH.OPUS", "AUDIO\\J5_DST.OPUS", "AUDIO\\J6_TBJ.OPUS", "AUDIO\\T1_TOL.OPUS", + "AUDIO\\T2_TPU.OPUS", "AUDIO\\T3_MAS.OPUS", "AUDIO\\T4_TAT.OPUS", "AUDIO\\T5_BF.OPUS", "AUDIO\\S0_MAS.OPUS", "AUDIO\\S1_PF.OPUS", + "AUDIO\\S2_CTG.OPUS", "AUDIO\\S3_RTC.OPUS", "AUDIO\\S5_LRQ.OPUS", "AUDIO\\S4_BDBA.OPUS", "AUDIO\\S4_BDBB.OPUS", "AUDIO\\S2_CTG2.OPUS", + "AUDIO\\S4_BDBD.OPUS", "AUDIO\\S5_LRQB.OPUS", "AUDIO\\S5_LRQC.OPUS", "AUDIO\\A1_SSO.OPUS", "AUDIO\\A2_PP.OPUS", "AUDIO\\A3_SS.OPUS", + "AUDIO\\A4_PDR.OPUS", "AUDIO\\A5_K2FT.OPUS", "AUDIO\\K1_KBO.OPUS", "AUDIO\\K2_GIS.OPUS", "AUDIO\\K3_DS.OPUS", "AUDIO\\K4_SHI.OPUS", + "AUDIO\\K5_SD.OPUS", "AUDIO\\R0_PDR2.OPUS", "AUDIO\\R1_SW.OPUS", "AUDIO\\R2_AP.OPUS", "AUDIO\\R3_ED.OPUS", "AUDIO\\R4_GF.OPUS", + "AUDIO\\R5_PB.OPUS", "AUDIO\\R6_MM.OPUS", "AUDIO\\D1_STOG.OPUS", "AUDIO\\D2_KK.OPUS", "AUDIO\\D3_ADO.OPUS", "AUDIO\\D5_ES.OPUS", + "AUDIO\\D7_MLD.OPUS", "AUDIO\\D4_GTA.OPUS", "AUDIO\\D4_GTA2.OPUS", "AUDIO\\D6_STS.OPUS", "AUDIO\\A6_BAIT.OPUS", "AUDIO\\A7_ETG.OPUS", + "AUDIO\\A8_PS.OPUS", "AUDIO\\A9_ASD.OPUS", "AUDIO\\K4_SHI2.OPUS", "AUDIO\\C1_TEX.OPUS", "AUDIO\\EL_PH1.OPUS", "AUDIO\\EL_PH2.OPUS", + "AUDIO\\EL_PH3.OPUS", "AUDIO\\EL_PH4.OPUS", "AUDIO\\YD_PH1.OPUS", "AUDIO\\YD_PH2.OPUS", "AUDIO\\YD_PH3.OPUS", "AUDIO\\YD_PH4.OPUS", + "AUDIO\\HD_PH1.OPUS", "AUDIO\\HD_PH2.OPUS", "AUDIO\\HD_PH3.OPUS", "AUDIO\\HD_PH4.OPUS", "AUDIO\\HD_PH5.OPUS", "AUDIO\\MT_PH1.OPUS", + "AUDIO\\MT_PH2.OPUS", "AUDIO\\MT_PH3.OPUS", "AUDIO\\MT_PH4.OPUS", "AUDIO\\MISCOM.OPUS", "AUDIO\\END.OPUS", "AUDIO\\lib_a1.OPUS", + "AUDIO\\lib_a2.OPUS", "AUDIO\\lib_a.OPUS", "AUDIO\\lib_b.OPUS", "AUDIO\\lib_c.OPUS", "AUDIO\\lib_d.OPUS", "AUDIO\\l2_a.OPUS", + "AUDIO\\j4t_1.OPUS", "AUDIO\\j4t_2.OPUS", "AUDIO\\j4t_3.OPUS", "AUDIO\\j4t_4.OPUS", "AUDIO\\j4_a.OPUS", "AUDIO\\j4_b.OPUS", + "AUDIO\\j4_c.OPUS", "AUDIO\\j4_d.OPUS", "AUDIO\\j4_e.OPUS", "AUDIO\\j4_f.OPUS", "AUDIO\\j6_1.OPUS", "AUDIO\\j6_a.OPUS", + "AUDIO\\j6_b.OPUS", "AUDIO\\j6_c.OPUS", "AUDIO\\j6_d.OPUS", "AUDIO\\t4_a.OPUS", "AUDIO\\s1_a.OPUS", "AUDIO\\s1_a1.OPUS", + "AUDIO\\s1_b.OPUS", "AUDIO\\s1_c.OPUS", "AUDIO\\s1_c1.OPUS", "AUDIO\\s1_d.OPUS", "AUDIO\\s1_e.OPUS", "AUDIO\\s1_f.OPUS", + "AUDIO\\s1_g.OPUS", "AUDIO\\s1_h.OPUS", "AUDIO\\s1_i.OPUS", "AUDIO\\s1_j.OPUS", "AUDIO\\s1_k.OPUS", "AUDIO\\s1_l.OPUS", + "AUDIO\\s3_a.OPUS", "AUDIO\\s3_b.OPUS", "AUDIO\\el3_a.OPUS", "AUDIO\\mf1_a.OPUS", "AUDIO\\mf2_a.OPUS", "AUDIO\\mf3_a.OPUS", + "AUDIO\\mf3_b.OPUS", "AUDIO\\mf3_b1.OPUS", "AUDIO\\mf3_c.OPUS", "AUDIO\\mf4_a.OPUS", "AUDIO\\mf4_b.OPUS", "AUDIO\\mf4_c.OPUS", + "AUDIO\\a1_a.OPUS", "AUDIO\\a3_a.OPUS", "AUDIO\\a5_a.OPUS", "AUDIO\\a4_a.OPUS", "AUDIO\\a4_b.OPUS", "AUDIO\\a4_c.OPUS", + "AUDIO\\a4_d.OPUS", "AUDIO\\k1_a.OPUS", "AUDIO\\k3_a.OPUS", "AUDIO\\r1_a.OPUS", "AUDIO\\r2_a.OPUS", "AUDIO\\r2_b.OPUS", + "AUDIO\\r2_c.OPUS", "AUDIO\\r2_d.OPUS", "AUDIO\\r2_e.OPUS", "AUDIO\\r2_f.OPUS", "AUDIO\\r2_g.OPUS", "AUDIO\\r2_h.OPUS", + "AUDIO\\r5_a.OPUS", "AUDIO\\r6_a.OPUS", "AUDIO\\r6_a1.OPUS", "AUDIO\\r6_b.OPUS", "AUDIO\\lo2_a.OPUS", "AUDIO\\lo6_a.OPUS", + "AUDIO\\yd2_a.OPUS", "AUDIO\\yd2_b.OPUS", "AUDIO\\yd2_c.OPUS", "AUDIO\\yd2_c1.OPUS", "AUDIO\\yd2_d.OPUS", "AUDIO\\yd2_e.OPUS", + "AUDIO\\yd2_f.OPUS", "AUDIO\\yd2_g.OPUS", "AUDIO\\yd2_h.OPUS", "AUDIO\\yd2_ass.OPUS", "AUDIO\\yd2_ok.OPUS", "AUDIO\\h5_a.OPUS", + "AUDIO\\h5_b.OPUS", "AUDIO\\h5_c.OPUS", "AUDIO\\ammu_a.OPUS", "AUDIO\\ammu_b.OPUS", "AUDIO\\ammu_c.OPUS", "AUDIO\\door_1.OPUS", + "AUDIO\\door_2.OPUS", "AUDIO\\door_3.OPUS", "AUDIO\\door_4.OPUS", "AUDIO\\door_5.OPUS", "AUDIO\\door_6.OPUS", "AUDIO\\t3_a.OPUS", + "AUDIO\\t3_b.OPUS", "AUDIO\\t3_c.OPUS", "AUDIO\\k1_b.OPUS", "AUDIO\\cat1.OPUS"}; +#else static char StreamedNameTable[][25]= { "AUDIO\\HEAD.WAV", @@ -343,3 +379,4 @@ static char StreamedNameTable[][25]= "AUDIO\\k1_b.WAV", "AUDIO\\cat1.WAV" }; +#endif \ No newline at end of file diff --git a/src/audio/sampman_oal.cpp b/src/audio/sampman_oal.cpp index 30efd7f5..d8d7ac24 100644 --- a/src/audio/sampman_oal.cpp +++ b/src/audio/sampman_oal.cpp @@ -27,6 +27,9 @@ #include "MusicManager.h" #include "Frontend.h" #include "Timer.h" +#ifdef AUDIO_OPUS +#include +#endif //TODO: fix eax3 reverb //TODO: max channals @@ -42,6 +45,10 @@ bool _bSampmanInitialised = false; uint32 BankStartOffset[MAX_SAMPLEBANKS]; +#ifdef AUDIO_OPUS +OggOpusFile *opusSFX; +#endif + int prevprovider=-1; int curprovider=-1; int usingEAX=0; @@ -444,6 +451,8 @@ int8 cSampleManager::GetCurrent3DProviderIndex(void) int8 cSampleManager::SetCurrent3DProvider(uint8 nProvider) { ASSERT( nProvider < m_nNumberOfProviders ); + if (nProvider >= m_nNumberOfProviders) + nProvider = 0; int savedprovider = curprovider; if ( nProvider < m_nNumberOfProviders ) @@ -743,12 +752,37 @@ cSampleManager::LoadSampleBank(uint8 nBank) return false; } +#ifdef AUDIO_OPUS + int ret; + //OggOpusFile *file = op_open_file("AUDIO/SFX0.RAW", &ret); + int samplesRead = 0; + int samplesSize = nSampleBankSize[nBank] / 2; + op_pcm_seek(opusSFX, 0); + while (samplesSize > 0) { + int size = op_read(opusSFX, (opus_int16 *)(nSampleBankMemoryStartAddress[nBank] + samplesRead), samplesSize, NULL); + if (size <= 0) { + // huh? + //assert(0); + break; + } + samplesRead += size*2; + samplesSize -= size; + } + //op_free(file); + + //if (samplesRead != nSampleBankSize[nBank]) + // return false; + + //FILE *fsd = fopen("sfx.temp", "wb"); + //fwrite((void *)nSampleBankMemoryStartAddress[nBank], 1, nSampleBankSize[nBank], fsd); + //fclose(fsd); +#else if ( fseek(fpSampleDataHandle, nSampleBankDiscStartOffset[nBank], SEEK_SET) != 0 ) return false; if ( fread((void *)nSampleBankMemoryStartAddress[nBank], 1, nSampleBankSize[nBank], fpSampleDataHandle) != nSampleBankSize[nBank] ) return false; - +#endif bSampleBankLoaded[nBank] = true; return true; @@ -836,13 +870,28 @@ cSampleManager::LoadPedComment(uint32 nComment) } } } - + +#ifdef AUDIO_OPUS + int samplesRead = 0; + int samplesSize = m_aSamples[nComment].nSize / 2; + op_pcm_seek(opusSFX, m_aSamples[nComment].nOffset / 2); + while (samplesSize > 0) { + int size = + op_read(opusSFX, (opus_int16 *)(nSampleBankMemoryStartAddress[SAMPLEBANK_PED] + PED_BLOCKSIZE * nCurrentPedSlot + samplesRead), samplesSize, NULL); + if (size <= 0) { + return false; + } + samplesRead += size * 2; + samplesSize -= size; + } +#else if ( fseek(fpSampleDataHandle, m_aSamples[nComment].nOffset, SEEK_SET) != 0 ) return false; if ( fread((void *)(nSampleBankMemoryStartAddress[SAMPLEBANK_PED] + PED_BLOCKSIZE*nCurrentPedSlot), 1, m_aSamples[nComment].nSize, fpSampleDataHandle) != m_aSamples[nComment].nSize ) return false; - + +#endif nPedSlotSfx[nCurrentPedSlot] = nComment; alBufferData(pedBuffers[nCurrentPedSlot], @@ -1406,6 +1455,15 @@ cSampleManager::InitialiseSampleBanks(void) nSampleBankSize[SAMPLEBANK_MAIN] = nSampleBankDiscStartOffset[SAMPLEBANK_PED] - nSampleBankDiscStartOffset[SAMPLEBANK_MAIN]; nSampleBankSize[SAMPLEBANK_PED] = _nSampleDataEndOffset - nSampleBankDiscStartOffset[SAMPLEBANK_PED]; + //int error = 0; + //auto encoder = opus_encoder_create(48000, 1, OPUS_APPLICATION_AUDIO, &error); + //error = opus_encoder_ctl(encoder, OPUS_SET_BITRATE(75.5)); + + //nbBytes = opus_encode(encoder, in, FRAME_SIZE, cbits, MAX_PACKET_SIZE); + + int e; + opusSFX = op_open_file("AUDIO/SFX.opus", &e); + return true; } From a705fc7eb83304e5e0d536c88353392bb7310141 Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Fri, 22 May 2020 17:41:48 +0300 Subject: [PATCH 03/14] fix eax --- eax/eax.h | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/eax/eax.h b/eax/eax.h index 0e2201db..7c0db32e 100644 --- a/eax/eax.h +++ b/eax/eax.h @@ -54,7 +54,8 @@ extern "C" { #include #include #else - #include + #include + #include #endif #ifndef GUID_DEFINED From 97b058d0fa44eb1bb032484a6f4bee6df1f249bd Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Fri, 22 May 2020 17:43:26 +0300 Subject: [PATCH 04/14] more checks in premake --- premake5.lua | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/premake5.lua b/premake5.lua index c6551a21..95c03b21 100644 --- a/premake5.lua +++ b/premake5.lua @@ -194,9 +194,11 @@ project "re3" includedirs { "openal-soft/include" } includedirs { "mpg123/include" } includedirs { "libsndfile/include" } - includedirs { "ogg/include" } - includedirs { "opus/include" } - includedirs { "opusfile/include" } + if _OPTIONS["with-opus"] then + includedirs { "ogg/include" } + includedirs { "opus/include" } + includedirs { "opusfile/include" } + end libdirs { "milessdk/lib" } libdirs { "openal-soft/libs/Win32" } From 3a7651e7ab87e21ff510441f98dcbe6711134a18 Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Sun, 24 May 2020 00:56:20 +0300 Subject: [PATCH 05/14] Cleanup --- premake5.lua | 1 + src/audio/sampman_oal.cpp | 48 ++++++++++++++------------------------- 2 files changed, 18 insertions(+), 31 deletions(-) diff --git a/premake5.lua b/premake5.lua index c7321dcb..036dad09 100644 --- a/premake5.lua +++ b/premake5.lua @@ -209,6 +209,7 @@ project "re3" libdirs { "opus/win32/VS2015/Win32/%{cfg.buildcfg}" } libdirs { "opusfile/win32/VS2015/Win32/Release-NoHTTP" } filter {} + defines { "AUDIO_OPUS" } end filter "platforms:*oal" diff --git a/src/audio/sampman_oal.cpp b/src/audio/sampman_oal.cpp index ff50ac07..1cd45e4f 100644 --- a/src/audio/sampman_oal.cpp +++ b/src/audio/sampman_oal.cpp @@ -45,10 +45,6 @@ bool _bSampmanInitialised = false; uint32 BankStartOffset[MAX_SAMPLEBANKS]; -#ifdef AUDIO_OPUS -OggOpusFile *opusSFX; -#endif - int prevprovider=-1; int curprovider=-1; int usingEAX=0; @@ -76,7 +72,11 @@ char SampleBankDescFilename[] = "audio/sfx.SDT"; char SampleBankDataFilename[] = "audio/sfx.RAW"; FILE *fpSampleDescHandle; +#ifdef AUDIO_OPUS +OggOpusFile *fpSampleDataHandle; +#else FILE *fpSampleDataHandle; +#endif bool bSampleBankLoaded [MAX_SAMPLEBANKS]; int32 nSampleBankDiscStartOffset [MAX_SAMPLEBANKS]; int32 nSampleBankSize [MAX_SAMPLEBANKS]; @@ -753,13 +753,11 @@ cSampleManager::LoadSampleBank(uint8 nBank) } #ifdef AUDIO_OPUS - int ret; - //OggOpusFile *file = op_open_file("AUDIO/SFX0.RAW", &ret); int samplesRead = 0; int samplesSize = nSampleBankSize[nBank] / 2; - op_pcm_seek(opusSFX, 0); + op_pcm_seek(fpSampleDataHandle, 0); while (samplesSize > 0) { - int size = op_read(opusSFX, (opus_int16 *)(nSampleBankMemoryStartAddress[nBank] + samplesRead), samplesSize, NULL); + int size = op_read(fpSampleDataHandle, (opus_int16 *)(nSampleBankMemoryStartAddress[nBank] + samplesRead), samplesSize, NULL); if (size <= 0) { // huh? //assert(0); @@ -768,14 +766,6 @@ cSampleManager::LoadSampleBank(uint8 nBank) samplesRead += size*2; samplesSize -= size; } - //op_free(file); - - //if (samplesRead != nSampleBankSize[nBank]) - // return false; - - //FILE *fsd = fopen("sfx.temp", "wb"); - //fwrite((void *)nSampleBankMemoryStartAddress[nBank], 1, nSampleBankSize[nBank], fsd); - //fclose(fsd); #else if ( fseek(fpSampleDataHandle, nSampleBankDiscStartOffset[nBank], SEEK_SET) != 0 ) return false; @@ -878,10 +868,10 @@ cSampleManager::LoadPedComment(uint32 nComment) #ifdef AUDIO_OPUS int samplesRead = 0; int samplesSize = m_aSamples[nComment].nSize / 2; - op_pcm_seek(opusSFX, m_aSamples[nComment].nOffset / 2); + op_pcm_seek(fpSampleDataHandle, m_aSamples[nComment].nOffset / 2); while (samplesSize > 0) { - int size = - op_read(opusSFX, (opus_int16 *)(nSampleBankMemoryStartAddress[SAMPLEBANK_PED] + PED_BLOCKSIZE * nCurrentPedSlot + samplesRead), samplesSize, NULL); + int size = op_read(fpSampleDataHandle, (opus_int16 *)(nSampleBankMemoryStartAddress[SAMPLEBANK_PED] + PED_BLOCKSIZE * nCurrentPedSlot + samplesRead), + samplesSize, NULL); if (size <= 0) { return false; } @@ -1425,7 +1415,7 @@ cSampleManager::InitialiseSampleBanks(void) fpSampleDescHandle = fopen(SampleBankDescFilename, "rb"); if ( fpSampleDescHandle == NULL ) return false; - +#ifndef AUDIO_OPUS fpSampleDataHandle = fopen(SampleBankDataFilename, "rb"); if ( fpSampleDataHandle == NULL ) { @@ -1438,9 +1428,14 @@ cSampleManager::InitialiseSampleBanks(void) fseek(fpSampleDataHandle, 0, SEEK_END); int32 _nSampleDataEndOffset = ftell(fpSampleDataHandle); rewind(fpSampleDataHandle); - +#else + int e; + fpSampleDataHandle = op_open_file(SampleBankDataFilename, &e); +#endif fread(m_aSamples, sizeof(tSample), TOTAL_AUDIO_SAMPLES, fpSampleDescHandle); - +#ifdef AUDIO_OPUS + int32 _nSampleDataEndOffset = m_aSamples[TOTAL_AUDIO_SAMPLES - 1].nOffset + m_aSamples[TOTAL_AUDIO_SAMPLES - 1].nSize; +#endif fclose(fpSampleDescHandle); fpSampleDescHandle = NULL; @@ -1458,15 +1453,6 @@ cSampleManager::InitialiseSampleBanks(void) nSampleBankSize[SAMPLEBANK_MAIN] = nSampleBankDiscStartOffset[SAMPLEBANK_PED] - nSampleBankDiscStartOffset[SAMPLEBANK_MAIN]; nSampleBankSize[SAMPLEBANK_PED] = _nSampleDataEndOffset - nSampleBankDiscStartOffset[SAMPLEBANK_PED]; - - //int error = 0; - //auto encoder = opus_encoder_create(48000, 1, OPUS_APPLICATION_AUDIO, &error); - //error = opus_encoder_ctl(encoder, OPUS_SET_BITRATE(75.5)); - - //nbBytes = opus_encode(encoder, in, FRAME_SIZE, cbits, MAX_PACKET_SIZE); - - int e; - opusSFX = op_open_file("AUDIO/SFX.opus", &e); return true; } From e259bb6609fc319f202016b3019e7ea8f3c3b5d2 Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Sun, 24 May 2020 18:43:50 +0300 Subject: [PATCH 06/14] fixes --- src/audio/oal/stream.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/audio/oal/stream.cpp b/src/audio/oal/stream.cpp index 597b3fb7..b129f6d4 100644 --- a/src/audio/oal/stream.cpp +++ b/src/audio/oal/stream.cpp @@ -183,7 +183,7 @@ class COpusFile : public IDecoder uint32 m_nRate; uint32 m_nChannels; public: - _declspec(noinline) COpusFile(const char *path) : m_FileH(nil), + COpusFile(const char *path) : m_FileH(nil), m_bOpened(false), m_nRate(0), m_nChannels(0) @@ -194,7 +194,7 @@ public: if (m_FileH) { m_nChannels = op_head(m_FileH, 0)->channel_count; m_nRate = op_head(m_FileH, 0)->input_sample_rate; - auto tags = op_tags(m_FileH, 0); + const OpusTags *tags = op_tags(m_FileH, 0); for (int i = 0; i < tags->comments; i++) { if (strncmp(tags->user_comments[i], "SAMPLERATE", sizeof("SAMPLERATE")-1) == 0) { From 2f40c3dc8bd30336189b2f53324ae6aa234993a1 Mon Sep 17 00:00:00 2001 From: aap Date: Wed, 29 Jul 2020 09:50:06 +0200 Subject: [PATCH 07/14] synch fakerw with reVC; update librw --- librw | 2 +- src/fakerw/fake.cpp | 11 ++++++----- 2 files changed, 7 insertions(+), 6 deletions(-) diff --git a/librw b/librw index 49ca300b..99c15d5e 160000 --- a/librw +++ b/librw @@ -1 +1 @@ -Subproject commit 49ca300b88c8c298e5811b41e753589ad2a4c367 +Subproject commit 99c15d5ed78cc112e1055cc89452dd57df28da58 diff --git a/src/fakerw/fake.cpp b/src/fakerw/fake.cpp index 7d563d77..b9ff0144 100644 --- a/src/fakerw/fake.cpp +++ b/src/fakerw/fake.cpp @@ -35,9 +35,9 @@ RwReal RwV3dLength(const RwV3d * in) { return length(*in); } //void RwV3dAssign(RwV3d * out, const RwV3d * ina); void RwV3dAdd(RwV3d * out, const RwV3d * ina, const RwV3d * inb) { *out = add(*ina, *inb); } void RwV3dSub(RwV3d * out, const RwV3d * ina, const RwV3d * inb) { *out = sub(*ina, *inb); } -//void RwV3dScale(RwV3d * out, const RwV3d * in, RwReal scalar); -//void RwV3dIncrementScaled(RwV3d * out, const RwV3d * in, RwReal scalar); -//void RwV3dNegate(RwV3d * out, const RwV3d * in); +void RwV3dScale(RwV3d * out, const RwV3d * in, RwReal scalar) { *out = scale(*in, scalar); } +void RwV3dIncrementScaled(RwV3d * out, const RwV3d * in, RwReal scalar) { *out = add(*out, scale(*in, scalar)); } +void RwV3dNegate(RwV3d * out, const RwV3d * in) { *out = neg(*in); } RwReal RwV3dDotProduct(const RwV3d * ina, const RwV3d * inb) { return dot(*ina, *inb); } //void RwV3dCrossProduct(RwV3d * out, const RwV3d * ina, const RwV3d * inb); RwV3d *RwV3dTransformPoints(RwV3d * pointsOut, const RwV3d * pointsIn, RwInt32 numPoints, const RwMatrix * matrix) @@ -83,7 +83,8 @@ RwFrame *RwFrameTranslate(RwFrame * frame, const RwV3d * v, RwOpCombineType comb RwFrame *RwFrameRotate(RwFrame * frame, const RwV3d * axis, RwReal angle, RwOpCombineType combine) { frame->rotate(axis, angle, (CombineOp)combine); return frame; } RwFrame *RwFrameScale(RwFrame * frame, const RwV3d * v, RwOpCombineType combine) { frame->scale(v, (CombineOp)combine); return frame; } RwFrame *RwFrameTransform(RwFrame * frame, const RwMatrix * m, RwOpCombineType combine) { frame->transform(m, (CombineOp)combine); return frame; } -//RwFrame *RwFrameOrthoNormalize(RwFrame * frame); +//TODO: actually implement this! +RwFrame *RwFrameOrthoNormalize(RwFrame * frame) { return frame; } RwFrame *RwFrameSetIdentity(RwFrame * frame) { frame->matrix.setIdentity(); frame->updateObjects(); return frame; } //RwFrame *RwFrameCloneHierarchy(RwFrame * root); //RwBool RwFrameDestroyHierarchy(RwFrame * frame); @@ -136,7 +137,7 @@ RwCamera *RwCameraCreate(void) { return rw::Camera::create(); } RwCamera *RwCameraClone(RwCamera * camera) { return camera->clone(); } RwCamera *RwCameraSetViewOffset(RwCamera *camera, const RwV2d *offset) { camera->setViewOffset(offset); return camera; } RwCamera *RwCameraSetViewWindow(RwCamera *camera, const RwV2d *viewWindow) { camera->setViewWindow(viewWindow); return camera; } -RwCamera *RwCameraSetProjection(RwCamera *camera, RwCameraProjection projection); +RwCamera *RwCameraSetProjection(RwCamera *camera, RwCameraProjection projection) { camera->projection = projection; return camera; } RwCamera *RwCameraSetNearClipPlane(RwCamera *camera, RwReal nearClip) { camera->setNearPlane(nearClip); return camera; } RwCamera *RwCameraSetFarClipPlane(RwCamera *camera, RwReal farClip) { camera->setFarPlane(farClip); return camera; } RwInt32 RwCameraRegisterPlugin(RwInt32 size, RwUInt32 pluginID, RwPluginObjectConstructor constructCB, RwPluginObjectDestructor destructCB, RwPluginObjectCopy copyCB); From 581cb5edfa39a263bcbcdf3e37c608a5c7758849 Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Wed, 29 Jul 2020 14:56:06 +0300 Subject: [PATCH 08/14] The real pickup reflection fix --- src/control/Pickups.cpp | 33 +++++++++------------------------ src/core/Camera.cpp | 4 ++-- src/core/Fire.cpp | 7 ++----- src/render/Shadows.cpp | 3 +++ src/rw/RwHelper.cpp | 34 ++++++++++++++++++++++++++++++++++ src/rw/RwHelper.h | 10 +++++++++- 6 files changed, 59 insertions(+), 32 deletions(-) diff --git a/src/control/Pickups.cpp b/src/control/Pickups.cpp index 32bffa17..eb4843c5 100644 --- a/src/control/Pickups.cpp +++ b/src/control/Pickups.cpp @@ -700,15 +700,9 @@ CPickups::DoPickUpEffects(CEntity *entity) const CVector &pos = entity->GetPosition(); float colorModifier = ((CGeneral::GetRandomNumber() & 0x1F) * 0.015f + 1.0f) * modifiedSin * 0.15f; - CShadows::StoreStaticShadow( - (uintptr)entity, - SHADOWTYPE_ADDITIVE, - gpShadowExplosionTex, - &pos, - 2.0f, 0.0f, 0.0f, -2.0f, - 255, // this is 0 on PC which results in no shadow - aWeaponReds[colorId] * colorModifier, aWeaponGreens[colorId] * colorModifier, aWeaponBlues[colorId] * colorModifier, - 4.0f, 1.0f, 40.0f, false, 0.0f); + CShadows::StoreStaticShadow((uintptr)entity, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &pos, 2.0f, 0.0f, 0.0f, -2.0f, 0, + aWeaponReds[colorId] * colorModifier, aWeaponGreens[colorId] * colorModifier, aWeaponBlues[colorId] * colorModifier, 4.0f, + 1.0f, 40.0f, false, 0.0f); float radius = (CGeneral::GetRandomNumber() & 0xF) * 0.1f + 3.0f; CPointLights::AddLight(CPointLights::LIGHT_POINT, pos, CVector(0.0f, 0.0f, 0.0f), radius, aWeaponReds[colorId] * modifiedSin / 256.0f, aWeaponGreens[colorId] * modifiedSin / 256.0f, aWeaponBlues[colorId] * modifiedSin / 256.0f, CPointLights::FOG_NONE, true); @@ -759,11 +753,8 @@ CPickups::DoMineEffects(CEntity *entity) float s = Sin((float)((CTimer::GetTimeInMilliseconds() + (uintptr)entity) & 0x1FF) * DEGTORAD(360.0f / 0x200)); int32 red = (MAXDIST - dist) * (0.5f * s + 0.5f) / MAXDIST * 64.0f; - CShadows::StoreStaticShadow((uintptr)entity, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &pos, - 2.0f, 0.0f, 0.0f, -2.0f, - 255, // this is 0 on PC which results in no shadow - red, 0, 0, - 4.0f, 1.0f, 40.0f, false, 0.0f); + CShadows::StoreStaticShadow((uintptr)entity, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &pos, 2.0f, 0.0f, 0.0f, -2.0f, 0, red, 0, 0, 4.0f, 1.0f, 40.0f, + false, 0.0f); CCoronas::RegisterCorona((uintptr)entity, red, 0, 0, 255, pos, 0.6f, 60.0f, CCoronas::TYPE_RING, CCoronas::FLARE_NONE, CCoronas::REFLECTION_OFF, CCoronas::LOSCHECK_OFF, CCoronas::STREAK_OFF, 0.0f); } @@ -781,11 +772,8 @@ CPickups::DoMoneyEffects(CEntity *entity) float s = Sin((float)((CTimer::GetTimeInMilliseconds() + (uintptr)entity) & 0x3FF) * DEGTORAD(360.0f / 0x400)); int32 green = (MAXDIST - dist) * (0.2f * s + 0.3f) / MAXDIST * 64.0f; - CShadows::StoreStaticShadow((uintptr)entity, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &pos, - 2.0f, 0.0f, 0.0f, -2.0f, - 255, // this is 0 on PC which results in no shadow - 0, green, 0, - 4.0f, 1.0f, 40.0f, false, 0.0f); + CShadows::StoreStaticShadow((uintptr)entity, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &pos, 2.0f, 0.0f, 0.0f, -2.0f, 0, 0, green, 0, 4.0f, 1.0f, + 40.0f, false, 0.0f); CCoronas::RegisterCorona((uintptr)entity, 0, green, 0, 255, pos, 0.4f, 40.0f, CCoronas::TYPE_RING, CCoronas::FLARE_NONE, CCoronas::REFLECTION_OFF, CCoronas::LOSCHECK_OFF, CCoronas::STREAK_OFF, 0.0f); } @@ -803,11 +791,8 @@ CPickups::DoCollectableEffects(CEntity *entity) float s = Sin((float)((CTimer::GetTimeInMilliseconds() + (uintptr)entity) & 0x7FF) * DEGTORAD(360.0f / 0x800)); int32 color = (MAXDIST - dist) * (0.5f * s + 0.5f) / MAXDIST * 255.0f; - CShadows::StoreStaticShadow((uintptr)entity, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &pos, - 2.0f, 0.0f, 0.0f, -2.0f, - 255, // this is 0 on PC which results in no shadow - color, color, color, - 4.0f, 1.0f, 40.0f, false, 0.0f); + CShadows::StoreStaticShadow((uintptr)entity, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &pos, 2.0f, 0.0f, 0.0f, -2.0f, 0, color, color, color, 4.0f, + 1.0f, 40.0f, false, 0.0f); CCoronas::RegisterCorona((uintptr)entity, color, color, color, 255, pos, 0.6f, 40.0f, CCoronas::TYPE_RING, CCoronas::FLARE_NONE, CCoronas::REFLECTION_OFF, CCoronas::LOSCHECK_OFF, CCoronas::STREAK_OFF, 0.0f); } diff --git a/src/core/Camera.cpp b/src/core/Camera.cpp index c253d00f..abe0833e 100644 --- a/src/core/Camera.cpp +++ b/src/core/Camera.cpp @@ -3587,8 +3587,8 @@ CCamera::CalculateDerivedValues(void) m_cameraMatrix = Invert(m_matrix); float hfov = DEGTORAD(CDraw::GetScaledFOV()/2.0f); - float c = cos(hfov); - float s = sin(hfov); + float c = Cos(hfov); + float s = Sin(hfov); // right plane m_vecFrustumNormals[0] = CVector(c, -s, 0.0f); diff --git a/src/core/Fire.cpp b/src/core/Fire.cpp index 933c73da..c6dece6a 100644 --- a/src/core/Fire.cpp +++ b/src/core/Fire.cpp @@ -128,11 +128,8 @@ CFire::ProcessFire(void) lightpos.z = m_vecPos.z + 5.0f; if (!m_pEntity) { - CShadows::StoreStaticShadow((uintptr)this, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &lightpos, - 7.0f, 0.0f, 0.0f, -7.0f, - 255, // this is 0 on PC which results in no shadow - nRandNumber / 2, nRandNumber / 2, 0, - 10.0f, 1.0f, 40.0f, 0, 0.0f); + CShadows::StoreStaticShadow((uintptr)this, SHADOWTYPE_ADDITIVE, gpShadowExplosionTex, &lightpos, 7.0f, 0.0f, 0.0f, -7.0f, 0, nRandNumber / 2, + nRandNumber / 2, 0, 10.0f, 1.0f, 40.0f, 0, 0.0f); } fGreen = nRandNumber / 128; fRed = nRandNumber / 128; diff --git a/src/render/Shadows.cpp b/src/render/Shadows.cpp index d07c302a..c169c351 100644 --- a/src/render/Shadows.cpp +++ b/src/render/Shadows.cpp @@ -796,6 +796,8 @@ CShadows::RenderStaticShadows(void) RwRenderStateSet(rwRENDERSTATEVERTEXALPHAENABLE, (void *)TRUE); RwRenderStateSet(rwRENDERSTATEFOGENABLE, (void *)FALSE); + SetAlphaTest(0); + for ( int32 i = 0; i < MAX_STATICSHADOWS; i++ ) aStaticShadows[i].m_bRendered = false; @@ -849,6 +851,7 @@ CShadows::RenderStaticShadows(void) RenderBuffer::RenderStuffInBuffer(); } } + RestoreAlphaTest(); RwRenderStateSet(rwRENDERSTATEVERTEXALPHAENABLE, (void *)FALSE); RwRenderStateSet(rwRENDERSTATEZWRITEENABLE, (void *)TRUE); diff --git a/src/rw/RwHelper.cpp b/src/rw/RwHelper.cpp index 3503e27d..bf70c8dc 100644 --- a/src/rw/RwHelper.cpp +++ b/src/rw/RwHelper.cpp @@ -611,3 +611,37 @@ CameraCreate(RwInt32 width, RwInt32 height, RwBool zBuffer) WRAPPER void _TexturePoolsInitialise() { EAXJMP(0x598B10); } WRAPPER void _TexturePoolsShutdown() { EAXJMP(0x598B30); } #endif + +#if defined(FIX_BUGS) && defined(GTA_PC) +RwUInt32 saved_alphafunc, saved_alpharef; + +void +SetAlphaTest(RwUInt32 alpharef) +{ +#ifdef LIBRW + saved_alphafunc = rw::GetRenderState(rw::ALPHATESTFUNC); + saved_alpharef = rw::GetRenderState(rw::ALPHATESTREF); + + rw::SetRenderState(rw::ALPHATESTFUNC, rw::ALPHAGREATEREQUAL); + rw::SetRenderState(rw::ALPHATESTREF, 0); +#else + RwD3D8GetRenderState(D3DRS_ALPHAFUNC, &saved_alphafunc); + RwD3D8GetRenderState(D3DRS_ALPHAREF, &saved_alpharef); + + RwD3D8SetRenderState(D3DRS_ALPHAFUNC, D3DCMP_GREATEREQUAL); + RwD3D8SetRenderState(D3DRS_ALPHAREF, alpharef); +#endif +} + +void +RestoreAlphaTest() +{ +#ifdef LIBRW + rw::SetRenderState(rw::ALPHATESTFUNC, saved_alphafunc); + rw::SetRenderState(rw::ALPHATESTREF, saved_alpharef); +#else + RwD3D8SetRenderState(D3DRS_ALPHAFUNC, saved_alphafunc); + RwD3D8SetRenderState(D3DRS_ALPHAREF, saved_alpharef); +#endif +} +#endif diff --git a/src/rw/RwHelper.h b/src/rw/RwHelper.h index a751ee39..eceaee07 100644 --- a/src/rw/RwHelper.h +++ b/src/rw/RwHelper.h @@ -52,4 +52,12 @@ RwCamera *CameraCreate(RwInt32 width, void _TexturePoolsInitialise(); -void _TexturePoolsShutdown(); \ No newline at end of file +void _TexturePoolsShutdown(); + +#if defined(FIX_BUGS) && defined (GTA_PC) +void SetAlphaTest(RwUInt32 alpharef); +void RestoreAlphaTest(); +#else +#define SetAlphaTest(a) (0) +#define RestoreAlphaTest() (0) +#endif \ No newline at end of file From 6b92e9e12b376b9edf04070ecf83179e9a0f8fda Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Wed, 29 Jul 2020 15:24:42 +0300 Subject: [PATCH 09/14] Dual pass rendering for RW 3.3 --- src/core/Game.cpp | 18 ++++++++++++++---- src/core/config.h | 1 + src/rw/RwHelper.cpp | 8 ++++++-- src/rw/RwMatFX.cpp | 4 ++-- 4 files changed, 23 insertions(+), 8 deletions(-) diff --git a/src/core/Game.cpp b/src/core/Game.cpp index 0d839dfa..2c9e784c 100644 --- a/src/core/Game.cpp +++ b/src/core/Game.cpp @@ -149,9 +149,14 @@ CGame::InitialiseOnceBeforeRW(void) return true; } -#if !defined(LIBRW) && defined(PS2_MATFX) +#ifndef LIBRW +#ifdef PS2_MATFX void ReplaceMatFxCallback(); -#endif +#endif // PS2_MATFX +#ifdef DUAL_PASS_RENDERING +void ReplaceAtomicPipeCallback(); +#endif // DUAL_PASS_RENDERING +#endif // !LIBRW bool CGame::InitialiseRenderWare(void) @@ -203,9 +208,14 @@ CGame::InitialiseRenderWare(void) #else rw::MatFX::modulateEnvMap = false; #endif -#elif defined(PS2_MATFX) +#else +#ifdef PS2_MATFX ReplaceMatFxCallback(); -#endif +#endif // PS2_MATFX +#ifdef DUAL_PASS_RENDERING + ReplaceAtomicPipeCallback(); +#endif // DUAL_PASS_RENDERING +#endif // LIBRW CFont::Initialise(); CHud::Initialise(); diff --git a/src/core/config.h b/src/core/config.h index 8972e7b7..9dfbad03 100644 --- a/src/core/config.h +++ b/src/core/config.h @@ -198,6 +198,7 @@ enum Config { #define ASPECT_RATIO_SCALE // Not just makes everything scale with aspect ratio, also adds support for all aspect ratios #define DEFAULT_NATIVE_RESOLUTION // Set default video mode to your native resolution (fixes Windows 10 launch) #define USE_TXD_CDIMAGE // generate and load textures from txd.img +#define DUAL_PASS_RENDERING // dual pass rendering from SkyGfx #define IMPROVED_VIDEOMODE // save and load videomode parameters instead of a magic number #define DISABLE_LOADING_SCREEN // disable the loading screen which vastly improves the loading time //#define NO_ISLAND_LOADING // disable loadscreen between islands via loading all island data at once, consumes more memory and CPU diff --git a/src/rw/RwHelper.cpp b/src/rw/RwHelper.cpp index bf70c8dc..08a8fca4 100644 --- a/src/rw/RwHelper.cpp +++ b/src/rw/RwHelper.cpp @@ -11,7 +11,11 @@ RtCharset *debugCharset; #endif -bool gPS2alphaTest = 1; +#ifdef DUAL_PASS_RENDERING +bool gPS2alphaTest = true; +#else +bool gPS2alphaTest = false; +#endif #ifndef FINAL static bool charsetOpen; @@ -644,4 +648,4 @@ RestoreAlphaTest() RwD3D8SetRenderState(D3DRS_ALPHAREF, saved_alpharef); #endif } -#endif +#endif \ No newline at end of file diff --git a/src/rw/RwMatFX.cpp b/src/rw/RwMatFX.cpp index a128ff1a..c8384b0f 100644 --- a/src/rw/RwMatFX.cpp +++ b/src/rw/RwMatFX.cpp @@ -2,7 +2,6 @@ #define WITHD3D #include "common.h" -#include "rwcore.h" #include "rpmatfx.h" struct MatFXNothing { int pad[5]; int effect; }; @@ -305,7 +304,8 @@ ReplaceMatFxCallback() { RxD3D8AllInOneSetRenderCallBack( RxPipelineFindNodeByName(RpMatFXGetD3D8Pipeline(rpMATFXD3D8ATOMICPIPELINE), RxNodeDefinitionGetD3D8AtomicAllInOne()->name, nil, nil), - _rwD3D8AtomicMatFXRenderCallback); + _rwD3D8AtomicMatFXRenderCallback); + } #endif // PS2_MATFX From 4a4feb948d0f6e67f3ff5c71a7aa23176cabb0e2 Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Wed, 29 Jul 2020 15:25:57 +0300 Subject: [PATCH 10/14] Add forgotten file --- src/rw/RwDualPass.cpp | 247 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 247 insertions(+) create mode 100644 src/rw/RwDualPass.cpp diff --git a/src/rw/RwDualPass.cpp b/src/rw/RwDualPass.cpp new file mode 100644 index 00000000..c8ebb8ad --- /dev/null +++ b/src/rw/RwDualPass.cpp @@ -0,0 +1,247 @@ +#ifndef LIBRW + +#define WITHD3D +#include "common.h" +#ifdef DUAL_PASS_RENDERING +#include "rwcore.h" + +extern "C" { +RwBool _rwD3D8RenderStateIsVertexAlphaEnable(void); +RwBool _rwD3D8RenderStateVertexAlphaEnable(RwBool enable); +RwRaster *_rwD3D8RWGetRasterStage(RwUInt32 stage); +} + +extern bool gPS2alphaTest; + +void +_rxD3D8DualPassRenderCallback(RwResEntry *repEntry, void *object, RwUInt8 type, RwUInt32 flags) +{ + RxD3D8ResEntryHeader *resEntryHeader; + RxD3D8InstanceData *instancedData; + RwInt32 numMeshes; + RwBool lighting; + RwBool vertexAlphaBlend; + RwBool forceBlack; + RwUInt32 ditherEnable; + RwUInt32 shadeMode; + void *lastVertexBuffer; + + /* Get lighting state */ + RwD3D8GetRenderState(D3DRS_LIGHTING, &lighting); + + forceBlack = FALSE; + + if (lighting) { + if (flags & rxGEOMETRY_PRELIT) { + /* Emmisive color from the vertex colors */ + RwD3D8SetRenderState(D3DRS_COLORVERTEX, TRUE); + RwD3D8SetRenderState(D3DRS_EMISSIVEMATERIALSOURCE, D3DMCS_COLOR1); + } else { + /* Emmisive color from material, set to black in the submit node */ + RwD3D8SetRenderState(D3DRS_COLORVERTEX, FALSE); + RwD3D8SetRenderState(D3DRS_EMISSIVEMATERIALSOURCE, D3DMCS_MATERIAL); + } + } else { + if ((flags & rxGEOMETRY_PRELIT) == 0) { + forceBlack = TRUE; + + RwD3D8GetRenderState(D3DRS_DITHERENABLE, &ditherEnable); + RwD3D8GetRenderState(D3DRS_SHADEMODE, &shadeMode); + + RwD3D8SetRenderState(D3DRS_TEXTUREFACTOR, 0xff000000); + RwD3D8SetRenderState(D3DRS_DITHERENABLE, FALSE); + RwD3D8SetRenderState(D3DRS_SHADEMODE, D3DSHADE_FLAT); + } + } + + /* Enable clipping */ + if (type == rpATOMIC) { + RpAtomic *atomic; + RwCamera *cam; + + atomic = (RpAtomic *)object; + + cam = RwCameraGetCurrentCamera(); + // RWASSERT(cam); + + if (RwD3D8CameraIsSphereFullyInsideFrustum(cam, RpAtomicGetWorldBoundingSphere(atomic))) { + RwD3D8SetRenderState(D3DRS_CLIPPING, FALSE); + } else { + RwD3D8SetRenderState(D3DRS_CLIPPING, TRUE); + } + } else { + RpWorldSector *worldSector; + RwCamera *cam; + + worldSector = (RpWorldSector *)object; + + cam = RwCameraGetCurrentCamera(); + // RWASSERT(cam); + + if (RwD3D8CameraIsBBoxFullyInsideFrustum(cam, RpWorldSectorGetTightBBox(worldSector))) { + RwD3D8SetRenderState(D3DRS_CLIPPING, FALSE); + } else { + RwD3D8SetRenderState(D3DRS_CLIPPING, TRUE); + } + } + + /* Set texture to NULL if hasn't any texture flags */ + if ((flags & (rxGEOMETRY_TEXTURED | rpGEOMETRYTEXTURED2)) == 0) { + RwD3D8SetTexture(NULL, 0); + + if (forceBlack) { + RwD3D8SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_SELECTARG2); + RwD3D8SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_TFACTOR); + + RwD3D8SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_DISABLE); + } + } + + /* Get vertex alpha Blend state */ + vertexAlphaBlend = _rwD3D8RenderStateIsVertexAlphaEnable(); + + /* Set Last vertex buffer to force the call */ + lastVertexBuffer = (void *)0xffffffff; + + /* Get the instanced data */ + resEntryHeader = (RxD3D8ResEntryHeader *)(repEntry + 1); + instancedData = (RxD3D8InstanceData *)(resEntryHeader + 1); + + /* + * Data shared between meshes + */ + + /* + * Set the Default Pixel shader + */ + RwD3D8SetPixelShader(0); + + /* + * Vertex shader + */ + RwD3D8SetVertexShader(instancedData->vertexShader); + + /* Get the number of meshes */ + numMeshes = resEntryHeader->numMeshes; + while (numMeshes--) { + // RWASSERT(instancedData->material != NULL); + + if ((flags & (rxGEOMETRY_TEXTURED | rpGEOMETRYTEXTURED2))) { + RwD3D8SetTexture(instancedData->material->texture, 0); + + if (forceBlack) { + /* Only change the colorop, we need to use the texture alpha channel */ + RwD3D8SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_SELECTARG2); + RwD3D8SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_TFACTOR); + } + } + + if (instancedData->vertexAlpha || (0xFF != instancedData->material->color.alpha)) { + if (!vertexAlphaBlend) { + vertexAlphaBlend = TRUE; + + _rwD3D8RenderStateVertexAlphaEnable(TRUE); + } + } else { + if (vertexAlphaBlend) { + vertexAlphaBlend = FALSE; + + _rwD3D8RenderStateVertexAlphaEnable(FALSE); + } + } + + if (lighting) { + if (instancedData->vertexAlpha) { + RwD3D8SetRenderState(D3DRS_DIFFUSEMATERIALSOURCE, D3DMCS_COLOR1); + } else { + RwD3D8SetRenderState(D3DRS_DIFFUSEMATERIALSOURCE, D3DMCS_MATERIAL); + } + + RwD3D8SetSurfaceProperties(&instancedData->material->color, &instancedData->material->surfaceProps, (flags & rxGEOMETRY_MODULATE)); + } + + /* + * Render + */ + + /* Set the stream source */ + if (lastVertexBuffer != instancedData->vertexBuffer) { + RwD3D8SetStreamSource(0, instancedData->vertexBuffer, instancedData->stride); + + lastVertexBuffer = instancedData->vertexBuffer; + } + if (!gPS2alphaTest) { + /* Set the Index buffer */ + if (instancedData->indexBuffer != NULL) { + RwD3D8SetIndices(instancedData->indexBuffer, instancedData->baseIndex); + + /* Draw the indexed primitive */ + RwD3D8DrawIndexedPrimitive((D3DPRIMITIVETYPE)instancedData->primType, 0, instancedData->numVertices, 0, instancedData->numIndices); + } else { + RwD3D8DrawPrimitive((D3DPRIMITIVETYPE)instancedData->primType, instancedData->baseIndex, instancedData->numVertices); + } + } else { + RwD3D8SetIndices(instancedData->indexBuffer, instancedData->baseIndex); + + int hasAlpha, alphafunc, alpharef, zwrite; + RwD3D8GetRenderState(D3DRS_ALPHABLENDENABLE, &hasAlpha); + RwD3D8GetRenderState(D3DRS_ZWRITEENABLE, &zwrite); + if (hasAlpha && zwrite) { + RwD3D8GetRenderState(D3DRS_ALPHAFUNC, &alphafunc); + RwD3D8GetRenderState(D3DRS_ALPHAREF, &alpharef); + + RwD3D8SetRenderState(D3DRS_ALPHAFUNC, D3DCMP_GREATEREQUAL); + RwD3D8SetRenderState(D3DRS_ALPHAREF, 128); + + if (instancedData->indexBuffer) + RwD3D8DrawIndexedPrimitive(instancedData->primType, 0, instancedData->numVertices, 0, instancedData->numIndices); + else + RwD3D8DrawPrimitive(instancedData->primType, instancedData->baseIndex, instancedData->numVertices); + + RwD3D8SetRenderState(D3DRS_ALPHAFUNC, D3DCMP_LESS); + RwRenderStateSet(rwRENDERSTATEZWRITEENABLE, FALSE); + + if (instancedData->indexBuffer) + RwD3D8DrawIndexedPrimitive(instancedData->primType, 0, instancedData->numVertices, 0, instancedData->numIndices); + else + RwD3D8DrawPrimitive(instancedData->primType, instancedData->baseIndex, instancedData->numVertices); + + RwD3D8SetRenderState(D3DRS_ALPHAFUNC, alphafunc); + RwD3D8SetRenderState(D3DRS_ALPHAREF, alpharef); + RwRenderStateSet(rwRENDERSTATEZWRITEENABLE, (void *)TRUE); + } else { + if (instancedData->indexBuffer) + RwD3D8DrawIndexedPrimitive(instancedData->primType, 0, instancedData->numVertices, 0, instancedData->numIndices); + else + RwD3D8DrawPrimitive(instancedData->primType, instancedData->baseIndex, instancedData->numVertices); + } + } + + /* Move onto the next instancedData */ + instancedData++; + } + + if (forceBlack) { + RwD3D8SetRenderState(D3DRS_DITHERENABLE, ditherEnable); + RwD3D8SetRenderState(D3DRS_SHADEMODE, shadeMode); + + if (_rwD3D8RWGetRasterStage(0)) { + RwD3D8SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_MODULATE); + RwD3D8SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE); + } else { + RwD3D8SetTextureStageState(0, D3DTSS_COLOROP, D3DTOP_SELECTARG2); + RwD3D8SetTextureStageState(0, D3DTSS_COLORARG2, D3DTA_DIFFUSE); + } + } +} + +void +ReplaceAtomicPipeCallback() +{ + RxD3D8AllInOneSetRenderCallBack(RxPipelineFindNodeByName(RXPIPELINEGLOBAL(platformAtomicPipeline), RxNodeDefinitionGetD3D8AtomicAllInOne()->name, nil, nil), + _rxD3D8DualPassRenderCallback); +} + +#endif // DUAL_PASS_RENDERING + +#endif // !LIBRW \ No newline at end of file From e13d80a4ebfdaa89de3ad2eb6dc9ec6fbc1d3132 Mon Sep 17 00:00:00 2001 From: aap Date: Wed, 29 Jul 2020 14:31:34 +0200 Subject: [PATCH 11/14] rename shit --- src/core/Game.cpp | 8 ++++---- src/core/config.h | 2 +- src/rw/RwHelper.cpp | 2 +- src/rw/{RwDualPass.cpp => RwPS2AlphaTest.cpp} | 4 ++-- 4 files changed, 8 insertions(+), 8 deletions(-) rename src/rw/{RwDualPass.cpp => RwPS2AlphaTest.cpp} (99%) diff --git a/src/core/Game.cpp b/src/core/Game.cpp index 2c9e784c..82e6992d 100644 --- a/src/core/Game.cpp +++ b/src/core/Game.cpp @@ -153,9 +153,9 @@ CGame::InitialiseOnceBeforeRW(void) #ifdef PS2_MATFX void ReplaceMatFxCallback(); #endif // PS2_MATFX -#ifdef DUAL_PASS_RENDERING +#ifdef PS2_ALPHA_TEST void ReplaceAtomicPipeCallback(); -#endif // DUAL_PASS_RENDERING +#endif // PS2_ALPHA_TEST #endif // !LIBRW bool @@ -212,9 +212,9 @@ CGame::InitialiseRenderWare(void) #ifdef PS2_MATFX ReplaceMatFxCallback(); #endif // PS2_MATFX -#ifdef DUAL_PASS_RENDERING +#ifdef PS2_ALPHA_TEST ReplaceAtomicPipeCallback(); -#endif // DUAL_PASS_RENDERING +#endif // PS2_ALPHA_TEST #endif // LIBRW CFont::Initialise(); diff --git a/src/core/config.h b/src/core/config.h index 9dfbad03..94a35782 100644 --- a/src/core/config.h +++ b/src/core/config.h @@ -198,7 +198,7 @@ enum Config { #define ASPECT_RATIO_SCALE // Not just makes everything scale with aspect ratio, also adds support for all aspect ratios #define DEFAULT_NATIVE_RESOLUTION // Set default video mode to your native resolution (fixes Windows 10 launch) #define USE_TXD_CDIMAGE // generate and load textures from txd.img -#define DUAL_PASS_RENDERING // dual pass rendering from SkyGfx +#define PS2_ALPHA_TEST // emulate ps2 alpha test #define IMPROVED_VIDEOMODE // save and load videomode parameters instead of a magic number #define DISABLE_LOADING_SCREEN // disable the loading screen which vastly improves the loading time //#define NO_ISLAND_LOADING // disable loadscreen between islands via loading all island data at once, consumes more memory and CPU diff --git a/src/rw/RwHelper.cpp b/src/rw/RwHelper.cpp index 08a8fca4..f568532a 100644 --- a/src/rw/RwHelper.cpp +++ b/src/rw/RwHelper.cpp @@ -11,7 +11,7 @@ RtCharset *debugCharset; #endif -#ifdef DUAL_PASS_RENDERING +#ifdef PS2_ALPHA_TEST bool gPS2alphaTest = true; #else bool gPS2alphaTest = false; diff --git a/src/rw/RwDualPass.cpp b/src/rw/RwPS2AlphaTest.cpp similarity index 99% rename from src/rw/RwDualPass.cpp rename to src/rw/RwPS2AlphaTest.cpp index c8ebb8ad..c0d68355 100644 --- a/src/rw/RwDualPass.cpp +++ b/src/rw/RwPS2AlphaTest.cpp @@ -2,7 +2,7 @@ #define WITHD3D #include "common.h" -#ifdef DUAL_PASS_RENDERING +#ifdef PS2_ALPHA_TEST #include "rwcore.h" extern "C" { @@ -242,6 +242,6 @@ ReplaceAtomicPipeCallback() _rxD3D8DualPassRenderCallback); } -#endif // DUAL_PASS_RENDERING +#endif // PS2_ALPHA_TEST #endif // !LIBRW \ No newline at end of file From 550b813d92f484fb278cd2e1606cc262d217ffb4 Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Wed, 29 Jul 2020 16:08:01 +0300 Subject: [PATCH 12/14] premake fix --- premake5.lua | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/premake5.lua b/premake5.lua index 87cb9e2d..3ddc554e 100644 --- a/premake5.lua +++ b/premake5.lua @@ -211,10 +211,11 @@ project "re3" includedirs { "opusfile/include" } end - libdirs { "milessdk/lib" } - libdirs { "openal-soft/libs/Win32" } - libdirs { "mpg123/lib" } - libdirs { "libsndfile/lib" } + filter "platforms:*mss" + defines { "AUDIO_MSS" } + includedirs { "milessdk/include" } + libdirs { "sdk/milessdk/lib" } + if _OPTIONS["with-opus"] then filter "platforms:win*" libdirs { "ogg/win32/VS2015/Win32/%{cfg.buildcfg}" } From e823e018600bbc71fd4a58c50d86f1bd2ce467ff Mon Sep 17 00:00:00 2001 From: Sergeanur Date: Wed, 29 Jul 2020 16:10:59 +0300 Subject: [PATCH 13/14] more fix --- premake5.lua | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/premake5.lua b/premake5.lua index 3ddc554e..57db0fe8 100644 --- a/premake5.lua +++ b/premake5.lua @@ -214,7 +214,7 @@ project "re3" filter "platforms:*mss" defines { "AUDIO_MSS" } includedirs { "milessdk/include" } - libdirs { "sdk/milessdk/lib" } + libdirs { "milessdk/lib" } if _OPTIONS["with-opus"] then filter "platforms:win*" From 8ceeb106ef10126e8e8429c096cadafc689f1ae0 Mon Sep 17 00:00:00 2001 From: shfil Date: Wed, 29 Jul 2020 18:25:27 +0200 Subject: [PATCH 14/14] Update README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 71a982e9..5d336435 100644 --- a/README.md +++ b/README.md @@ -31,7 +31,7 @@ such that we have a working game at all times. - **If you use 64-bit D3D9**: We don't ship 64-bit Dx9 SDK. You need to download it from Microsoft if you don't have it(although it should come pre-installed after some Windows version) -> :information_source: **If you choose OpenAL(OAL) on Windows** You must read [Running OAL build on Windows](https://github.com/GTAmodding/re3/wiki/Running-OAL-build-on-Windows). +> :information_source: **If you choose OpenAL on Windows** You must read [Running OpenAL build on Windows](https://github.com/GTAmodding/re3/wiki/Running-OpenAL-build-on-Windows). > :information_source: **Did you notice librw?** re3 uses completely homebrew RenderWare-replacement rendering engine; [librw](https://github.com/aap/librw/). librw comes as submodule of re3, but you also can use LIBRW enviorenment variable to specify path to your own librw.