From f9d2dc51d0ea3a37ec25cc9ba98d53927406549c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 22 Dec 2019 10:20:47 +0100 Subject: [PATCH 01/15] - cleanup of new colorization code. - profiling shows that running the code for applying the colorization and the gradients is extremely expensive, apparently this always causes a cache miss, so now the entire thing is enabled by a sidedef flag. --- src/gamedata/r_defs.h | 155 ++++++++++---------- src/maploader/udmf.cpp | 25 +++- src/maploader/udmf.h | 8 +- src/rendering/hwrenderer/scene/hw_walls.cpp | 54 +++---- 4 files changed, 135 insertions(+), 107 deletions(-) diff --git a/src/gamedata/r_defs.h b/src/gamedata/r_defs.h index 6b345692e..d9f30dd8b 100644 --- a/src/gamedata/r_defs.h +++ b/src/gamedata/r_defs.h @@ -611,12 +611,64 @@ struct TextureManipulation BlendOverlay = 3, BlendHardLight = 4, BlendMask = 7, - InvertBit = 8 + InvertBit = 8, + ActiveBit = 16, // Must be set for the shader to do something }; PalEntry AddColor; // Alpha contains the blend flags PalEntry ModulateColor; // Alpha may contain a multiplier to get higher values than 1.0 without promoting this to 4 full floats. PalEntry BlendColor; float DesaturationFactor; + + bool CheckIfEnabled() // check if this manipulation is doing something. NoOps do not need to be preserved, unless they override older setttings. + { + if (AddColor != 0 || // this includes a check for the blend mode without which BlendColor is not active + ModulateColor != 0x01ffffff || // 1 in alpha must be the default for a no-op. + DesaturationFactor != 0) + { + AddColor.a |= ActiveBit; // mark as active for the shader's benefit. + return true; + } + return false; + } + + void SetTextureModulateColor(int slot, PalEntry rgb) + { + rgb.a = ModulateColor.a; + ModulateColor = rgb; + } + + void SetTextureModulateScaleFactor(int slot, int fac) + { + ModulateColor.a = (uint8_t)fac; + } + + void SetTextureAdditiveColor(int slot, PalEntry rgb) + { + rgb.a = AddColor.a; + AddColor = rgb; + } + + void SetTextureBlendColor(int slot, PalEntry rgb) + { + BlendColor = rgb; + } + + void SetTextureDesaturationFactor(int slot, double fac) + { + DesaturationFactor = (float)fac; + } + + void SetTextureBlendMode(int slot, int mode) + { + AddColor.a = (AddColor.a & ~TextureManipulation::BlendMask) | (mode & TextureManipulation::BlendMask); + } + + void SetTextureInvert(bool on) + { + AddColor.a |= TextureManipulation::InvertBit; + AddColor.a &= ~TextureManipulation::InvertBit; + } + }; struct sector_t @@ -1047,21 +1099,32 @@ public: Flags &= ~SECF_SPECIALFLAGS; } + void CheckExColorFlag(); + + void InitAllExcolors() + { + if (SpecialColors[sector_t::wallbottom] != 0xffffffff || SpecialColors[sector_t::walltop] != 0xffffffff || AdditiveColors[sector_t::walltop] != 0xffffffff) CheckExColorFlag(); + } + void SetSpecialColor(int slot, int r, int g, int b) { SpecialColors[slot] = PalEntry(255, r, g, b); + if ((slot == sector_t::wallbottom || slot == sector_t::walltop) && SpecialColors[slot] != 0xffffffff) CheckExColorFlag(); } void SetSpecialColor(int slot, PalEntry rgb) { rgb.a = 255; SpecialColors[slot] = rgb; + if ((slot == sector_t::wallbottom || slot == sector_t::walltop) && rgb != 0xffffffff) CheckExColorFlag(); } void SetAdditiveColor(int slot, PalEntry rgb) { rgb.a = 255; AdditiveColors[slot] = rgb; + if ((slot == sector_t::walltop) && AdditiveColors[slot] != 0xffffffff) CheckExColorFlag(); // Wallbottom of this is not used. + } // TextureFX parameters @@ -1071,44 +1134,6 @@ public: planes[slot].TextureFx = tm; // this is for getting the data from a texture. } - void SetTextureModulateColor(int slot, PalEntry rgb) - { - rgb.a = planes[slot].TextureFx.ModulateColor.a; - planes[slot].TextureFx.ModulateColor = rgb; - } - - void SetTextureModulateScaleFactor(int slot, int fac) - { - planes[slot].TextureFx.ModulateColor.a = (uint8_t)fac; - } - - void SetTextureAdditiveColor(int slot, PalEntry rgb) - { - rgb.a = planes[slot].TextureFx.AddColor.a; - planes[slot].TextureFx.AddColor = rgb; - } - - void SetTextureBlendColor(int slot, PalEntry rgb) - { - planes[slot].TextureFx.BlendColor = rgb; - } - - void SetTextureDesaturationFactor(int slot, double fac) - { - planes[slot].TextureFx.DesaturationFactor = (float)fac; - } - - void SetTextureBlendMode(int slot, int mode) - { - planes[slot].TextureFx.AddColor.a = (planes[slot].TextureFx.AddColor.a & ~TextureManipulation::BlendMask) | (mode & TextureManipulation::BlendMask); - } - - void SetTextureInvert(int slot, bool on) - { - if (on) planes[slot].TextureFx.AddColor.a |= TextureManipulation::InvertBit; - else planes[slot].TextureFx.AddColor.a &= ~TextureManipulation::InvertBit; - } - inline bool PortalBlocksView(int plane); inline bool PortalBlocksSight(int plane); @@ -1194,6 +1219,7 @@ enum WALLF_WRAP_MIDTEX = 32, // Like the line counterpart, but only for this side. WALLF_POLYOBJ = 64, // This wall belongs to a polyobject. WALLF_LIGHT_FOG = 128, // This wall's Light is used even in fog. + WALLF_EXTCOLOR = 256, // enables the extended color options (flagged to allow the renderer to easily skip the relevant code) }; struct side_t @@ -1385,10 +1411,11 @@ struct side_t void EnableAdditiveColor(int which, bool enable) { - int flag = enable ? part::UseOwnAdditiveColor : 0; + const int flag = part::UseOwnAdditiveColor; if (enable) { textures[which].flags |= flag; + Flags |= WALLF_EXTCOLOR; } else { @@ -1402,42 +1429,10 @@ struct side_t textures[which].AdditiveColor = rgb; } - void SetTextureModulateColor(int slot, PalEntry rgb) + void SetTextureFx(int slot, const TextureManipulation& tm) { - rgb.a = textures[slot].TextureFx.ModulateColor.a; - textures[slot].TextureFx.ModulateColor = rgb; - } - - void SetTextureModulateScaleFactor(int slot, int fac) - { - textures[slot].TextureFx.ModulateColor.a = (uint8_t)fac; - } - - void SetTextureAdditiveColor(int slot, PalEntry rgb) - { - rgb.a = textures[slot].TextureFx.AddColor.a; - textures[slot].TextureFx.AddColor = rgb; - } - - void SetTextureBlendColor(int slot, PalEntry rgb) - { - textures[slot].TextureFx.BlendColor = rgb; - } - - void SetTextureDesaturationFactor(int slot, double fac) - { - textures[slot].TextureFx.DesaturationFactor = (float)fac; - } - - void SetTextureBlendMode(int slot, int mode) - { - textures[slot].TextureFx.AddColor.a = (textures[slot].TextureFx.AddColor.a & ~TextureManipulation::BlendMask) | (mode & TextureManipulation::BlendMask); - } - - void SetTextureInvert(int slot, bool on) - { - if (on) textures[slot].TextureFx.AddColor.a |= TextureManipulation::InvertBit; - else textures[slot].TextureFx.AddColor.a &= ~TextureManipulation::InvertBit; + textures[slot].TextureFx = tm; // this is for getting the data from a texture. + if (tm.AddColor.a) Flags |= WALLF_EXTCOLOR; } PalEntry GetAdditiveColor(int which, sector_t *frontsector) const @@ -1785,5 +1780,15 @@ inline int sector_t::GetFloorLight() const { return ::GetFloorLight(this); } inline int sector_t::GetCeilingLight() const { return ::GetCeilingLight(this); } inline double sector_t::GetFriction(int plane, double *movefac) const { return ::GetFriction(this, plane, movefac); } +inline void sector_t::CheckExColorFlag() +{ + for (auto ld : Lines) + { + if (ld->frontsector == this) ld->sidedef[0]->Flags |= WALLF_EXTCOLOR; + if (ld->backsector == this) ld->sidedef[1]->Flags |= WALLF_EXTCOLOR; + } +} + + #endif diff --git a/src/maploader/udmf.cpp b/src/maploader/udmf.cpp index 8226f525d..b1c0ba054 100644 --- a/src/maploader/udmf.cpp +++ b/src/maploader/udmf.cpp @@ -1308,7 +1308,8 @@ public: break; case NAME_useowncolors_top: - Flag(sd->textures[side_t::top].flags, side_t::part::UseOwnSpecialColors, key); + if (Flag(sd->textures[side_t::top].flags, side_t::part::UseOwnSpecialColors, key)) + sd->Flags |= WALLF_EXTCOLOR; break; case NAME_uppercolor_top: @@ -1332,7 +1333,9 @@ public: break; case NAME_useowncolors_mid: - Flag(sd->textures[side_t::mid].flags, side_t::part::UseOwnSpecialColors, key); + if (Flag(sd->textures[side_t::mid].flags, side_t::part::UseOwnSpecialColors, key)) + sd->Flags |= WALLF_EXTCOLOR; + break; case NAME_uppercolor_mid: @@ -1356,7 +1359,8 @@ public: break; case NAME_useowncolors_bottom: - Flag(sd->textures[side_t::bottom].flags, side_t::part::UseOwnSpecialColors, key); + if (Flag(sd->textures[side_t::bottom].flags, side_t::part::UseOwnSpecialColors, key)) + sd->Flags |= WALLF_EXTCOLOR; break; case NAME_uppercolor_bottom: @@ -1380,13 +1384,17 @@ public: break; case NAME_useowncoloradd_top: - sd->textures[side_t::top].flags |= side_t::part::UseOwnAdditiveColor * CheckBool(key); + Flag(sd->textures[side_t::top].flags, side_t::part::UseOwnAdditiveColor, key); + sd->Flags |= WALLF_EXTCOLOR; case NAME_useowncoloradd_mid: - sd->textures[side_t::mid].flags |= side_t::part::UseOwnAdditiveColor * CheckBool(key); + if (Flag(sd->textures[side_t::mid].flags, side_t::part::UseOwnAdditiveColor, key)) + sd->Flags |= WALLF_EXTCOLOR; case NAME_useowncoloradd_bottom: - sd->textures[side_t::bottom].flags |= side_t::part::UseOwnAdditiveColor * CheckBool(key); + if (Flag(sd->textures[side_t::bottom].flags, side_t::part::UseOwnAdditiveColor, key)) + sd->Flags |= WALLF_EXTCOLOR; + break; default: break; @@ -2284,6 +2292,11 @@ public: // Create the real linedefs and decompress the sidedefs ProcessLineDefs(); + // enable the excolor flag on all sidedefs which need it for a gradient transfer from the sector. + for (auto& sec : Level->sectors) + { + sec.CheckExColorFlag(); + } } }; diff --git a/src/maploader/udmf.h b/src/maploader/udmf.h index 8e0901755..a6f402bf1 100644 --- a/src/maploader/udmf.h +++ b/src/maploader/udmf.h @@ -23,12 +23,18 @@ protected: const char *CheckString(const char *key); template - void Flag(T &value, int mask, const char *key) + bool Flag(T &value, int mask, const char *key) { if (CheckBool(key)) + { value |= mask; + return true; + } else + { value &= ~mask; + return false; + } } }; diff --git a/src/rendering/hwrenderer/scene/hw_walls.cpp b/src/rendering/hwrenderer/scene/hw_walls.cpp index 9b98bc28a..1873ce5d3 100644 --- a/src/rendering/hwrenderer/scene/hw_walls.cpp +++ b/src/rendering/hwrenderer/scene/hw_walls.cpp @@ -168,38 +168,42 @@ void HWWall::RenderTexturedWall(HWDrawInfo *di, FRenderState &state, int rflags) if (type != RENDERWALL_COLOR && seg->sidedef != nullptr) { auto side = seg->sidedef; - auto tierndx = renderwalltotier[type]; - auto &tier = side->textures[tierndx]; - PalEntry color1 = side->GetSpecialColor(tierndx, side_t::walltop, frontsector); - PalEntry color2 = side->GetSpecialColor(tierndx, side_t::wallbottom, frontsector); - state.SetObjectColor(color1); - state.SetObjectColor2((color1 != color2) ? color2 : PalEntry(0)); - state.SetAddColor(side->GetAdditiveColor(tierndx, frontsector)); - state.ApplyTextureManipulation(&side->textures[tierndx].TextureFx); - - if (color1 != color2) + if (seg->sidedef->Flags & WALLF_EXTCOLOR) // this block incurs a costly cache miss, so only process if needed. { - // Do gradient setup only if there actually is a gradient. - state.EnableGradient(true); - if ((tier.flags & side_t::part::ClampGradient) && backsector) + auto tierndx = renderwalltotier[type]; + auto& tier = side->textures[tierndx]; + PalEntry color1 = side->GetSpecialColor(tierndx, side_t::walltop, frontsector); + PalEntry color2 = side->GetSpecialColor(tierndx, side_t::wallbottom, frontsector); + state.SetObjectColor(color1); + state.SetObjectColor2((color1 != color2) ? color2 : PalEntry(0)); + state.SetAddColor(side->GetAdditiveColor(tierndx, frontsector)); + state.ApplyTextureManipulation(&tier.TextureFx); + + if (color1 != color2) { - if (tierndx == side_t::top) + // Do gradient setup only if there actually is a gradient. + + state.EnableGradient(true); + if ((tier.flags & side_t::part::ClampGradient) && backsector) { - state.SetGradientPlanes(frontsector->ceilingplane, backsector->ceilingplane); + if (tierndx == side_t::top) + { + state.SetGradientPlanes(frontsector->ceilingplane, backsector->ceilingplane); + } + else if (tierndx == side_t::mid) + { + state.SetGradientPlanes(backsector->ceilingplane, backsector->floorplane); + } + else // side_t::bottom: + { + state.SetGradientPlanes(backsector->floorplane, frontsector->floorplane); + } } - else if (tierndx == side_t::mid) + else { - state.SetGradientPlanes(backsector->ceilingplane, backsector->floorplane); + state.SetGradientPlanes(frontsector->ceilingplane, frontsector->floorplane); } - else // side_t::bottom: - { - state.SetGradientPlanes(backsector->floorplane, frontsector->floorplane); - } - } - else - { - state.SetGradientPlanes(frontsector->ceilingplane, frontsector->floorplane); } } } From 9b9fd35107493ea38fc77a6d1c2478e322a5681d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 22 Dec 2019 16:08:34 +0100 Subject: [PATCH 02/15] - hooked up the colorization feature. It can now be used from UDMF and ZScript. To avoid clutter it doesn't allow setting the values individually but requires definition of a data record in TEXTURES. colorization { DesaturationFactor Invert AddColor ModulateColor BlendColor , [, ] } Mode for BlendColor can be Alpha (normal translucent blending), as well as 3 special values taken from Build engine games: Screen, Overlay and HardLight. --- specs/udmf_zdoom.txt | 9 +++ src/gamedata/r_defs.h | 89 ++++-------------------- src/gamedata/textures/texturemanager.cpp | 76 ++++++++++++++++++-- src/gamedata/textures/textures.h | 8 +++ src/maploader/udmf.cpp | 20 ++++++ src/p_saveg.cpp | 27 +++++++ src/r_data/r_translate.h | 71 +++++++++++++++++++ src/scripting/vmthunks.cpp | 37 ++++++++++ src/utility/namedef.h | 5 ++ wadsrc/static/zscript/mapdata.zs | 2 + 10 files changed, 265 insertions(+), 79 deletions(-) diff --git a/specs/udmf_zdoom.txt b/specs/udmf_zdoom.txt index 2f30e4df9..2559ebe78 100644 --- a/specs/udmf_zdoom.txt +++ b/specs/udmf_zdoom.txt @@ -210,6 +210,9 @@ Note: All fields default to false unless mentioned otherwise. coloradd_top = ; // Additive material color to apply to top section of sidedef. Default is black (0x000000) coloradd_mid = ; // Additive material color to apply to middle section of sidedef. Default is black (0x000000) coloradd_bottom = ; // Additive material color to apply to bottom section of sidedef. Default is black (0x000000) + colorization_top = ; // Sets a colorization record for the upper texture. Colorization records must be defined in TEXTURES. + colorization_mid = ; // Sets a colorization record for the middle texture. Colorization records must be defined in TEXTURES. + colorization_bottom = ; // Sets a colorization record for the lower texture. Colorization records must be defined in TEXTURES. } sector @@ -288,6 +291,9 @@ Note: All fields default to false unless mentioned otherwise. coloradd_sprites = ; // Additive material color applied to sprites within the sector. Default is black (0x000000) coloradd_walls = ; // Additive material color applied to walls within the sector. Default is black (0x000000) + colorization_floor = ; // Sets a colorization record for the floor texture. Colorization records must be defined in TEXTURES. + colorization_ceiling = ; // Sets a colorization record for the ceiling texture. Colorization records must be defined in TEXTURES. + portal_ceil_blocksound = ; // ceiling portal blocks sound. portal_ceil_disabled = ; // ceiling portal disabled. portal_ceil_nopass = ; // ceiling portal blocks movement if true. @@ -495,6 +501,9 @@ arg0str in dynamic lights. Added automapstyle and revealed linedef properties. Replaced tabs with spaces. +1.31 22.12.2019 +Coloriation options added + =============================================================================== EOF =============================================================================== diff --git a/src/gamedata/r_defs.h b/src/gamedata/r_defs.h index d9f30dd8b..8c551ba0c 100644 --- a/src/gamedata/r_defs.h +++ b/src/gamedata/r_defs.h @@ -34,6 +34,7 @@ #include "templates.h" #include "m_bbox.h" #include "dobjgc.h" +#include "r_data/r_translate.h" // Some more or less basic data types // we depend on. @@ -601,76 +602,6 @@ FSerializer &Serialize(FSerializer &arc, const char *key, secspecial_t &spec, se enum class EMoveResult { ok, crushed, pastdest }; -struct TextureManipulation -{ - enum - { - BlendNone = 0, - BlendAlpha = 1, - BlendScreen = 2, - BlendOverlay = 3, - BlendHardLight = 4, - BlendMask = 7, - InvertBit = 8, - ActiveBit = 16, // Must be set for the shader to do something - }; - PalEntry AddColor; // Alpha contains the blend flags - PalEntry ModulateColor; // Alpha may contain a multiplier to get higher values than 1.0 without promoting this to 4 full floats. - PalEntry BlendColor; - float DesaturationFactor; - - bool CheckIfEnabled() // check if this manipulation is doing something. NoOps do not need to be preserved, unless they override older setttings. - { - if (AddColor != 0 || // this includes a check for the blend mode without which BlendColor is not active - ModulateColor != 0x01ffffff || // 1 in alpha must be the default for a no-op. - DesaturationFactor != 0) - { - AddColor.a |= ActiveBit; // mark as active for the shader's benefit. - return true; - } - return false; - } - - void SetTextureModulateColor(int slot, PalEntry rgb) - { - rgb.a = ModulateColor.a; - ModulateColor = rgb; - } - - void SetTextureModulateScaleFactor(int slot, int fac) - { - ModulateColor.a = (uint8_t)fac; - } - - void SetTextureAdditiveColor(int slot, PalEntry rgb) - { - rgb.a = AddColor.a; - AddColor = rgb; - } - - void SetTextureBlendColor(int slot, PalEntry rgb) - { - BlendColor = rgb; - } - - void SetTextureDesaturationFactor(int slot, double fac) - { - DesaturationFactor = (float)fac; - } - - void SetTextureBlendMode(int slot, int mode) - { - AddColor.a = (AddColor.a & ~TextureManipulation::BlendMask) | (mode & TextureManipulation::BlendMask); - } - - void SetTextureInvert(bool on) - { - AddColor.a |= TextureManipulation::InvertBit; - AddColor.a &= ~TextureManipulation::InvertBit; - } - -}; - struct sector_t { @@ -1129,9 +1060,10 @@ public: // TextureFX parameters - void SetTextureFx(int slot, const TextureManipulation &tm) + void SetTextureFx(int slot, const TextureManipulation *tm) { - planes[slot].TextureFx = tm; // this is for getting the data from a texture. + if (tm) planes[slot].TextureFx = *tm; // this is for getting the data from a texture. + else planes[slot].TextureFx = {}; } @@ -1429,10 +1361,17 @@ struct side_t textures[which].AdditiveColor = rgb; } - void SetTextureFx(int slot, const TextureManipulation& tm) + void SetTextureFx(int slot, const TextureManipulation* tm) { - textures[slot].TextureFx = tm; // this is for getting the data from a texture. - if (tm.AddColor.a) Flags |= WALLF_EXTCOLOR; + if (tm) + { + textures[slot].TextureFx = *tm; // this is for getting the data from a texture. + if (tm->AddColor.a) Flags |= WALLF_EXTCOLOR; + } + else + { + textures[slot].TextureFx = {}; + } } PalEntry GetAdditiveColor(int which, sector_t *frontsector) const diff --git a/src/gamedata/textures/texturemanager.cpp b/src/gamedata/textures/texturemanager.cpp index 1bdbf9624..cc2dc548f 100644 --- a/src/gamedata/textures/texturemanager.cpp +++ b/src/gamedata/textures/texturemanager.cpp @@ -141,6 +141,7 @@ void FTextureManager::DeleteAll() } mAnimatedDoors.Clear(); BuildTileData.Clear(); + tmanips.Clear(); } //========================================================================== @@ -688,6 +689,69 @@ void FTextureManager::AddHiresTextures (int wadnum) // //========================================================================== +void FTextureManager::ParseColorization(FScanner& sc) +{ + TextureManipulation tm = {}; + sc.MustGetString(); + FName cname = sc.String; + sc.MustGetToken('{'); + while (!sc.CheckToken('}')) + { + if (sc.Compare("desaturation")) + { + sc.MustGetFloat(); + tm.DesaturationFactor = sc.Float; + } + else if (sc.Compare("AddColor")) + { + sc.MustGetString(); + tm.AddColor = (tm.AddColor & 0xff000000) | (V_GetColor(NULL, sc) & 0xffffff); + } + else if (sc.Compare("ModulateColor")) + { + sc.MustGetString(); + tm.ModulateColor = V_GetColor(NULL, sc) & 0xffffff; + if (sc.CheckToken(',')) + { + sc.MustGetNumber(); + tm.ModulateColor.a = sc.Number; + } + } + else if (sc.Compare("BlendColor")) + { + sc.MustGetString(); + tm.BlendColor = V_GetColor(NULL, sc) & 0xffffff; + sc.MustGetToken(','); + sc.MustGetString(); + static const char* opts[] = {"none", "alpha", "screen", "overlay", "hardlight", nullptr}; + tm.AddColor.a = (tm.AddColor.a & ~TextureManipulation::BlendMask) | sc.MustMatchString(opts); + if (sc.CheckToken(',')) + { + sc.MustGetFloat(); + tm.BlendColor.a = clamp(sc.Float, 0., 1.) * 255; + } + } + else if (sc.Compare("invert")) + { + tm.AddColor.a |= TextureManipulation::InvertBit; + } + } + if (tm.CheckIfEnabled()) + { + tmanips.Insert(cname, tm); + } + else + { + tmanips.Remove(cname); + } + +} +//========================================================================== +// +// Loads the HIRESTEX lumps +// +//========================================================================== + void FTextureManager::LoadTextureDefs(int wadnum, const char *lumpname, FMultipatchTextureBuilder &build) { int remapLump, lastLump; @@ -824,19 +888,23 @@ void FTextureManager::ParseTextureDef(int lump, FMultipatchTextureBuilder &build } else if (sc.Compare("sprite")) { - build.ParseTexture(sc, ETextureType::Sprite); + build.ParseTexture(sc, ETextureType::Sprite); } else if (sc.Compare("walltexture")) { - build.ParseTexture(sc, ETextureType::Wall); + build.ParseTexture(sc, ETextureType::Wall); } else if (sc.Compare("flat")) { - build.ParseTexture(sc, ETextureType::Flat); + build.ParseTexture(sc, ETextureType::Flat); } else if (sc.Compare("graphic")) { - build.ParseTexture(sc, ETextureType::MiscPatch); + build.ParseTexture(sc, ETextureType::MiscPatch); + } + else if (sc.Compare("colorization")) + { + ParseColorization(sc); } else if (sc.Compare("#include")) { diff --git a/src/gamedata/textures/textures.h b/src/gamedata/textures/textures.h index 279119915..416d9e719 100644 --- a/src/gamedata/textures/textures.h +++ b/src/gamedata/textures/textures.h @@ -601,6 +601,7 @@ public: void AddPatches (int lumpnum); void AddHiresTextures (int wadnum); void LoadTextureDefs(int wadnum, const char *lumpname, FMultipatchTextureBuilder &build); + void ParseColorization(FScanner& sc); void ParseTextureDef(int remapLump, FMultipatchTextureBuilder &build); void SortTexturesByType(int start, int end); bool AreTexturesCompatible (FTextureID picnum1, FTextureID picnum2); @@ -626,6 +627,12 @@ public: FSwitchDef *FindSwitch (FTextureID texture); FDoorAnimation *FindAnimatedDoor (FTextureID picnum); + TextureManipulation* GetTextureManipulation(FName name) + { + return tmanips.CheckKey(name); + } + + private: // texture counting @@ -683,6 +690,7 @@ private: TArray mSwitchDefs; TArray mAnimatedDoors; + TMap tmanips; public: TArray mAnimations; diff --git a/src/maploader/udmf.cpp b/src/maploader/udmf.cpp index b1c0ba054..c1aae1715 100644 --- a/src/maploader/udmf.cpp +++ b/src/maploader/udmf.cpp @@ -1295,6 +1295,18 @@ public: Flag(sd->Flags, WALLF_NOAUTODECALS, key); continue; + case NAME_colorization_top: + sd->SetTextureFx(side_t::top, TexMan.GetTextureManipulation(CheckString(key))); + break; + + case NAME_colorization_mid: + sd->SetTextureFx(side_t::mid, TexMan.GetTextureManipulation(CheckString(key))); + break; + + case NAME_colorization_bottom: + sd->SetTextureFx(side_t::bottom, TexMan.GetTextureManipulation(CheckString(key))); + break; + case NAME_nogradient_top: Flag(sd->textures[side_t::top].flags, side_t::part::NoGradient, key); break; @@ -1650,6 +1662,14 @@ public: sec->AdditiveColors[sector_t::sprites] = CheckInt(key) | 0xff000000; break; + case NAME_colorization_floor: + sec->SetTextureFx(sector_t::floor, TexMan.GetTextureManipulation(CheckString(key))); + break; + + case NAME_colorization_ceiling: + sec->SetTextureFx(sector_t::ceiling, TexMan.GetTextureManipulation(CheckString(key))); + break; + case NAME_Desaturation: desaturation = int(255*CheckFloat(key) + FLT_EPSILON); // FLT_EPSILON to avoid rounding errors with numbers slightly below a full integer. continue; diff --git a/src/p_saveg.cpp b/src/p_saveg.cpp index 025ca18a4..add4ce024 100644 --- a/src/p_saveg.cpp +++ b/src/p_saveg.cpp @@ -89,6 +89,31 @@ FSerializer &Serialize(FSerializer &arc, const char *key, line_t &line, line_t * } +//========================================================================== +// +// +// +//========================================================================== + +FSerializer& Serialize(FSerializer& arc, const char* key, TextureManipulation& part, TextureManipulation *def) +{ + if (arc.canSkip() && def != nullptr && !memcmp(&part, def, sizeof(part))) + { + return arc; + } + + if (arc.BeginObject(key)) + { + arc("addcolor", part.AddColor, def->AddColor) + ("yoffset", part.ModulateColor, def->ModulateColor) + ("xscale", part.BlendColor, def->BlendColor) + ("yscale", part.DesaturationFactor, def->DesaturationFactor) + .EndObject(); + } + return arc; +} + + //========================================================================== // // @@ -114,6 +139,7 @@ FSerializer &Serialize(FSerializer &arc, const char *key, side_t::part &part, si ("color1", part.SpecialColors[0], def->SpecialColors[0]) ("color2", part.SpecialColors[1], def->SpecialColors[1]) ("addcolor", part.AdditiveColor, def->AdditiveColor) + ("texturefx", part.TextureFx, def->TextureFx) .EndObject(); } return arc; @@ -212,6 +238,7 @@ FSerializer &Serialize(FSerializer &arc, const char *key, sector_t::splane &p, s ("alpha", p.alpha, def->alpha) ("glowcolor", p.GlowColor, def->GlowColor) ("glowheight", p.GlowHeight, def->GlowHeight) + ("texturefx", p.TextureFx, def->TextureFx) .EndObject(); } return arc; diff --git a/src/r_data/r_translate.h b/src/r_data/r_translate.h index 8e704a5d3..0c52f256d 100644 --- a/src/r_data/r_translate.h +++ b/src/r_data/r_translate.h @@ -147,6 +147,77 @@ int CreateBloodTranslation(PalEntry color); int R_FindCustomTranslation(FName name); void R_ParseTrnslate(); +struct TextureManipulation +{ + enum + { + BlendNone = 0, + BlendAlpha = 1, + BlendScreen = 2, + BlendOverlay = 3, + BlendHardLight = 4, + BlendMask = 7, + InvertBit = 8, + ActiveBit = 16, // Must be set for the shader to do something + }; + PalEntry AddColor; // Alpha contains the blend flags + PalEntry ModulateColor; // Alpha may contain a multiplier to get higher values than 1.0 without promoting this to 4 full floats. + PalEntry BlendColor; + float DesaturationFactor; + + bool CheckIfEnabled() // check if this manipulation is doing something. NoOps do not need to be preserved, unless they override older setttings. + { + if (AddColor != 0 || // this includes a check for the blend mode without which BlendColor is not active + ModulateColor != 0x01ffffff || // 1 in alpha must be the default for a no-op. + DesaturationFactor != 0) + { + AddColor.a |= ActiveBit; // mark as active for the shader's benefit. + return true; + } + return false; + } + + void SetTextureModulateColor(int slot, PalEntry rgb) + { + rgb.a = ModulateColor.a; + ModulateColor = rgb; + } + + void SetTextureModulateScaleFactor(int slot, int fac) + { + ModulateColor.a = (uint8_t)fac; + } + + void SetTextureAdditiveColor(int slot, PalEntry rgb) + { + rgb.a = AddColor.a; + AddColor = rgb; + } + + void SetTextureBlendColor(int slot, PalEntry rgb) + { + BlendColor = rgb; + } + + void SetTextureDesaturationFactor(int slot, double fac) + { + DesaturationFactor = (float)fac; + } + + void SetTextureBlendMode(int slot, int mode) + { + AddColor.a = (AddColor.a & ~TextureManipulation::BlendMask) | (mode & TextureManipulation::BlendMask); + } + + void SetTextureInvert(bool on) + { + AddColor.a |= TextureManipulation::InvertBit; + AddColor.a &= ~TextureManipulation::InvertBit; + } + +}; + + #endif // __R_TRANSLATE_H diff --git a/src/scripting/vmthunks.cpp b/src/scripting/vmthunks.cpp index 4f0d2fb32..ea4d9530b 100644 --- a/src/scripting/vmthunks.cpp +++ b/src/scripting/vmthunks.cpp @@ -652,6 +652,24 @@ DEFINE_ACTION_FUNCTION_NATIVE(_Sector, SetAdditiveColor, SetAdditiveColor) return 0; } +static void SetColorization(sector_t* self, int pos, int cname) +{ + if (pos >= 0 && pos < 2) + { + self->SetTextureFx(pos, TexMan.GetTextureManipulation(ENamedName(cname))); + } +} + +DEFINE_ACTION_FUNCTION_NATIVE(_Sector, SetColorization, SetColorization) +{ + PARAM_SELF_STRUCT_PROLOGUE(sector_t); + PARAM_INT(pos); + PARAM_INT(color); + SetColorization(self, pos, color); + return 0; +} + + static void SetFogDensity(sector_t *self, int dens) { self->Colormap.FogDensity = dens; @@ -1749,6 +1767,25 @@ DEFINE_ACTION_FUNCTION_NATIVE(_Sector, SetXOffset, SetXOffset) return 0; } + static void SetWallColorization(side_t* self, int pos, int cname) + { + if (pos >= 0 && pos < 2) + { + self->SetTextureFx(pos, TexMan.GetTextureManipulation(ENamedName(cname))); + } + } + + DEFINE_ACTION_FUNCTION_NATIVE(_Side, SetColorization, SetWallColorization) + { + PARAM_SELF_STRUCT_PROLOGUE(side_t); + PARAM_INT(pos); + PARAM_INT(color); + SetWallColorization(self, pos, color); + return 0; + } + + + static int SideIndex(side_t *self) { return self->Index(); diff --git a/src/utility/namedef.h b/src/utility/namedef.h index e2063f8a7..c0d5f82d3 100644 --- a/src/utility/namedef.h +++ b/src/utility/namedef.h @@ -671,6 +671,11 @@ xx(useowncoloradd_mid) xx(coloradd_mid) xx(useowncoloradd_bottom) xx(coloradd_bottom) +xx(colorization_top) +xx(colorization_mid) +xx(colorization_bottom) +xx(colorization_floor) +xx(colorization_ceiling) xx(Renderstyle) diff --git a/wadsrc/static/zscript/mapdata.zs b/wadsrc/static/zscript/mapdata.zs index 3fbb21df9..d3fd0d21b 100644 --- a/wadsrc/static/zscript/mapdata.zs +++ b/wadsrc/static/zscript/mapdata.zs @@ -87,6 +87,7 @@ struct Side native play native Color GetAdditiveColor(int tier); native void SetAdditiveColor(int tier, Color color); native void EnableAdditiveColor(int tier, bool enable); + native void SetColorization(int tier, Name cname); //native DInterpolation *SetInterpolation(int position); //native void StopInterpolation(int position); @@ -469,6 +470,7 @@ struct Sector native play native void SetGlowColor(int pos, color color); native void SetSpecialColor(int pos, color color); native void SetAdditiveColor(int pos, Color color); + native void SetColorization(int tier, Name cname); native TextureID GetTexture(int pos); native void SetTexture(int pos, TextureID tex, bool floorclip = true); From 3530bc59459062c369be6d8ead8b7be95b3ebc6d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 23 Dec 2019 16:57:30 +0100 Subject: [PATCH 03/15] - cleanup. (The Raven license got removed from sc_man after checking that no Raven code is still present here, this file got a nearly complete overhaul over all those years.) --- src/gamedata/textures/texturemanager.cpp | 4 +- src/utility/sc_man.cpp | 36 ++---- src/utility/sc_man.h | 1 + src/win32/zdoom.rc | 143 ----------------------- 4 files changed, 12 insertions(+), 172 deletions(-) diff --git a/src/gamedata/textures/texturemanager.cpp b/src/gamedata/textures/texturemanager.cpp index cc2dc548f..3f1225f40 100644 --- a/src/gamedata/textures/texturemanager.cpp +++ b/src/gamedata/textures/texturemanager.cpp @@ -700,7 +700,7 @@ void FTextureManager::ParseColorization(FScanner& sc) if (sc.Compare("desaturation")) { sc.MustGetFloat(); - tm.DesaturationFactor = sc.Float; + tm.DesaturationFactor = (float)sc.Float; } else if (sc.Compare("AddColor")) { @@ -728,7 +728,7 @@ void FTextureManager::ParseColorization(FScanner& sc) if (sc.CheckToken(',')) { sc.MustGetFloat(); - tm.BlendColor.a = clamp(sc.Float, 0., 1.) * 255; + tm.BlendColor.a = (uint8_t)clamp(sc.Float, 0., 1.) * 255; } } else if (sc.Compare("invert")) diff --git a/src/utility/sc_man.cpp b/src/utility/sc_man.cpp index 986d41d7a..3901a1f44 100644 --- a/src/utility/sc_man.cpp +++ b/src/utility/sc_man.cpp @@ -31,29 +31,6 @@ ** */ -// This file contains some code by Raven Software, licensed under: - -//----------------------------------------------------------------------------- -// -// Copyright 1994-1996 Raven Software -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// You should have received a copy of the GNU General Public License -// along with this program. If not, see http://www.gnu.org/licenses/ -// -//----------------------------------------------------------------------------- -// - - // HEADER FILES ------------------------------------------------------------ @@ -622,12 +599,14 @@ bool FScanner::GetToken () String[StringLen - 2] == 'u' || String[StringLen - 2] == 'U') { TokenType = TK_UIntConst; - Number = (int)strtoull(String, &stopper, 0); + BigNumber = (int64_t)strtoull(String, &stopper, 0); + Number = (int)clamp(BigNumber, 0, UINT_MAX); Float = (unsigned)Number; } else { - Number = (int)strtoll(String, &stopper, 0); + BigNumber = strtoll(String, &stopper, 0); + Number = (int)clamp(BigNumber, INT_MIN, INT_MAX); Float = Number; } } @@ -728,7 +707,8 @@ bool FScanner::GetNumber () } else { - Number = (int)strtoll (String, &stopper, 0); + BigNumber = strtoll(String, &stopper, 0); + Number = (int)clamp(BigNumber, INT_MIN, INT_MAX); if (*stopper != 0) { ScriptError ("SC_GetNumber: Bad numeric constant \"%s\".", String); @@ -779,11 +759,13 @@ bool FScanner::CheckNumber () } else if (strcmp (String, "MAXINT") == 0) { + BigNumber = INT64_MAX; Number = INT_MAX; } else { - Number = (int)strtoll (String, &stopper, 0); + BigNumber = strtoll (String, &stopper, 0); + Number = (int)clamp(BigNumber, INT_MIN, INT_MAX); if (*stopper != 0) { UnGet(); diff --git a/src/utility/sc_man.h b/src/utility/sc_man.h index b345ee15b..908089b8e 100644 --- a/src/utility/sc_man.h +++ b/src/utility/sc_man.h @@ -87,6 +87,7 @@ public: int StringLen; int TokenType; int Number; + int64_t BigNumber; double Float; int Line; bool End; diff --git a/src/win32/zdoom.rc b/src/win32/zdoom.rc index c455fa6cb..6ac1a2340 100644 --- a/src/win32/zdoom.rc +++ b/src/win32/zdoom.rc @@ -228,149 +228,6 @@ BEGIN CONTROL "SoftPoly",IDC_WELCOME_VULKAN3,"Button",BS_AUTORADIOBUTTON,13,188,43,10 END -IDD_EAXPROPERTYLIST DIALOGEX 0, 0, 265, 404 -STYLE DS_SETFONT | DS_3DLOOK | DS_FIXEDSYS | DS_CONTROL | WS_CHILD | WS_VSCROLL -EXSTYLE WS_EX_CLIENTEDGE -FONT 8, "MS Shell Dlg", 400, 0, 0x1 -BEGIN - EDITTEXT IDCE_ENVIRONMENTSIZE,76,7,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_ENVIRONMENTDIFFUSION,76,20,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_ROOM,76,33,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_ROOMHF,76,46,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_ROOMLF,76,59,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_DECAYTIME,76,72,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_DECAYHFRATIO,76,85,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_DECAYLFRATIO,76,98,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REFLECTIONS,76,111,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REFLECTIONSDELAY,76,124,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REVERB,76,137,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REVERBDELAY,76,150,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_ECHOTIME,76,163,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_ECHODEPTH,76,176,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_MODULATIONTIME,76,189,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_MODULATIONDEPTH,76,202,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_AIRABSORPTIONHF,76,215,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_HFREFERENCE,76,228,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_LFREFERENCE,76,241,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_ROOMROLLOFFFACTOR,76,254,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REFLECTIONSPANX,76,267,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REFLECTIONSPANY,76,280,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REFLECTIONSPANZ,76,293,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REVERBPANX,76,306,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REVERBPANY,76,319,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - EDITTEXT IDCE_REVERBPANZ,76,332,48,12,ES_AUTOHSCROLL,WS_EX_RIGHT - CONTROL "",IDCS_ENVIRONMENTSIZE,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,7,123,12 - CONTROL "",IDCS_ENVIRONMENTDIFFUSION,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,20,123,12 - CONTROL "",IDCS_ROOM,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,33,123,12 - CONTROL "",IDCS_ROOMHF,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,46,123,12 - CONTROL "",IDCS_ROOMLF,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,59,123,12 - CONTROL "",IDCS_DECAYTIME,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,72,123,12 - CONTROL "",IDCS_DECAYHFRATIO,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,85,123,12 - CONTROL "",IDCS_DECAYLFRATIO,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,98,123,12 - CONTROL "",IDCS_REFLECTIONS,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,111,123,12 - CONTROL "",IDCS_REFLECTIONSDELAY,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,124,123,12 - CONTROL "",IDCS_REVERB,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,137,123,12 - CONTROL "",IDCS_REVERBDELAY,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,150,123,12 - CONTROL "",IDCS_ECHOTIME,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,163,123,12 - CONTROL "",IDCS_ECHODEPTH,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,176,123,12 - CONTROL "",IDCS_MODULATIONTIME,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,189,123,12 - CONTROL "",IDCS_MODULATIONDEPTH,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,202,123,12 - CONTROL "",IDCS_AIRABSORPTIONHF,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,215,123,12 - CONTROL "",IDCS_HFREFERENCE,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,228,123,12 - CONTROL "",IDCS_LFREFERENCE,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,241,123,12 - CONTROL "",IDCS_ROOMROLLOFFFACTOR,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,254,123,12 - CONTROL "",IDCS_REFLECTIONSPANX,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,267,123,12 - CONTROL "",IDCS_REFLECTIONSPANY,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,280,123,12 - CONTROL "",IDCS_REFLECTIONSPANZ,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,293,123,12 - CONTROL "",IDCS_REVERBPANX,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,306,123,12 - CONTROL "",IDCS_REVERBPANY,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,319,123,12 - CONTROL "",IDCS_REVERBPANZ,"msctls_trackbar32",TBS_BOTH | TBS_NOTICKS | WS_TABSTOP,126,332,123,12 - CONTROL "Reflections Scale",IDC_REFLECTIONSSCALE,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,19,353,70,10 - CONTROL "Reflections Delay Scale",IDC_REFLECTIONSDELAYSCALE, - "Button",BS_AUTOCHECKBOX | WS_TABSTOP,19,366,90,10 - CONTROL "Decay Time Scale",IDC_DECAYTIMESCALE,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,19,377,71,10 - CONTROL "Decay HF Limit",IDC_DECAYHFLIMIT,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,19,390,63,10 - CONTROL "Reverb Scale",IDC_REVERBSCALE,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,139,353,58,10 - CONTROL "Reverb Delay Scale",IDC_REVERBDELAYSCALE,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,139,366,78,10 - CONTROL "Echo Time Scale",IDC_ECHOTIMESCALE,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,139,377,67,10 - CONTROL "Modulation Time Scale",IDC_MODULATIONTIMESCALE,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,139,390,86,10 - LTEXT "Environment Size",IDC_STATIC,17,9,56,8,0,WS_EX_RIGHT - LTEXT "Environment Diffusion",IDC_STATIC,2,22,71,8,0,WS_EX_RIGHT - LTEXT "Room",IDC_STATIC,53,35,19,8,0,WS_EX_RIGHT - LTEXT "Room HF",IDC_STATIC,43,48,30,8,0,WS_EX_RIGHT - LTEXT "Room LF",IDC_STATIC,45,60,28,8,0,WS_EX_RIGHT - LTEXT "Decay Time",IDC_STATIC,35,74,38,8,0,WS_EX_RIGHT - LTEXT "Decay HF Ratio",IDC_STATIC,23,87,50,8,0,WS_EX_RIGHT - LTEXT "Decay LF Ratio",IDC_STATIC,24,100,49,8,0,WS_EX_RIGHT - LTEXT "Reflections",IDC_STATIC,37,113,36,8,0,WS_EX_RIGHT - LTEXT "Reflections Delay",IDC_STATIC,17,126,56,8,0,WS_EX_RIGHT - LTEXT "Reflections Pan X",IDC_STATIC,17,267,56,8,0,WS_EX_RIGHT - LTEXT "Reflections Pan Y",IDC_STATIC,17,280,56,8,0,WS_EX_RIGHT - LTEXT "Reflections Pan Z",IDC_STATIC,17,293,56,8,0,WS_EX_RIGHT - LTEXT "Reverb",IDC_STATIC,49,137,24,8,0,WS_EX_RIGHT - LTEXT "Reverb Delay",IDC_STATIC,29,150,44,8,0,WS_EX_RIGHT - LTEXT "Reverb Pan X",IDC_STATIC,29,306,44,8,0,WS_EX_RIGHT - LTEXT "Reverb Pan Y",IDC_STATIC,29,319,44,8,0,WS_EX_RIGHT - LTEXT "Reverb Pan Z",IDC_STATIC,29,332,44,8,0,WS_EX_RIGHT - LTEXT "Echo Time",IDC_STATIC,40,163,33,8,0,WS_EX_RIGHT - LTEXT "Echo Depth",IDC_STATIC,35,176,38,8,0,WS_EX_RIGHT - LTEXT "Modulation Time",IDC_STATIC,21,189,52,8,0,WS_EX_RIGHT - LTEXT "Modulation Depth",IDC_STATIC,16,202,57,8,0,WS_EX_RIGHT - LTEXT "Air Absorption HF",IDC_STATIC,16,215,57,8,0,WS_EX_RIGHT - LTEXT "HF Reference",IDC_STATIC,28,228,45,8,0,WS_EX_RIGHT - LTEXT "LF Reference",IDC_STATIC,29,241,44,8,0,WS_EX_RIGHT - LTEXT "Room Rolloff Factor",IDC_STATIC,9,254,64,8,0,WS_EX_RIGHT -END - -IDD_EAXEDIT DIALOGEX 0, 0, 280, 326 -STYLE DS_SETFONT | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_VISIBLE | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | WS_CAPTION | WS_SYSMENU | WS_THICKFRAME -EXSTYLE WS_EX_TOOLWINDOW | WS_EX_WINDOWEDGE -CAPTION "Environment Editor" -FONT 8, "MS Shell Dlg", 400, 0, 0x1 -BEGIN - COMBOBOX IDC_CURRENTENVIRONMENT,7,19,265,14,CBS_DROPDOWNLIST | CBS_SORT | WS_VSCROLL | WS_TABSTOP - LTEXT "Static",IDC_DUMMY,7,36,265,263,0,WS_EX_CLIENTEDGE - PUSHBUTTON "&New...",IDC_NEW,8,305,45,14 - PUSHBUTTON "&Save...",IDC_SAVE,60,305,45,14 - PUSHBUTTON "&Revert",IDC_REVERT,112,305,45,14 - CONTROL "&Test in level",IDC_TESTEAX,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,165,307,54,10 - PUSHBUTTON "&Done",IDOK,228,305,45,14 - CONTROL "Show &IDs in List",IDC_SHOWIDS,"Button",BS_AUTOCHECKBOX | WS_TABSTOP,7,7,66,10 - LTEXT "ID 2:",IDC_STATIC,239,7,19,8 - LTEXT "ID 1:",IDC_STATIC,198,7,19,8 - LTEXT "255",IDC_ID2,258,7,15,8 - LTEXT "255",IDC_ID1,218,7,15,8 -END - -IDD_NEWEAX DIALOGEX 0, 0, 348, 257 -STYLE DS_SETFONT | DS_MODALFRAME | DS_FIXEDSYS | DS_CENTERMOUSE | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU -CAPTION "Create New Environment..." -FONT 8, "MS Shell Dlg", 400, 0, 0x1 -BEGIN - EDITTEXT IDC_NEWENVNAME,32,216,187,12,ES_AUTOHSCROLL - EDITTEXT IDC_EDITID1,248,216,32,12,ES_AUTOHSCROLL | ES_NUMBER - CONTROL "",IDC_SPINID1,"msctls_updown32",UDS_SETBUDDYINT | UDS_ALIGNRIGHT | UDS_AUTOBUDDY | UDS_ARROWKEYS,236,216,11,14 - EDITTEXT IDC_EDITID2,309,216,32,12,ES_AUTOHSCROLL | ES_NUMBER - CONTROL "",IDC_SPINID2,"msctls_updown32",UDS_SETBUDDYINT | UDS_ALIGNRIGHT | UDS_AUTOBUDDY | UDS_ARROWKEYS,297,216,11,14 - CONTROL "",IDC_ENVIRONMENTLIST,"SysListView32",LVS_LIST | LVS_SINGLESEL | LVS_SHOWSELALWAYS | LVS_SORTASCENDING | LVS_ALIGNLEFT | WS_BORDER | WS_TABSTOP,7,18,334,192 - DEFPUSHBUTTON "Create",IDOK,246,236,45,14 - PUSHBUTTON "Cancel",IDCANCEL,296,236,45,14 - LTEXT "Name:",IDC_STATIC,7,218,22,8 - LTEXT "ID 1:",IDC_STATIC,226,218,17,8 - LTEXT "ID 2:",IDC_STATIC,287,218,17,8 - LTEXT "Based on:",IDC_STATIC,7,7,33,8 -END - -IDD_SAVEEAX DIALOGEX 0, 0, 394, 95 -STYLE DS_SETFONT | DS_3DLOOK | DS_FIXEDSYS | DS_CONTROL | WS_CHILD | WS_CLIPSIBLINGS | WS_CLIPCHILDREN | WS_SYSMENU -EXSTYLE WS_EX_TRANSPARENT -FONT 8, "MS Shell Dlg", 400, 0, 0x1 -BEGIN - GROUPBOX "Include these environments:",IDC_SAVEGROUP,6,0,371,90,0,WS_EX_TRANSPARENT - CONTROL "",IDC_ENVLIST,"SysListView32",LVS_LIST | LVS_SHOWSELALWAYS | LVS_SORTASCENDING | LVS_ALIGNLEFT | WS_BORDER | WS_TABSTOP,12,12,303,72 - PUSHBUTTON "Select All",IDC_SELECTALL,320,12,50,14 - PUSHBUTTON "Select None",IDC_SELECTNONE,320,31,50,14 -END IDD_CRASHDIALOG DIALOGEX 0, 0, 415, 308 STYLE DS_SETFONT | DS_MODALFRAME | DS_SETFOREGROUND | DS_FIXEDSYS | DS_CENTER | WS_POPUP | WS_VISIBLE | WS_CAPTION | WS_SYSMENU From 77469e051266a8d351ecbb74b3bd8f80bfb69492 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 29 Dec 2019 12:11:16 +0100 Subject: [PATCH 04/15] - fixed the colorization parser. --- src/gamedata/r_defs.h | 2 +- src/gamedata/textures/texturemanager.cpp | 13 +++++++++---- src/rendering/hwrenderer/scene/hw_renderstate.h | 2 +- wadsrc/static/zscript/mapdata.zs | 4 ++-- 4 files changed, 13 insertions(+), 8 deletions(-) diff --git a/src/gamedata/r_defs.h b/src/gamedata/r_defs.h index 8c551ba0c..4987ee6fc 100644 --- a/src/gamedata/r_defs.h +++ b/src/gamedata/r_defs.h @@ -1208,7 +1208,7 @@ struct side_t uint32_t LeftSide, RightSide; // [RH] Group walls into loops uint16_t TexelLength; int16_t Light; - uint8_t Flags; + uint16_t Flags; int UDMFIndex; // needed to access custom UDMF fields which are stored in loading order. FLightNode * lighthead; // all dynamic lights that may affect this wall seg_t **segs; // all segs belonging to this sidedef in ascending order. Used for precise rendering diff --git a/src/gamedata/textures/texturemanager.cpp b/src/gamedata/textures/texturemanager.cpp index 3f1225f40..589f787b3 100644 --- a/src/gamedata/textures/texturemanager.cpp +++ b/src/gamedata/textures/texturemanager.cpp @@ -692,12 +692,14 @@ void FTextureManager::AddHiresTextures (int wadnum) void FTextureManager::ParseColorization(FScanner& sc) { TextureManipulation tm = {}; + tm.ModulateColor = 0x01ffffff; sc.MustGetString(); FName cname = sc.String; sc.MustGetToken('{'); while (!sc.CheckToken('}')) { - if (sc.Compare("desaturation")) + sc.MustGetString(); + if (sc.Compare("DesaturationFactor")) { sc.MustGetFloat(); tm.DesaturationFactor = (float)sc.Float; @@ -716,6 +718,7 @@ void FTextureManager::ParseColorization(FScanner& sc) sc.MustGetNumber(); tm.ModulateColor.a = sc.Number; } + else tm.ModulateColor.a = 1; } else if (sc.Compare("BlendColor")) { @@ -723,18 +726,20 @@ void FTextureManager::ParseColorization(FScanner& sc) tm.BlendColor = V_GetColor(NULL, sc) & 0xffffff; sc.MustGetToken(','); sc.MustGetString(); - static const char* opts[] = {"none", "alpha", "screen", "overlay", "hardlight", nullptr}; + static const char* opts[] = { "none", "alpha", "screen", "overlay", "hardlight", nullptr }; tm.AddColor.a = (tm.AddColor.a & ~TextureManipulation::BlendMask) | sc.MustMatchString(opts); - if (sc.CheckToken(',')) + if (sc.Compare("alpha")) { + sc.MustGetToken(','); sc.MustGetFloat(); - tm.BlendColor.a = (uint8_t)clamp(sc.Float, 0., 1.) * 255; + tm.BlendColor.a = (uint8_t)(clamp(sc.Float, 0., 1.) * 255); } } else if (sc.Compare("invert")) { tm.AddColor.a |= TextureManipulation::InvertBit; } + else sc.ScriptError("Unknown token '%s'", sc.String); } if (tm.CheckIfEnabled()) { diff --git a/src/rendering/hwrenderer/scene/hw_renderstate.h b/src/rendering/hwrenderer/scene/hw_renderstate.h index d725d820d..42092b2e1 100644 --- a/src/rendering/hwrenderer/scene/hw_renderstate.h +++ b/src/rendering/hwrenderer/scene/hw_renderstate.h @@ -157,7 +157,7 @@ struct FVector4PalEntry r = newvalue.r * normScale; g = newvalue.g * normScale; b = newvalue.b * normScale; - a = newvalue.a; + a = 1; return *this; } diff --git a/wadsrc/static/zscript/mapdata.zs b/wadsrc/static/zscript/mapdata.zs index d3fd0d21b..3628ca750 100644 --- a/wadsrc/static/zscript/mapdata.zs +++ b/wadsrc/static/zscript/mapdata.zs @@ -67,7 +67,7 @@ struct Side native play //DBaseDecal* AttachedDecals; // [RH] Decals bound to the wall native readonly Line linedef; native int16 Light; - native uint8 Flags; + native uint16 Flags; native TextureID GetTexture(int which); native void SetTexture(int which, TextureID tex); @@ -159,7 +159,7 @@ struct Line native play native uint activation; // activation type native int special; native int args[5]; // <--- hexen-style arguments (expanded to ZDoom's full width) - native double alpha; // <--- translucency (0=invisible, FRACUNIT=opaque) + native double alpha; // <--- translucency (0=invisible, 1.0=opaque) native readonly Side sidedef[2]; native readonly double bbox[4]; // bounding box, for the extent of the LineDef. native readonly Sector frontsector, backsector; From 703686beee1e06c09996a812c7cb0195ea5bcee3 Mon Sep 17 00:00:00 2001 From: Alexander Kromm Date: Sun, 29 Dec 2019 17:35:06 +0700 Subject: [PATCH 05/15] export TMap to ZScript --- src/CMakeLists.txt | 1 + src/scripting/thingdef_data.cpp | 16 +++++++ src/serializer.cpp | 70 +++++++++++++++++++++++++++++ src/serializer.h | 4 ++ src/utility/dictionary.cpp | 70 +++++++++++++++++++++++++++++ src/utility/dictionary.h | 6 +++ wadsrc/static/zscript.txt | 1 + wadsrc/static/zscript/dictionary.zs | 10 +++++ 8 files changed, 178 insertions(+) create mode 100644 src/utility/dictionary.cpp create mode 100644 src/utility/dictionary.h create mode 100644 wadsrc/static/zscript/dictionary.zs diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 700d1c609..839914811 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1171,6 +1171,7 @@ add_executable( zdoom WIN32 MACOSX_BUNDLE utility/x86.cpp utility/strnatcmp.c utility/zstring.cpp + utility/dictionary.cpp utility/math/asin.c utility/math/atan.c utility/math/const.c diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 43982bc25..efb630891 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -55,6 +55,7 @@ #include "wi_stuff.h" #include "a_dynlight.h" #include "types.h" +#include "utility/dictionary.h" static TArray properties; static TArray AFTable; @@ -841,6 +842,21 @@ void InitThingdef() wbplayerstruct->Size = sizeof(wbplayerstruct_t); wbplayerstruct->Align = alignof(wbplayerstruct_t); + auto dictionarystruct = NewStruct("Dictionary", nullptr, true); + dictionarystruct->Size = sizeof(Dictionary); + dictionarystruct->Align = alignof(Dictionary); + NewPointer(dictionarystruct, false)->InstallHandlers( + [](FSerializer &ar, const char *key, const void *addr) + { + ar(key, *(Dictionary **)addr); + }, + [](FSerializer &ar, const char *key, void *addr) + { + Serialize(ar, key, *(Dictionary **)addr, nullptr); + return true; + } + ); + FAutoSegIterator probe(CRegHead, CRegTail); while (*++probe != NULL) diff --git a/src/serializer.cpp b/src/serializer.cpp index 57ce752cb..c336af2f6 100644 --- a/src/serializer.cpp +++ b/src/serializer.cpp @@ -2156,6 +2156,76 @@ template<> FSerializer &Serialize(FSerializer &arc, const char *key, FFont *&fon } +//========================================================================== +// +// Dictionary +// +//========================================================================== + +FString DictionaryToString(const Dictionary &dict) +{ + Dictionary::ConstPair *pair; + Dictionary::ConstIterator i { dict }; + + rapidjson::StringBuffer buffer; + rapidjson::Writer writer(buffer); + writer.StartObject(); + + while (i.NextPair(pair)) + { + writer.Key(pair->Key); + writer.String(pair->Value); + } + + writer.EndObject(); + + FString contents { buffer.GetString(), buffer.GetSize() }; + return contents; +} + +Dictionary *DictionaryFromString(const FString &string) +{ + Dictionary *const dict = new Dictionary; + + rapidjson::Document doc; + doc.Parse(string.GetChars(), string.Len()); + + if (doc.GetType() != rapidjson::Type::kObjectType) + { + I_Error("Dictionary is expected to be an object."); + return dict; + } + + for (auto i = doc.MemberBegin(); i != doc.MemberEnd(); ++i) + { + if (i->value.GetType() != rapidjson::Type::kStringType) + { + I_Error("Dictionary value is expected to be a string."); + return dict; + } + + dict->Insert(i->name.GetString(), i->value.GetString()); + } + + return dict; +} + +template<> FSerializer &Serialize(FSerializer &arc, const char *key, Dictionary *&dict, Dictionary **) +{ + if (arc.isWriting()) + { + FString contents { DictionaryToString(*dict) }; + return arc(key, contents); + } + else + { + FString contents; + arc(key, contents); + dict = DictionaryFromString(contents); + return arc; + } +} + //========================================================================== // // Handler to retrieve a numeric value of any kind. diff --git a/src/serializer.h b/src/serializer.h index 46f6dfbb2..71f8f76e1 100644 --- a/src/serializer.h +++ b/src/serializer.h @@ -7,6 +7,7 @@ #include "r_defs.h" #include "resourcefiles/file_zip.h" #include "tflags.h" +#include "utility/dictionary.h" extern bool save_full; @@ -270,6 +271,7 @@ template<> FSerializer &Serialize(FSerializer &arc, const char *key, FDoorAnimat template<> FSerializer &Serialize(FSerializer &arc, const char *key, char *&pstr, char **def); template<> FSerializer &Serialize(FSerializer &arc, const char *key, FFont *&font, FFont **def); template<> FSerializer &Serialize(FSerializer &arc, const char *key, FLevelLocals *&font, FLevelLocals **def); +template<> FSerializer &Serialize(FSerializer &arc, const char *key, Dictionary *&dict, Dictionary **def); FSerializer &Serialize(FSerializer &arc, const char *key, FState *&state, FState **def, bool *retcode); template<> inline FSerializer &Serialize(FSerializer &arc, const char *key, FState *&state, FState **def) @@ -311,5 +313,7 @@ FSerializer &Serialize(FSerializer &arc, const char *key, TFlags &flags, return Serialize(arc, key, flags.Value, def? &def->Value : nullptr); } +FString DictionaryToString(const Dictionary &dict); +Dictionary *DictionaryFromString(const FString &string); #endif diff --git a/src/utility/dictionary.cpp b/src/utility/dictionary.cpp new file mode 100644 index 000000000..59db6ec08 --- /dev/null +++ b/src/utility/dictionary.cpp @@ -0,0 +1,70 @@ +#include "utility/dictionary.h" + +#include "scripting/vm/vm.h" +#include "serializer.h" + +//===================================================================================== +// +// Dictionary exports +// +//===================================================================================== + +DEFINE_ACTION_FUNCTION(_Dictionary, Create) +{ + PARAM_PROLOGUE; + ACTION_RETURN_POINTER(new Dictionary); +} + +static void DictInsert(Dictionary *dict, const FString &key, const FString &value) +{ + dict->Insert(key, value); +} + +DEFINE_ACTION_FUNCTION_NATIVE(_Dictionary, Insert, DictInsert) +{ + PARAM_SELF_STRUCT_PROLOGUE(Dictionary); + PARAM_STRING(key); + PARAM_STRING(value); + DictInsert(self, key, value); + return 0; +} + +static void DictAt(const Dictionary *dict, const FString &key, FString *result) +{ + const FString *value = dict->CheckKey(key); + *result = value ? *value : ""; +} + +DEFINE_ACTION_FUNCTION_NATIVE(_Dictionary, At, DictAt) +{ + PARAM_SELF_STRUCT_PROLOGUE(Dictionary); + PARAM_STRING(key); + FString result; + DictAt(self, key, &result); + ACTION_RETURN_STRING(result); +} + +static void DictToString(const Dictionary *dict, FString *result) +{ + *result = DictionaryToString(*dict); +} + +DEFINE_ACTION_FUNCTION_NATIVE(_Dictionary, ToString, DictToString) +{ + PARAM_SELF_STRUCT_PROLOGUE(Dictionary); + FString result; + DictToString(self, &result); + ACTION_RETURN_STRING(result); +} + +static Dictionary *DictFromString(const FString& string) +{ + return DictionaryFromString(string); +} + +DEFINE_ACTION_FUNCTION_NATIVE(_Dictionary, FromString, DictFromString) +{ + PARAM_PROLOGUE; + PARAM_STRING(string); + ACTION_RETURN_POINTER(DictFromString(string)); +} diff --git a/src/utility/dictionary.h b/src/utility/dictionary.h new file mode 100644 index 000000000..460716c91 --- /dev/null +++ b/src/utility/dictionary.h @@ -0,0 +1,6 @@ +#pragma once + +#include "tarray.h" +#include "zstring.h" + +using Dictionary = TMap; diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 7981d9032..921c9beb8 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -8,6 +8,7 @@ version "4.2" #include "zscript/destructible.zs" #include "zscript/level_postprocessor.zs" #include "zscript/level_compatibility.zs" +#include "zscript/dictionary.zs" #include "zscript/actors/actor.zs" #include "zscript/actors/checks.zs" diff --git a/wadsrc/static/zscript/dictionary.zs b/wadsrc/static/zscript/dictionary.zs new file mode 100644 index 000000000..10f9cb20c --- /dev/null +++ b/wadsrc/static/zscript/dictionary.zs @@ -0,0 +1,10 @@ +struct Dictionary native +{ + native static Dictionary Create(); + native static Dictionary FromString(String s); + + native void Insert(String key, String value); + native String At(String key) const; + + native String ToString() const; +} From 0b0984b88eb35ccb5f5c431109403a0ea1fd670f Mon Sep 17 00:00:00 2001 From: Major Cooke Date: Thu, 14 Nov 2019 11:48:50 -0600 Subject: [PATCH 06/15] Added STOPRAILS actor flag. - An actor with this flag will prevent railgun shots from penetrating further. --- src/playsim/actor.h | 1 + src/playsim/p_map.cpp | 3 ++- src/scripting/thingdef_data.cpp | 1 + 3 files changed, 4 insertions(+), 1 deletion(-) diff --git a/src/playsim/actor.h b/src/playsim/actor.h index 0b76592e2..32ea5dfd1 100644 --- a/src/playsim/actor.h +++ b/src/playsim/actor.h @@ -411,6 +411,7 @@ enum ActorFlag8 MF8_NOFRICTIONBOUNCE = 0x00000040, // don't bounce off walls when on icy floors MF8_RETARGETAFTERSLAM = 0x00000080, // Forces jumping to the idle state after slamming into something MF8_RECREATELIGHTS = 0x00000100, // Internal flag that signifies that the light attachments need to be recreated at the + MF8_STOPRAILS = 0x00000200, // [MC] Prevent rails from going further if an actor has this flag. }; // --- mobj.renderflags --- diff --git a/src/playsim/p_map.cpp b/src/playsim/p_map.cpp index 08525e6d6..068e1cbf5 100644 --- a/src/playsim/p_map.cpp +++ b/src/playsim/p_map.cpp @@ -5127,7 +5127,8 @@ static ETraceStatus ProcessRailHit(FTraceResults &res, void *userdata) { data->count++; } - return (data->StopAtOne || (data->limit && (data->count >= data->limit))) ? TRACE_Stop : TRACE_Continue; + return (data->StopAtOne || (data->limit && (data->count >= data->limit)) || (res.Actor->flags8 & MF8_STOPRAILS)) + ? TRACE_Stop : TRACE_Continue; } //========================================================================== diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index efb630891..c308b00e3 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -323,6 +323,7 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(MF8, NOFRICTION, AActor, flags8), DEFINE_FLAG(MF8, NOFRICTIONBOUNCE, AActor, flags8), DEFINE_FLAG(MF8, RETARGETAFTERSLAM, AActor, flags8), + DEFINE_FLAG(MF8, STOPRAILS, AActor, flags8), // Effect flags DEFINE_FLAG(FX, VISIBILITYPULSE, AActor, effects), From 5425aa979d66fc39a99b2db4974a6a019b9551df Mon Sep 17 00:00:00 2001 From: Major Cooke Date: Thu, 14 Nov 2019 11:51:36 -0600 Subject: [PATCH 07/15] - Fixed: Invulnerability checking for rails was done before the various THRU actor flags instead of after, meaning actors could block shots regardless of those flags. This was never intended. --- src/playsim/p_map.cpp | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/playsim/p_map.cpp b/src/playsim/p_map.cpp index 068e1cbf5..00d47aa37 100644 --- a/src/playsim/p_map.cpp +++ b/src/playsim/p_map.cpp @@ -5089,12 +5089,6 @@ static ETraceStatus ProcessRailHit(FTraceResults &res, void *userdata) return TRACE_Stop; } - // Invulnerable things completely block the shot - if (data->StopAtInvul && res.Actor->flags2 & MF2_INVULNERABLE) - { - return TRACE_Stop; - } - // Skip actors if the puff has: // 1. THRUACTORS (This one did NOT include a check for spectral) // 2. MTHRUSPECIES on puff and the shooter has same species as the hit actor @@ -5109,6 +5103,12 @@ static ETraceStatus ProcessRailHit(FTraceResults &res, void *userdata) return TRACE_Skip; } + // Invulnerable things completely block the shot + if (data->StopAtInvul && res.Actor->flags2 & MF2_INVULNERABLE) + { + return TRACE_Stop; + } + // Save this thing for damaging later, and continue the trace SRailHit newhit; newhit.HitActor = res.Actor; From d79c6c1c0a3dd57b5915a3fdeb7ae9aee9dad0a0 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 30 Dec 2019 09:09:08 +0100 Subject: [PATCH 08/15] - fixed: A_StartSound was still masking the sound channel value for checking if it plays something. --- src/sound/s_doomsound.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/sound/s_doomsound.cpp b/src/sound/s_doomsound.cpp index d2f551597..12ec59cf1 100644 --- a/src/sound/s_doomsound.cpp +++ b/src/sound/s_doomsound.cpp @@ -470,14 +470,14 @@ void A_StartSound(AActor *self, int soundid, int channel, int flags, double volu { if (!looping) { - if (!(flags & CHANF_NOSTOP) || !S_IsActorPlayingSomething(self, channel & 7, soundid)) + if (!(flags & CHANF_NOSTOP) || !S_IsActorPlayingSomething(self, channel, soundid)) { S_PlaySoundPitch(self, channel, EChanFlags::FromInt(flags), soundid, (float)volume, (float)attenuation, local, (float)pitch); } } else { - if (!S_IsActorPlayingSomething(self, channel & 7, soundid)) + if (!S_IsActorPlayingSomething(self, channel, soundid)) { S_PlaySoundPitch(self, channel, EChanFlags::FromInt(flags) | CHANF_LOOP, soundid, (float)volume, (float)attenuation, local, (float)pitch); } From d08bb93b84b9f52cd1801d5372b0f8ba99b45491 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 30 Dec 2019 09:47:25 +0100 Subject: [PATCH 09/15] - elimintated all cases from the ZScript code where channel indices and flags were combined into one parameter and removed all remnants of CHAN_PICKUP. --- src/sound/backend/i_soundinternal.h | 2 -- src/sound/s_soundinternal.h | 1 - wadsrc/static/zscript/actors/hexen/magelightning.zs | 2 +- wadsrc/static/zscript/actors/inventory/inventory.zs | 9 ++++++--- wadsrc/static/zscript/constants.zs | 11 ++++++++++- 5 files changed, 17 insertions(+), 8 deletions(-) diff --git a/src/sound/backend/i_soundinternal.h b/src/sound/backend/i_soundinternal.h index 08dd311a2..823f672b7 100644 --- a/src/sound/backend/i_soundinternal.h +++ b/src/sound/backend/i_soundinternal.h @@ -20,8 +20,6 @@ enum EChanFlag CHANF_AREA = 128, // Sound plays from all around. Only valid with sector sounds. CHANF_LOOP = 256, - CHANF_PICKUP = CHANF_MAYBE_LOCAL, - CHANF_NONE = 0, CHANF_IS3D = 1, // internal: Sound is 3D. CHANF_EVICTED = 2, // internal: Sound was evicted. diff --git a/src/sound/s_soundinternal.h b/src/sound/s_soundinternal.h index 2865e766b..09cffbcf9 100644 --- a/src/sound/s_soundinternal.h +++ b/src/sound/s_soundinternal.h @@ -192,7 +192,6 @@ struct FSoundChan : public FISoundChannel // CHAN_VOICE is for oof, sight, or other voice sounds // CHAN_ITEM is for small things and item pickup // CHAN_BODY is for generic body sounds -// CHAN_PICKUP can optionally be set as a local sound only for "compatibility" enum EChannel { diff --git a/wadsrc/static/zscript/actors/hexen/magelightning.zs b/wadsrc/static/zscript/actors/hexen/magelightning.zs index 5ece4fd80..f68defe9d 100644 --- a/wadsrc/static/zscript/actors/hexen/magelightning.zs +++ b/wadsrc/static/zscript/actors/hexen/magelightning.zs @@ -124,7 +124,7 @@ class Lightning : Actor if ((!thing.player && !thing.bBoss) || !(Level.maptime & 1)) { thing.DamageMobj(self, target, 3, 'Electric'); - A_PlaySound(AttackSound, CHAN_WEAPON|CHAN_NOSTOP, 1, false); + A_StartSound(AttackSound, CHAN_WEAPON, CHANF_NOSTOP, 1, false); if (thing.bIsMonster && random[LightningHit]() < 64) { thing.Howl (); diff --git a/wadsrc/static/zscript/actors/inventory/inventory.zs b/wadsrc/static/zscript/actors/inventory/inventory.zs index 98db7e9aa..ca6d48de2 100644 --- a/wadsrc/static/zscript/actors/inventory/inventory.zs +++ b/wadsrc/static/zscript/actors/inventory/inventory.zs @@ -1046,6 +1046,7 @@ class Inventory : Actor { double atten; int chan; + int flags = 0; if (bNoAttenPickupSound) { @@ -1065,13 +1066,15 @@ class Inventory : Actor if (toucher != NULL && toucher.CheckLocalView()) { - chan = CHAN_PICKUP|CHAN_NOPAUSE; + chan = CHAN_ITEM; + flags = CHANF_NOPAUSE | CHANF_MAYBE_LOCAL; } else { - chan = CHAN_PICKUP; + chan = CHAN_ITEM; + flags = CHANF_MAYBE_LOCAL; } - toucher.A_PlaySound(PickupSound, chan, 1, false, atten); + toucher.A_StartSound(PickupSound, chan, flags, 1, false, atten); } //=========================================================================== diff --git a/wadsrc/static/zscript/constants.zs b/wadsrc/static/zscript/constants.zs index 2b299e777..bd6207dc3 100644 --- a/wadsrc/static/zscript/constants.zs +++ b/wadsrc/static/zscript/constants.zs @@ -418,10 +418,19 @@ enum ESoundFlags CHAN_UI = 32, CHAN_NOPAUSE = 64, CHAN_LOOP = 256, - CHAN_PICKUP = (CHAN_ITEM|CHAN_MAYBE_LOCAL), + CHAN_PICKUP = (CHAN_ITEM|CHAN_MAYBE_LOCAL), // Do not use this with A_StartSound! It would not do what is expected. CHAN_NOSTOP = 4096, CHAN_OVERLAP = 8192, + // Same as above, with an F appended to allow better distinction of channel and channel flags. + CHANF_LISTENERZ = 8, + CHANF_MAYBE_LOCAL = 16, + CHANF_UI = 32, + CHANF_NOPAUSE = 64, + CHANF_LOOP = 256, + CHANF_NOSTOP = 4096, + CHANF_OVERLAP = 8192, + }; // sound attenuation values From 55e482d0fc35316a4284ecdbaf5f8ff6de8d48b6 Mon Sep 17 00:00:00 2001 From: Marisa Kirisame Date: Mon, 30 Dec 2019 10:51:59 +0100 Subject: [PATCH 10/15] Additional CHAN_OVERLAP awareness for StartSound and ChangeSoundVolume/Pitch. --- src/sound/s_sound.cpp | 3 --- 1 file changed, 3 deletions(-) diff --git a/src/sound/s_sound.cpp b/src/sound/s_sound.cpp index d07b744d2..5e6c16095 100644 --- a/src/sound/s_sound.cpp +++ b/src/sound/s_sound.cpp @@ -542,7 +542,6 @@ FSoundChan *SoundEngine::StartSound(int type, const void *source, if (foundit) { StopChannel(chan); - break; } } } @@ -1055,7 +1054,6 @@ void SoundEngine::ChangeSoundVolume(int sourcetype, const void *source, int chan { GSnd->ChannelVolume(chan, volume); chan->Volume = volume; - return; } } return; @@ -1086,7 +1084,6 @@ void SoundEngine::ChangeSoundPitch(int sourcetype, const void *source, int chann (sound_id == -1? (chan->EntChannel == channel) : (chan->OrgID == sound_id))) { SetPitch(chan, (float)pitch); - return; } } return; From 7fd27bc9258c4bc8331bf73322d91c4f17360c20 Mon Sep 17 00:00:00 2001 From: Cacodemon345 Date: Sun, 1 Sep 2019 14:04:53 +0600 Subject: [PATCH 11/15] Add PSPF_PLAYERTRANSLATED flag (makes a PSprite layer translated to the user's color) --- src/playsim/p_pspr.cpp | 1 + src/playsim/p_pspr.h | 1 + src/r_data/models/models.cpp | 2 +- src/rendering/hwrenderer/scene/hw_weapon.cpp | 2 +- wadsrc/static/zscript/actors/player/player.zs | 3 ++- wadsrc/static/zscript/constants.zs | 1 + 6 files changed, 7 insertions(+), 3 deletions(-) diff --git a/src/playsim/p_pspr.cpp b/src/playsim/p_pspr.cpp index 97be2772c..bcbbf2f18 100644 --- a/src/playsim/p_pspr.cpp +++ b/src/playsim/p_pspr.cpp @@ -140,6 +140,7 @@ DEFINE_FIELD_BIT(DPSprite, Flags, bPowDouble, PSPF_POWDOUBLE) DEFINE_FIELD_BIT(DPSprite, Flags, bCVarFast, PSPF_CVARFAST) DEFINE_FIELD_BIT(DPSprite, Flags, bFlip, PSPF_FLIP) DEFINE_FIELD_BIT(DPSprite, Flags, bMirror, PSPF_MIRROR) +DEFINE_FIELD_BIT(DPSprite, Flags, bPlayerTranslated, PSPF_PLAYERTRANSLATED) //------------------------------------------------------------------------ // diff --git a/src/playsim/p_pspr.h b/src/playsim/p_pspr.h index 4723fa1cb..b807e4f09 100644 --- a/src/playsim/p_pspr.h +++ b/src/playsim/p_pspr.h @@ -68,6 +68,7 @@ enum PSPFlags PSPF_FORCEALPHA = 1 << 7, PSPF_FORCESTYLE = 1 << 8, PSPF_MIRROR = 1 << 9, + PSPF_PLAYERTRANSLATED = 1 << 10 }; class DPSprite : public DObject diff --git a/src/r_data/models/models.cpp b/src/r_data/models/models.cpp index 4d4471717..51ff94b74 100644 --- a/src/r_data/models/models.cpp +++ b/src/r_data/models/models.cpp @@ -211,7 +211,7 @@ void FModelRenderer::RenderHUDModel(DPSprite *psp, float ofsX, float ofsY) float orientation = smf->xscale * smf->yscale * smf->zscale; BeginDrawHUDModel(playermo, objectToWorldMatrix, orientation < 0); - RenderFrameModels(playermo->Level, smf, psp->GetState(), psp->GetTics(), playermo->player->ReadyWeapon->GetClass(), 0); + RenderFrameModels(playermo->Level, smf, psp->GetState(), psp->GetTics(), playermo->player->ReadyWeapon->GetClass(), psp->Flags & PSPF_PLAYERTRANSLATED ? psp->Owner->mo->Translation : 0); EndDrawHUDModel(playermo); } diff --git a/src/rendering/hwrenderer/scene/hw_weapon.cpp b/src/rendering/hwrenderer/scene/hw_weapon.cpp index 85f66ab09..8eec8a13a 100644 --- a/src/rendering/hwrenderer/scene/hw_weapon.cpp +++ b/src/rendering/hwrenderer/scene/hw_weapon.cpp @@ -95,7 +95,7 @@ void HWDrawInfo::DrawPSprite(HUDSprite *huds, FRenderState &state) { float thresh = (huds->tex->tex->GetTranslucency() || huds->OverrideShader != -1) ? 0.f : gl_mask_sprite_threshold; state.AlphaFunc(Alpha_GEqual, thresh); - state.SetMaterial(huds->tex, CLAMP_XY_NOMIP, 0, huds->OverrideShader); + state.SetMaterial(huds->tex, CLAMP_XY_NOMIP, (huds->weapon->Flags & PSPF_PLAYERTRANSLATED) ? huds->owner->Translation : 0, huds->OverrideShader); state.Draw(DT_TriangleStrip, huds->mx, 4); } diff --git a/wadsrc/static/zscript/actors/player/player.zs b/wadsrc/static/zscript/actors/player/player.zs index 0036f922a..58cba9f0f 100644 --- a/wadsrc/static/zscript/actors/player/player.zs +++ b/wadsrc/static/zscript/actors/player/player.zs @@ -2543,7 +2543,8 @@ class PSprite : Object native play native bool bCVarFast; native bool bFlip; native bool bMirror; - + native bool bPlayerTranslated; + native void SetState(State newstate, bool pending = false); //------------------------------------------------------------------------ diff --git a/wadsrc/static/zscript/constants.zs b/wadsrc/static/zscript/constants.zs index bd6207dc3..8c91efb09 100644 --- a/wadsrc/static/zscript/constants.zs +++ b/wadsrc/static/zscript/constants.zs @@ -748,6 +748,7 @@ enum EPSpriteFlags PSPF_FORCEALPHA = 1 << 7, PSPF_FORCESTYLE = 1 << 8, PSPF_MIRROR = 1 << 9, + PSPF_PLAYERTRANSLATED = 1 << 10 }; // Default psprite layers From 2dc98370784c2337924730d5a34486b0272feb48 Mon Sep 17 00:00:00 2001 From: Alexander Kromm Date: Mon, 30 Dec 2019 20:26:40 +0700 Subject: [PATCH 12/15] fix crash with saving null Dictionary --- src/serializer.cpp | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/serializer.cpp b/src/serializer.cpp index c336af2f6..490a3bef9 100644 --- a/src/serializer.cpp +++ b/src/serializer.cpp @@ -2185,6 +2185,11 @@ FString DictionaryToString(const Dictionary &dict) Dictionary *DictionaryFromString(const FString &string) { + if (string.IsEmpty()) + { + return nullptr; + } + Dictionary *const dict = new Dictionary; rapidjson::Document doc; @@ -2214,7 +2219,7 @@ template<> FSerializer &Serialize(FSerializer &arc, const char *key, Dictionary { if (arc.isWriting()) { - FString contents { DictionaryToString(*dict) }; + FString contents { dict ? DictionaryToString(*dict) : "" }; return arc(key, contents); } else From bd1892120d42f6e927209a7156a202fa9755c930 Mon Sep 17 00:00:00 2001 From: Alexander Kromm Date: Mon, 30 Dec 2019 20:33:15 +0700 Subject: [PATCH 13/15] add Dictionary.Remove(String key) function --- src/utility/dictionary.cpp | 13 +++++++++++++ wadsrc/static/zscript/dictionary.zs | 1 + 2 files changed, 14 insertions(+) diff --git a/src/utility/dictionary.cpp b/src/utility/dictionary.cpp index 59db6ec08..e951439ec 100644 --- a/src/utility/dictionary.cpp +++ b/src/utility/dictionary.cpp @@ -68,3 +68,16 @@ DEFINE_ACTION_FUNCTION_NATIVE(_Dictionary, FromString, DictFromString) PARAM_STRING(string); ACTION_RETURN_POINTER(DictFromString(string)); } + +static void DictRemove(Dictionary *dict, const FString &key) +{ + dict->Remove(key); +} + +DEFINE_ACTION_FUNCTION_NATIVE(_Dictionary, Remove, DictRemove) +{ + PARAM_SELF_STRUCT_PROLOGUE(Dictionary); + PARAM_STRING(key); + DictRemove(self, key); + return 0; +} diff --git a/wadsrc/static/zscript/dictionary.zs b/wadsrc/static/zscript/dictionary.zs index 10f9cb20c..f802a2fae 100644 --- a/wadsrc/static/zscript/dictionary.zs +++ b/wadsrc/static/zscript/dictionary.zs @@ -4,6 +4,7 @@ struct Dictionary native native static Dictionary FromString(String s); native void Insert(String key, String value); + native void Remove(String key); native String At(String key) const; native String ToString() const; From b4ba7dfec2d7c0aa104b38daaff4cc5984270483 Mon Sep 17 00:00:00 2001 From: Chronos Ouroboros Date: Mon, 30 Dec 2019 12:33:30 -0300 Subject: [PATCH 14/15] Fixed a regression in DoTakeInventory. (the C++ code just ignored the null pointer, but ZScript can't do that) --- wadsrc/static/zscript/actors/inventory_util.zs | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/wadsrc/static/zscript/actors/inventory_util.zs b/wadsrc/static/zscript/actors/inventory_util.zs index d64625109..6b65b6420 100644 --- a/wadsrc/static/zscript/actors/inventory_util.zs +++ b/wadsrc/static/zscript/actors/inventory_util.zs @@ -504,6 +504,10 @@ extend class Actor { return false; } + if (receiver == NULL) + { + return false; + } if (!orresult) { receiver = receiver.GetPointer(setreceiver); From 2b05bfed689209aa988faa520446a9ed3cee89d6 Mon Sep 17 00:00:00 2001 From: Rachael Alexanderson Date: Wed, 27 Nov 2019 18:27:59 -0500 Subject: [PATCH 15/15] - implement 'defcvars' # Conflicts: # src/d_main.cpp --- src/console/c_cvars.cpp | 54 +++++++++++++++++++++++++++++++++++++++++ src/d_main.cpp | 3 +++ 2 files changed, 57 insertions(+) diff --git a/src/console/c_cvars.cpp b/src/console/c_cvars.cpp index 103c8cf95..0b4bdd2ed 100644 --- a/src/console/c_cvars.cpp +++ b/src/console/c_cvars.cpp @@ -48,6 +48,8 @@ #include "menu/menu.h" #include "vm.h" +#include "version.h" + struct FLatchedValue { FBaseCVar *Variable; @@ -1745,3 +1747,55 @@ CCMD (archivecvar) } } } + +void C_GrabCVarDefaults () +{ + int lump, lastlump = 0; + int lumpversion, gamelastrunversion; + gamelastrunversion = atoi(LASTRUNVERSION); + + while ((lump = Wads.FindLump("DEFCVARS", &lastlump)) != -1) + { + FScanner sc(lump); + + sc.MustGetString(); + if (!sc.Compare("version")) + sc.ScriptError("Must declare version for defcvars!"); + sc.MustGetNumber(); + lumpversion = sc.Number; + if (lumpversion > gamelastrunversion) + sc.ScriptError("Unsupported version %i (%i supported)", lumpversion, gamelastrunversion); + if (lumpversion < 218) + sc.ScriptError("Version must be at least 218 (current version %i)", gamelastrunversion); + + FBaseCVar *var; + + while (sc.GetString()) + { + if (sc.Compare("set")) + { + sc.MustGetString(); + } + var = FindCVar (sc.String, NULL); + if (var != NULL) + { + if (var->GetFlags() & CVAR_ARCHIVE) + { + UCVarValue val; + + sc.MustGetString(); + val.String = const_cast(sc.String); + var->SetGenericRepDefault(val, CVAR_String); + } + else + { + sc.ScriptError("Cannot set cvar default for non-config cvar '%s'", sc.String); + } + } + else + { + sc.ScriptError("Unknown cvar '%s'", sc.String); + } + } + } +} diff --git a/src/d_main.cpp b/src/d_main.cpp index bc4b66dde..12ea85c47 100644 --- a/src/d_main.cpp +++ b/src/d_main.cpp @@ -145,6 +145,7 @@ void DrawFullscreenSubtitle(const char *text); void D_Cleanup(); void FreeSBarInfoScript(); void I_UpdateWindowTitle(); +void C_GrabCVarDefaults (); // PRIVATE FUNCTION PROTOTYPES --------------------------------------------- @@ -2531,6 +2532,8 @@ static int D_DoomMain_Internal (void) allwads.ShrinkToFit(); SetMapxxFlag(); + C_GrabCVarDefaults(); //parse DEFCVARS + GameConfig->DoKeySetup(gameinfo.ConfigName); // Now that wads are loaded, define mod-specific cvars.