diff --git a/CMakeLists.txt b/CMakeLists.txt index 25a44f016..5d2d4a7e6 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,5 +1,17 @@ cmake_minimum_required(VERSION 3.0) +# Enable CCache early +set(SRB2_USE_CCACHE OFF CACHE BOOL "Use CCache") +if (${SRB2_USE_CCACHE}) + find_program(CCACHE_PROGRAM ccache) + if(CCACHE_PROGRAM) + message(STATUS "Found CCache: ${CCACHE_PROGRAM}") + set_property(GLOBAL PROPERTY RULE_LAUNCH_COMPILE "${CCACHE_PROGRAM}") + else() + message(WARNING "You have specified to use CCACHE but it was not found. Object files will not be cached.") + endif() +endif() + file(STRINGS src/version.h SRB2_VERSION) string(REGEX MATCH "[0-9]+\\.[0-9.]+" SRB2_VERSION ${SRB2_VERSION}) @@ -13,6 +25,10 @@ if(${PROJECT_SOURCE_DIR} MATCHES ${PROJECT_BINARY_DIR}) message(FATAL_ERROR "In-source builds will bring you a world of pain. Please make a separate directory to invoke CMake from.") endif() +if ((${SRB2_USE_CCACHE}) AND (${CMAKE_C_COMPILER} MATCHES "clang")) + message(WARNING "Using clang and CCache: You may want to set environment variable CCACHE_CPP2=yes to prevent include errors during compile.") +endif() + # Set up CMAKE path set(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH} "${CMAKE_SOURCE_DIR}/cmake/Modules/") @@ -117,16 +133,19 @@ configure_file(${CMAKE_CURRENT_SOURCE_DIR}/src/config.h.in ${CMAKE_CURRENT_BINAR ##### PACKAGE CONFIGURATION ##### -if(${CMAKE_SYSTEM} MATCHES "Windows") - set(CPACK_GENERATOR "ZIP") -endif() -if(${CMAKE_SYSTEM} MATCHES "Linux") - set(CPACK_GENERATOR "TGZ") -endif() -if(${CMAKE_SYSTEM} MATCHES "Darwin") - set(CPACK_GENERATOR "DragNDrop") +set(SRB2_CPACK_GENERATOR "" CACHE STRING "Generator to use for making a package. E.g., ZIP, TGZ, DragNDrop (OSX only). Leave blank for default generator.") + +if("${SRB2_CPACK_GENERATOR}" STREQUAL "") + if(${CMAKE_SYSTEM} MATCHES "Windows") + set(SRB2_CPACK_GENERATOR "ZIP") + elseif(${CMAKE_SYSTEM} MATCHES "Linux") + set(SRB2_CPACK_GENERATOR "TGZ") + elseif(${CMAKE_SYSTEM} MATCHES "Darwin") + set(SRB2_CPACK_GENERATOR "TGZ") + endif() endif() +set(CPACK_GENERATOR ${SRB2_CPACK_GENERATOR}) set(CPACK_PACKAGE_DESCRIPTION_SUMMARY "Sonic Robo Blast 2" CACHE STRING "Program name for display purposes") set(CPACK_PACKAGE_VENDOR "Sonic Team Jr." CACHE STRING "Vendor name for display purposes") #set(CPACK_PACKAGE_DESCRIPTION_FILE ) @@ -135,4 +154,5 @@ set(CPACK_PACKAGE_VERSION_MAJOR ${SRB2_VERSION_MAJOR}) set(CPACK_PACKAGE_VERSION_MINOR ${SRB2_VERSION_MINOR}) set(CPACK_PACKAGE_VERSION_PATCH ${SRB2_VERSION_PATCH}) set(CPACK_PACKAGE_INSTALL_DIRECTORY "CMake ${CMAKE_VERSION_MAJOR}.${CMAKE_VERSION_MINOR}") +SET(CPACK_OUTPUT_FILE_PREFIX package) include(CPack) diff --git a/assets/CMakeLists.txt b/assets/CMakeLists.txt index 095349418..3ea7c28df 100644 --- a/assets/CMakeLists.txt +++ b/assets/CMakeLists.txt @@ -12,6 +12,9 @@ ENDFUNCTION(PREPEND) set(SRB2_ASSET_DIRECTORY "${CMAKE_CURRENT_SOURCE_DIR}/installer" CACHE STRING "Path to directory that contains all asset files for the installer.") +set(SRB2_ASSET_INSTALL ON + CACHE BOOL "Insert asset files into the install directory or package.") + #################### # POST-V2.2 NOTE: Do not forget to add patch.pk3 to the end of this list! #################### @@ -43,20 +46,27 @@ endforeach() if(${CMAKE_SYSTEM} MATCHES Darwin) get_target_property(outname SRB2SDL2 OUTPUT_NAME) - install(DIRECTORY "${SRB2_ASSET_DIRECTORY}/" - DESTINATION "${outname}.app/Contents/Resources" - ) + if(${SRB2_ASSET_INSTALL}) + install(DIRECTORY "${SRB2_ASSET_DIRECTORY}/" + DESTINATION "${outname}.app/Contents/Resources" + ) + endif() + # Always install the doc files, even in non-asset packages. install(FILES ${SRB2_ASSET_DOCS} DESTINATION . OPTIONAL ) else() - install(DIRECTORY "${SRB2_ASSET_DIRECTORY}/" - DESTINATION . - ) - # Docs are assumed to be located in SRB2_ASSET_DIRECTORY, so don't install again - #install(FILES ${SRB2_ASSET_DOCS} - # DESTINATION . - # OPTIONAL - #) + if(${SRB2_ASSET_INSTALL}) + install(DIRECTORY "${SRB2_ASSET_DIRECTORY}/" + DESTINATION . + ) + # Docs are assumed to be located in SRB2_ASSET_DIRECTORY, so don't install them in their own call. + else() + # Always install the doc files, even in non-asset packages. + install(FILES ${SRB2_ASSET_DOCS} + DESTINATION . + OPTIONAL + ) + endif() endif() diff --git a/cmake/launch-c.in b/cmake/launch-c.in new file mode 100644 index 000000000..c60558232 --- /dev/null +++ b/cmake/launch-c.in @@ -0,0 +1,3 @@ +#!/bin/sh +export CCACHE_CPP2=true +exec "${RULE_LAUNCH_COMPILE}" "${CMAKE_C_COMPILER}" "$@" diff --git a/cmake/launch-cxx.in b/cmake/launch-cxx.in new file mode 100644 index 000000000..c60558232 --- /dev/null +++ b/cmake/launch-cxx.in @@ -0,0 +1,3 @@ +#!/bin/sh +export CCACHE_CPP2=true +exec "${RULE_LAUNCH_COMPILE}" "${CMAKE_C_COMPILER}" "$@" diff --git a/extras/conf/udb/Includes/Game_SRB222.cfg b/extras/conf/udb/Includes/Game_SRB222.cfg new file mode 100644 index 000000000..2ad0dc61d --- /dev/null +++ b/extras/conf/udb/Includes/Game_SRB222.cfg @@ -0,0 +1,77 @@ +// Default lump name for new map +defaultlumpname = "MAP01"; +//GZDB specific. Don't try to load lumps that don't exist. +basegame = "Doom"; + +//Sky textures for vanilla maps +defaultskytextures +{ + SKY1 = "MAP01,MAP02,MAP03,MAP33,MAP50,MAP60,MAPF0,MAPM0"; + SKY2 = "MAPM7,MAPMB"; + SKY4 = "MAP04,MAP06,MAP61,MAPF6,MAPM1"; + SKY6 = "MAP05,MAP51,MAPMA"; + SKY7 = "MAPM2,MAPM5"; + SKY8 = "MAP07,MAP08,MAP09,MAP52,MAP62,MAPF1"; + SKY10 = "MAP10,MAP12,MAP53,MAP63,MAPM3"; + SKY11 = "MAP11,MAPF7"; + SKY13 = "MAP13,MAP64"; + SKY14 = "MAP14"; + SKY15 = "MAP15,MAP54"; + SKY17 = "MAP70"; + SKY20 = "MAP32,MAP55,MAP65,MAPF2,MAPF5"; + SKY21 = "MAPM4"; + SKY22 = "MAP22,MAP23,MAP25,MAP26,MAP27,MAP56,MAP66,MAPF4,MAPM6"; + SKY30 = "MAP30"; + SKY31 = "MAP31"; + SKY35 = "MAP42"; + SKY40 = "MAP41,MAP71,MAPM9"; + SKY55 = "MAPF3,MAPM8"; + SKY68 = "MAPF8"; + SKY99 = "MAP57,MAPZ0"; + SKY159 = "MAP16"; + SKY172 = "MAP40"; + SKY300 = "MAP72"; + SKY301 = "MAP73"; +} + +// Skill levels +skills +{ + 1 = "Normal"; +} + +// Skins +skins +{ + Sonic; + Tails; + Knuckles; + Amy; + Fang; + Metalsonic; +} + +// Gametypes +gametypes +{ + -1 = "Single Player"; + 0 = "Co-op"; + 1 = "Competition"; + 2 = "Race"; + 3 = "Match"; + 4 = "Team Match"; + 5 = "Tag"; + 6 = "Hide and Seek"; + 7 = "CTF"; +} + +// Texture loading options +defaultwalltexture = "GFZROCK"; +defaultfloortexture = "GFZFLR01"; +defaultceilingtexture = "F_SKY1"; + +// Default texture sets +// (these are not required, but useful for new users) +texturesets +{ +} \ No newline at end of file diff --git a/extras/conf/udb/Includes/SRB222_common.cfg b/extras/conf/udb/Includes/SRB222_common.cfg new file mode 100644 index 000000000..d67835aeb --- /dev/null +++ b/extras/conf/udb/Includes/SRB222_common.cfg @@ -0,0 +1,297 @@ +common +{ + // Simulate Doom brightness levels (turn this off for linear lighting) + doomlightlevels = true; + + // Enables support for long (> 8 chars) texture names + // WARNING: this should only be enabled for UDMF game configurations! + // WARNING: enabling this will make maps incompatible with Doom Builder 2 and can lead to problems in Slade 3! + longtexturenames = false; + + // These directory names are ignored when loading PK3/PK7/Directory resources + ignoreddirectories = ".svn .git"; + + // Files with these extensions are ignored when loading PK3/PK7/Directory resources + ignoredextensions = "wad pk3 pk7 bak backup1 backup2 backup3 zip rar 7z"; + + // Default testing parameters + testparameters = "-file \"%AP\" \"%F\" -warp %L"; + testshortpaths = true; + + // Action special help + actionspecialhelp = "https://wiki.srb2.org/wiki/Linedef_type_%K"; + + // Generalized actions + generalizedlinedefs = false; + generalizedsectors = true; + + // Maximum safe map size check (0 means skip check) + safeboundary = 1; + + // Map boundaries. Map objects can only be placed within these boundaries + leftboundary = -32768; + rightboundary = 32767; + topboundary = 32767; + bottomboundary = -32768; + + // Texture loading options + mixtexturesflats = true; + defaulttexturescale = 1.0f; + defaultflatscale = 1.0f; + scaledtextureoffsets = true; + + // Thing number for start position in 3D Mode + start3dmode = 3328; + + // Texture sources + textures + { + include("SRB222_misc.cfg", "textures"); + } + + // Patch sources + patches + { + include("SRB222_misc.cfg", "patches"); + } + + // Sprite sources + sprites + { + include("SRB222_misc.cfg", "sprites"); + } + + // Flat sources + flats + { + include("SRB222_misc.cfg", "flats"); + } +} + +mapformat_doom +{ + // The format interface handles the map data format + formatinterface = "DoomMapSetIO"; + + // Default nodebuilder configurations + defaultsavecompiler = "zennode_normal"; + defaulttestcompiler = "zennode_fast"; + + /* + GAME DETECT PATTERN + Used to guess the game for which a WAD file is made. + + 1 = One of these lumps must exist + 2 = None of these lumps must exist + 3 = All of these lumps must exist + */ + + gamedetect + { + EXTENDED = 2; + + + BEHAVIOR = 2; + + E#M# = 2; + + MAP?? = 1; + } + + /* + MAP LUMP NAMES + Map lumps are loaded with the map as long as they are right after each other. When the editor + meets a lump which is not defined in this list it will ignore the map if not satisfied. + The order of items defines the order in which lumps will be written to WAD file on save. + To indicate the map header lump, use ~MAP + + Legenda: + required = Lump is required to exist. + blindcopy = Lump will be copied along with the map blindly. (usefull for lumps Doom Builder doesn't use) + nodebuild = The nodebuilder generates this lump. + allowempty = The nodebuilder is allowed to leave this lump empty. + script = This lump is a text-based script. Specify the filename of the script configuration to use. + */ + + maplumpnames + { + include("SRB222_misc.cfg", "doommaplumpnames"); + } + + // When this is set to true, sectors with the same tag will light up when a line is highlighted + linetagindicatesectors = true; + + // Special linedefs + include("SRB222_misc.cfg", "speciallinedefs"); + + // Default flags for first new thing + defaultthingflags + { + } + + // DEFAULT SECTOR BRIGHTNESS LEVELS + sectorbrightness + { + include("SRB222_misc.cfg", "sectorbrightness"); + } + + // SECTOR TYPES + sectortypes + { + include("SRB222_sectors.cfg", "sectortypes"); + } + + // GENERALISED SECTOR TYPES + gen_sectortypes + { + include("SRB222_sectors.cfg", "gen_sectortypes"); + } + + // LINEDEF FLAGS + linedefflags + { + include("SRB222_misc.cfg", "linedefflags"); + } + + // Linedef flags UDMF translation table + // This is needed for copy/paste and prefabs to work properly + // When the UDMF field name is prefixed with ! it is inverted + linedefflagstranslation + { + include("SRB222_misc.cfg", "linedefflagstranslation"); + } + + // LINEDEF ACTIVATIONS + linedefactivations + { + } + + // LINEDEF TYPES + linedeftypes + { + include("SRB222_linedefs.cfg", "doom"); + } + + // THING FLAGS + thingflags + { + include("SRB222_misc.cfg", "thingflags"); + } + + // Thing flags UDMF translation table + // This is needed for copy/paste and prefabs to work properly + // When the UDMF field name is prefixed with ! it is inverted + thingflagstranslation + { + include("SRB222_misc.cfg", "thingflagstranslation"); + } + + // THING FLAGS ERROR MASK + // Mask for the thing flags which indicates the options + // that make the same thing appear in the same modes + thingflagsmask1 = 7; // 1 + 2 + 4 + thingflagsmask2 = 0; +} + +mapformat_udmf +{ + // The format interface handles the map data format + formatinterface = "UniversalMapSetIO"; + + // Default nodebuilder configurations + defaultsavecompiler = "zdbsp_udmf_normal"; + defaulttestcompiler = "zdbsp_udmf_fast"; + + // Determines the textmap namespace + engine = "srb2"; + + maplumpnames + { + include("UDMF_misc.cfg", "udmfmaplumpnames_begin"); + include("SRB222_misc.cfg", "udmfmaplumpnames"); + include("UDMF_misc.cfg", "udmfmaplumpnames_end"); + } + + universalfields + { + include("SRB222_misc.cfg", "universalfields"); + } + + // When this is set to true, sectors with the same tag will light up when a line is highlighted + linetagindicatesectors = false; + + // Special linedefs + include("SRB222_misc.cfg", "speciallinedefs_udmf"); + + // Default flags for first new thing + defaultthingflags + { + } + + // SECTOR FLAGS + sectorflags + { + include("SRB222_misc.cfg", "sectorflags"); + } + + // DEFAULT SECTOR BRIGHTNESS LEVELS + sectorbrightness + { + include("SRB222_misc.cfg", "sectorbrightness"); + } + + // SECTOR TYPES + sectortypes + { + include("SRB222_sectors.cfg", "sectortypes"); + } + + // GENERALISED SECTOR TYPES + gen_sectortypes + { + include("SRB222_sectors.cfg", "gen_sectortypes"); + } + + // LINEDEF FLAGS + linedefflags + { + include("SRB222_misc.cfg", "linedefflags_udmf"); + } + + linedefflagstranslation + { + include("SRB222_misc.cfg", "linedefflagstranslation"); + } + + // LINEDEF RENDERSTYLES + /*linedefrenderstyles + { + include("SRB222_misc.cfg", "linedefrenderstyles"); + }*/ + + // THING FLAGS + thingflags + { + include("SRB222_misc.cfg", "thingflags_udmf"); + } + + // Thing flags UDMF translation table + // This is needed for copy/paste and prefabs to work properly + // When the UDMF field name is prefixed with ! it is inverted + thingflagstranslation + { + include("SRB222_misc.cfg", "thingflagstranslation"); + } + + // How to compare thing flags (for the stuck things error checker) + thingflagscompare + { + include("UDMF_misc.cfg", "thingflagscompare"); + } + + // LINEDEF TYPES + linedeftypes + { + include("SRB222_linedefs.cfg", "udmf"); + } +} \ No newline at end of file diff --git a/extras/conf/udb/Includes/SRB222_linedefs.cfg b/extras/conf/udb/Includes/SRB222_linedefs.cfg new file mode 100644 index 000000000..1f87c2c3a --- /dev/null +++ b/extras/conf/udb/Includes/SRB222_linedefs.cfg @@ -0,0 +1,1901 @@ +doom +{ + misc + { + title = "Miscellaneous"; + + 0 + { + title = "None"; + prefix = "(0)"; + } + 1 + { + title = "Per-Sector Gravity"; + prefix = "(1)"; + } + 5 + { + title = "Camera Scanner"; + prefix = "(5)"; + } + 7 + { + title = "Sector Flat Alignment"; + prefix = "(7)"; + } + 10 + { + title = "Culling Plane"; + prefix = "(10)"; + } + 13 + { + title = "Heat Wave Effect"; + prefix = "(13)"; + } + 40 + { + title = "Visual Portal Between Tagged Linedefs"; + prefix = "(40)"; + } + 41 + { + title = "Horizon Effect"; + prefix = "(41)"; + } + 50 + { + title = "Instantly Lower Floor on Level Load"; + prefix = "(50)"; + } + 51 + { + title = "Instantly Raise Ceiling on Level Load"; + prefix = "(51)"; + } + 63 + { + title = "Fake Floor/Ceiling Planes"; + prefix = "(63)"; + } + 540 + { + title = "Floor Friction"; + prefix = "(540)"; + } + } + + parameters + { + title = "Parameters"; + + 2 + { + title = "Custom Exit"; + prefix = "(2)"; + } + 3 + { + title = "Zoom Tube Parameters"; + prefix = "(3)"; + } + 4 + { + title = "Speed Pad Parameters"; + prefix = "(4)"; + } + 8 + { + title = "Special Sector Properties"; + prefix = "(8)"; + } + 9 + { + title = "Chain Parameters"; + prefix = "(9)"; + } + 11 + { + title = "Rope Hang Parameters"; + prefix = "(11)"; + } + 12 + { + title = "Rock Spawner Parameters"; + prefix = "(12)"; + } + 14 + { + title = "Bustable Block Parameters"; + prefix = "(14)"; + } + 15 + { + title = "Fan Particle Spawner Parameters"; + prefix = "(15)"; + } + 16 + { + title = "Minecart Parameters"; + prefix = "(16)"; + } + 64 + { + title = "Continuously Appearing/Disappearing FOF"; + prefix = "(64)"; + } + 65 + { + title = "Bridge Thinker "; + prefix = "(65)"; + } + } + + polyobject + { + title = "PolyObject"; + + 20 + { + title = "First Line"; + prefix = "(20)"; + } + 21 + { + title = "Explicitly Include Line "; + prefix = "(21)"; + } + 22 + { + title = "Parameters"; + prefix = "(22)"; + } + 30 + { + title = "Waving Flag"; + prefix = "(30)"; + } + 31 + { + title = "Displacement by Front Sector"; + prefix = "(31)"; + } + 32 + { + title = "Angular Displacement by Front Sector"; + prefix = "(32)"; + } + } + + planemove + { + title = "Plane Movement"; + + 52 + { + title = "Continuously Falling Sector"; + prefix = "(52)"; + } + 53 + { + title = "Continuous Floor/Ceiling Mover"; + prefix = "(53)"; + } + 54 + { + title = "Continuous Floor Mover"; + prefix = "(54)"; + } + 55 + { + title = "Continuous Ceiling Mover"; + prefix = "(55)"; + } + 56 + { + title = "Continuous Two-Speed Floor/Ceiling Mover"; + prefix = "(56)"; + } + 57 + { + title = "Continuous Two-Speed Floor Mover"; + prefix = "(57)"; + } + 58 + { + title = "Continuous Two-Speed Ceiling Mover"; + prefix = "(58)"; + } + 59 + { + title = "Activate Moving Platform"; + prefix = "(59)"; + } + 60 + { + title = "Activate Moving Platform (Adjustable Speed)"; + prefix = "(60)"; + } + 61 + { + title = "Crusher (Ceiling to Floor)"; + prefix = "(61)"; + } + 62 + { + title = "Crusher (Floor to Ceiling)"; + prefix = "(62)"; + } + 66 + { + title = "Move Floor by Displacement"; + prefix = "(66)"; + } + 67 + { + title = "Move Ceiling by Displacement"; + prefix = "(67)"; + } + 68 + { + title = "Move Floor and Ceiling by Displacement"; + prefix = "(68)"; + } + } + + fofsolid + { + title = "FOF (solid)"; + + 100 + { + title = "Solid, Opaque"; + prefix = "(100)"; + } + 101 + { + title = "Solid, Opaque, No Shadow"; + prefix = "(101)"; + } + 102 + { + title = "Solid, Translucent"; + prefix = "(102)"; + } + 103 + { + title = "Solid, Sides Only"; + prefix = "(103)"; + } + 104 + { + title = "Solid, No Sides"; + prefix = "(104)"; + } + 105 + { + title = "Solid, Invisible"; + prefix = "(105)"; + } + 140 + { + title = "Intangible from Bottom, Opaque"; + prefix = "(140)"; + } + 141 + { + title = "Intangible from Bottom, Translucent"; + prefix = "(141)"; + } + 142 + { + title = "Intangible from Bottom, Translucent, No Sides"; + prefix = "(142)"; + } + 143 + { + title = "Intangible from Top, Opaque"; + prefix = "(143)"; + } + 144 + { + title = "Intangible from Top, Translucent"; + prefix = "(144)"; + } + 145 + { + title = "Intangible from Top, Translucent, No Sides"; + prefix = "(145)"; + } + 146 + { + title = "Only Tangible from Sides"; + prefix = "(146)"; + } + } + + fofintangible + { + title = "FOF (intangible)"; + + 120 + { + title = "Water, Opaque"; + prefix = "(120)"; + } + 121 + { + title = "Water, Translucent"; + prefix = "(121)"; + } + 122 + { + title = "Water, Opaque, No Sides"; + prefix = "(122)"; + } + 123 + { + title = "Water, Translucent, No Sides"; + prefix = "(123)"; + } + 124 + { + title = "Goo Water, Translucent"; + prefix = "(124)"; + } + 125 + { + title = "Goo Water, Translucent, No Sides"; + prefix = "(125)"; + } + 220 + { + title = "Intangible, Opaque"; + prefix = "(220)"; + } + 221 + { + title = "Intangible, Translucent"; + prefix = "(221)"; + } + 222 + { + title = "Intangible, Sides Only"; + prefix = "(222)"; + } + 223 + { + title = "Intangible, Invisible"; + prefix = "(223)"; + } + } + + fofmoving + { + title = "FOF (moving)"; + + 150 + { + title = "Air Bobbing"; + prefix = "(150)"; + } + 151 + { + title = "Air Bobbing (Adjustable)"; + prefix = "(151)"; + } + 152 + { + title = "Reverse Air Bobbing (Adjustable)"; + prefix = "(152)"; + } + 153 + { + title = "Dynamically Sinking Platform"; + prefix = "(153)"; + } + 160 + { + title = "Floating, Bobbing"; + prefix = "(160)"; + } + 190 + { + title = "Rising Platform, Solid, Opaque"; + prefix = "(190)"; + } + 191 + { + title = "Rising Platform, Solid, Opaque, No Shadow"; + prefix = "(191)"; + } + 192 + { + title = "Rising Platform, Solid, Translucent"; + prefix = "(192)"; + } + 193 + { + title = "Rising Platform, Solid, Invisible"; + prefix = "(193)"; + } + 194 + { + title = "Rising Platform, Intangible from Bottom, Opaque"; + prefix = "(194)"; + } + 195 + { + title = "Rising Platform, Intangible from Bottom, Translucent"; + prefix = "(195)"; + } + } + + fofcrumbling + { + title = "FOF (crumbling)"; + + 170 + { + title = "Crumbling, Respawn"; + prefix = "(170)"; + } + 171 + { + title = "Crumbling, No Respawn"; + prefix = "(171)"; + } + 172 + { + title = "Crumbling, Respawn, Intangible from Bottom"; + prefix = "(172)"; + } + 173 + { + title = "Crumbling, No Respawn, Intangible from Bottom"; + prefix = "(173)"; + } + 174 + { + title = "Crumbling, Respawn, Int. from Bottom, Translucent"; + prefix = "(174)"; + } + 175 + { + title = "Crumbling, No Respawn, Int. from Bottom, Translucent"; + prefix = "(175)"; + } + 176 + { + title = "Crumbling, Respawn, Floating, Bobbing"; + prefix = "(176)"; + } + 177 + { + title = "Crumbling, No Respawn, Floating, Bobbing"; + prefix = "(177)"; + } + 178 + { + title = "Crumbling, Respawn, Floating"; + prefix = "(178)"; + } + 179 + { + title = "Crumbling, No Respawn, Floating"; + prefix = "(179)"; + } + 180 + { + title = "Crumbling, Respawn, Air Bobbing"; + prefix = "(180)"; + } + } + + fofspecial + { + title = "FOF (special)"; + + 200 + { + title = "Light Block"; + prefix = "(200)"; + } + 201 + { + title = "Half Light Block"; + prefix = "(201)"; + } + 202 + { + title = "Fog Block"; + prefix = "(202)"; + } + 250 + { + title = "Mario Block"; + prefix = "(250)"; + } + 251 + { + title = "Thwomp Block"; + prefix = "(251)"; + } + 252 + { + title = "Shatter Block"; + prefix = "(252)"; + } + 253 + { + title = "Shatter Block, Translucent"; + prefix = "(253)"; + } + 254 + { + title = "Bustable Block"; + prefix = "(254)"; + } + 255 + { + title = "Spin-Bustable Block"; + prefix = "(255)"; + } + 256 + { + title = "Spin-Bustable Block, Translucent"; + prefix = "(256)"; + } + 257 + { + title = "Quicksand"; + prefix = "(257)"; + } + 258 + { + title = "Laser"; + prefix = "(258)"; + } + 259 + { + title = "Custom FOF"; + prefix = "(259)"; + } + } + + linedeftrigger + { + title = "Linedef Executor Trigger"; + + 300 + { + title = "Continuous"; + prefix = "(300)"; + } + 301 + { + title = "Each Time"; + prefix = "(301)"; + } + 302 + { + title = "Once"; + prefix = "(302)"; + } + 303 + { + title = "Ring Count - Continuous"; + prefix = "(303)"; + } + 304 + { + title = "Ring Count - Once"; + prefix = "(304)"; + } + 305 + { + title = "Character Ability - Continuous"; + prefix = "(305)"; + } + 306 + { + title = "Character Ability - Each Time"; + prefix = "(306)"; + } + 307 + { + title = "Character Ability - Once"; + prefix = "(307)"; + } + 308 + { + title = "Race Only - Once"; + prefix = "(308)"; + } + 309 + { + title = "CTF Red Team - Continuous"; + prefix = "(309)"; + } + 310 + { + title = "CTF Red Team - Each Time"; + prefix = "(310)"; + } + 311 + { + title = "CTF Blue Team - Continuous"; + prefix = "(311)"; + } + 312 + { + title = "CTF Blue Team - Each Time"; + prefix = "(312)"; + } + 313 + { + title = "No More Enemies - Once"; + prefix = "(313)"; + } + 314 + { + title = "Number of Pushables - Continuous"; + prefix = "(314)"; + } + 315 + { + title = "Number of Pushables - Once"; + prefix = "(315)"; + } + 317 + { + title = "Condition Set Trigger - Continuous"; + prefix = "(317)"; + } + 318 + { + title = "Condition Set Trigger - Once"; + prefix = "(318)"; + } + 319 + { + title = "Unlockable - Continuous"; + prefix = "(319)"; + } + 320 + { + title = "Unlockable - Once"; + prefix = "(320)"; + } + 321 + { + title = "Trigger After X Calls - Continuous"; + prefix = "(321)"; + } + 322 + { + title = "Trigger After X Calls - Each Time"; + prefix = "(322)"; + } + 323 + { + title = "NiGHTSerize - Each Time"; + prefix = "(323)"; + } + 324 + { + title = "NiGHTSerize - Once"; + prefix = "(324)"; + } + 325 + { + title = "De-NiGHTSerize - Each Time"; + prefix = "(325)"; + } + 326 + { + title = "De-NiGHTSerize - Once"; + prefix = "(326)"; + } + 327 + { + title = "NiGHTS Lap - Each Time"; + prefix = "(327)"; + } + 328 + { + title = "NiGHTS Lap - Once"; + prefix = "(328)"; + } + 329 + { + title = "Ideya Capture Touch - Each Time"; + prefix = "(329)"; + } + 330 + { + title = "Ideya Capture Touch - Once"; + prefix = "(330)"; + } + 331 + { + title = "Player Skin - Continuous"; + flags64text = "[6] Disable for this skin"; + prefix = "(331)"; + } + 332 + { + title = "Player Skin - Each Time"; + prefix = "(332)"; + } + 333 + { + title = "Player Skin - Once"; + prefix = "(333)"; + } + 399 + { + title = "Level Load"; + prefix = "(399)"; + } + } + + linedefexecsector + { + title = "Linedef Executor (sector)"; + + 400 + { + title = "Set Tagged Sector's Floor Height/Texture"; + prefix = "(400)"; + } + 401 + { + title = "Set Tagged Sector's Ceiling Height/Texture"; + prefix = "(401)"; + } + 402 + { + title = "Set Tagged Sector's Light Level"; + prefix = "(402)"; + } + 409 + { + title = "Change Tagged Sector's Tag"; + prefix = "(409)"; + } + 410 + { + title = "Change Front Sector's Tag"; + prefix = "(410)"; + } + 416 + { + title = "Start Adjustable Flickering Light"; + prefix = "(416)"; + } + 417 + { + title = "Start Adjustable Pulsating Light"; + prefix = "(417)"; + } + 418 + { + title = "Start Adjustable Blinking Light (unsynchronized)"; + prefix = "(418)"; + } + 419 + { + title = "Start Adjustable Blinking Light (synchronized)"; + prefix = "(419)"; + } + 420 + { + title = "Fade Light Level"; + prefix = "(420)"; + } + 421 + { + title = "Stop Lighting Effect"; + prefix = "(421)"; + } + 435 + { + title = "Change Plane Scroller Direction"; + prefix = "(435)"; + } + } + + linedefexecplane + { + title = "Linedef Executor (plane movement)"; + + 403 + { + title = "Move Tagged Sector's Floor"; + prefix = "(403)"; + } + 404 + { + title = "Move Tagged Sector's Ceiling"; + prefix = "(404)"; + } + 405 + { + title = "Move Floor According to Front Texture Offsets"; + prefix = "(405)"; + } + 407 + { + title = "Move Ceiling According to Front Texture Offsets"; + prefix = "(407)"; + } + 411 + { + title = "Stop Plane Movement"; + prefix = "(411)"; + } + 428 + { + title = "Start Platform Movement"; + prefix = "(428)"; + } + 429 + { + title = "Crush Ceiling Once"; + prefix = "(429)"; + } + 430 + { + title = "Crush Floor Once"; + prefix = "(430)"; + } + 431 + { + title = "Crush Floor and Ceiling Once"; + prefix = "(431)"; + } + } + + linedefexecplayer + { + title = "Linedef Executor (player/object)"; + + 412 + { + title = "Teleporter"; + prefix = "(412)"; + } + 425 + { + title = "Change Object State"; + prefix = "(425)"; + } + 426 + { + title = "Stop Object"; + prefix = "(426)"; + } + 427 + { + title = "Award Score"; + prefix = "(427)"; + } + 432 + { + title = "Enable/Disable 2D Mode"; + prefix = "(432)"; + } + 433 + { + title = "Enable/Disable Gravity Flip"; + prefix = "(433)"; + } + 434 + { + title = "Award Power-Up"; + prefix = "(434)"; + } + 437 + { + title = "Disable Player Control"; + prefix = "(437)"; + } + 438 + { + title = "Change Object Size"; + prefix = "(438)"; + } + 442 + { + title = "Change Object Type State"; + prefix = "(442)"; + } + 457 + { + title = "Track Object's Angle"; + prefix = "(457)"; + } + 458 + { + title = "Stop Tracking Object's Angle"; + prefix = "(458)"; + } + 460 + { + title = "Award Rings"; + prefix = "(460)"; + } + 461 + { + title = "Spawn Object"; + prefix = "(461)"; + } + 462 + { + title = "Stop Timer/Exit Stage in Record Attack"; + prefix = "(462)"; + } + } + + linedefexecmisc + { + title = "Linedef Executor (misc.)"; + + 413 + { + title = "Change Music"; + prefix = "(413)"; + } + 414 + { + title = "Play Sound Effect"; + prefix = "(414)"; + } + 415 + { + title = "Run Script"; + prefix = "(415)"; + } + 422 + { + title = "Switch to Cut-Away View"; + prefix = "(422)"; + } + 423 + { + title = "Change Sky"; + prefix = "(423)"; + } + 424 + { + title = "Change Weather"; + prefix = "(424)"; + } + 436 + { + title = "Shatter FOF"; + prefix = "(436)"; + } + 439 + { + title = "Change Tagged Linedef's Textures"; + prefix = "(439)"; + } + 440 + { + title = "Start Metal Sonic Race"; + prefix = "(440)"; + } + 441 + { + title = "Condition Set Trigger"; + prefix = "(441)"; + } + 443 + { + title = "Call Lua Function"; + prefix = "(443)"; + } + 444 + { + title = "Earthquake"; + prefix = "(444)"; + } + 445 + { + title = "Make FOF Disappear/Reappear"; + prefix = "(445)"; + } + 446 + { + title = "Make FOF Crumble"; + prefix = "(446)"; + } + 447 + { + title = "Change Tagged Sector's Colormap"; + prefix = "(447)"; + } + 448 + { + title = "Change Skybox"; + prefix = "(448)"; + } + 449 + { + title = "Enable Bosses with Parameter"; + prefix = "(449)"; + } + 450 + { + title = "Execute Linedef Executor (specific tag)"; + prefix = "(450)"; + } + 451 + { + title = "Execute Linedef Executor (random tag in range)"; + prefix = "(451)"; + } + 452 + { + title = "Set FOF Translucency"; + prefix = "(452)"; + } + 453 + { + title = "Fade FOF"; + prefix = "(453)"; + } + 454 + { + title = "Stop Fading FOF"; + prefix = "(454)"; + } + 455 + { + title = "Fade Tagged Sector's Colormap"; + prefix = "(455)"; + } + 456 + { + title = "Stop Fading Tagged Sector's Colormap"; + prefix = "(456)"; + } + 459 + { + title = "Control Text Prompt"; + prefix = "(459)"; + } + } + + linedefexecpoly + { + title = "Linedef Executor (polyobject)"; + + 480 + { + title = "Door Slide"; + prefix = "(480)"; + } + 481 + { + title = "Door Swing"; + prefix = "(481)"; + } + 482 + { + title = "Move"; + prefix = "(482)"; + } + 483 + { + title = "Move, Override"; + prefix = "(483)"; + } + 484 + { + title = "Rotate Right"; + prefix = "(484)"; + } + 485 + { + title = "Rotate Right, Override"; + prefix = "(485)"; + } + 486 + { + title = "Rotate Left"; + prefix = "(486)"; + } + 487 + { + title = "Rotate Left, Override"; + prefix = "(487)"; + } + 488 + { + title = "Move by Waypoints"; + prefix = "(488)"; + } + 489 + { + title = "Turn Invisible, Intangible"; + prefix = "(489)"; + } + 490 + { + title = "Turn Visible, Tangible"; + prefix = "(490)"; + } + 491 + { + title = "Set Translucency"; + prefix = "(491)"; + } + 492 + { + title = "Fade Translucency"; + prefix = "(492)"; + } + } + + wallscroll + { + title = "Wall Scrolling"; + + 500 + { + title = "Scroll Wall Front Side Left"; + prefix = "(500)"; + } + 501 + { + title = "Scroll Wall Front Side Right"; + prefix = "(501)"; + } + 502 + { + title = "Scroll Wall According to Linedef"; + prefix = "(502)"; + } + 503 + { + title = "Scroll Wall According to Linedef (Accelerative)"; + prefix = "(503)"; + } + 504 + { + title = "Scroll Wall According to Linedef (Displacement)"; + prefix = "(504)"; + } + 505 + { + title = "Scroll Texture by Front Side Offsets"; + prefix = "(505)"; + } + 506 + { + title = "Scroll Texture by Back Side Offsets"; + prefix = "(506)"; + } + } + + planescroll + { + title = "Plane Scrolling"; + + 510 + { + title = "Scroll Floor Texture"; + prefix = "(510)"; + } + 511 + { + title = "Scroll Floor Texture (Accelerative)"; + prefix = "(511)"; + } + 512 + { + title = "Scroll Floor Texture (Displacement)"; + prefix = "(512)"; + } + 513 + { + title = "Scroll Ceiling Texture"; + prefix = "(513)"; + } + 514 + { + title = "Scroll Ceiling Texture (Accelerative)"; + prefix = "(514)"; + } + 515 + { + title = "Scroll Ceiling Texture (Displacement)"; + prefix = "(515)"; + } + 520 + { + title = "Carry Objects on Floor"; + prefix = "(520)"; + } + 521 + { + title = "Carry Objects on Floor (Accelerative)"; + prefix = "(521)"; + } + 522 + { + title = "Carry Objects on Floor (Displacement)"; + prefix = "(522)"; + } + 523 + { + title = "Carry Objects on Ceiling"; + prefix = "(523)"; + } + 524 + { + title = "Carry Objects on Ceiling (Accelerative)"; + prefix = "(524)"; + } + 525 + { + title = "Carry Objects on Ceiling (Displacement)"; + prefix = "(525)"; + } + 530 + { + title = "Scroll Floor Texture and Carry Objects"; + prefix = "(530)"; + } + 531 + { + title = "Scroll Floor Texture and Carry Objects (Accelerative)"; + prefix = "(531)"; + } + 532 + { + title = "Scroll Floor Texture and Carry Objects (Displacement)"; + prefix = "(532)"; + } + 533 + { + title = "Scroll Ceiling Texture and Carry Objects"; + prefix = "(533)"; + } + 534 + { + title = "Scroll Ceiling Texture and Carry Objects (Accelerative)"; + prefix = "(534)"; + } + 535 + { + title = "Scroll Ceiling Texture and Carry Objects (Displacement)"; + prefix = "(535)"; + } + } + + pusher + { + title = "Pusher"; + + 541 + { + title = "Wind"; + prefix = "(541)"; + } + 542 + { + title = "Upwards Wind"; + prefix = "(542)"; + } + 543 + { + title = "Downwards Wind"; + prefix = "(543)"; + } + 544 + { + title = "Current"; + prefix = "(544)"; + } + 545 + { + title = "Upwards Current"; + prefix = "(545)"; + } + 546 + { + title = "Downwards Current"; + prefix = "(546)"; + } + 547 + { + title = "Push/Pull"; + prefix = "(547)"; + } + } + + light + { + title = "Lighting"; + + 600 + { + title = "Floor Lighting"; + prefix = "(600)"; + } + 601 + { + title = "Ceiling Lighting"; + prefix = "(601)"; + } + 602 + { + title = "Adjustable Pulsating Light"; + prefix = "(602)"; + } + 603 + { + title = "Adjustable Flickering Light"; + prefix = "(603)"; + } + 604 + { + title = "Adjustable Blinking Light (unsynchronized)"; + prefix = "(604)"; + } + 605 + { + title = "Adjustable Blinking Light (synchronized)"; + prefix = "(605)"; + } + 606 + { + title = "Colormap"; + prefix = "(606)"; + } + } + + slope + { + title = "Slope"; + + 700 + { + title = "Slope Frontside Floor"; + prefix = "(700)"; + } + 701 + { + title = "Slope Frontside Ceiling"; + prefix = "(701)"; + } + 702 + { + title = "Slope Frontside Floor and Ceiling"; + prefix = "(702)"; + } + 703 + { + title = "Slope Frontside Floor and Backside Ceiling"; + prefix = "(703)"; +ยด } + 704 + { + title = "Slope Frontside Floor by 3 Tagged Vertex Things"; + prefix = "(704)"; + } + 705 + { + title = "Slope Frontside Ceiling by 3 Tagged Vertex Things"; + prefix = "(705)"; + } + 710 + { + title = "Slope Backside Floor"; + prefix = "(710)"; + } + 711 + { + title = "Slope Backside Ceiling"; + prefix = "(711)"; + } + 712 + { + title = "Slope Backside Floor and Ceiling"; + prefix = "(712)"; + } + 713 + { + title = "Slope Backside Floor and Frontside Ceiling"; + prefix = "(713)"; + } + 714 + { + title = "Slope Backside Floor by 3 Tagged Vertex Things"; + prefix = "(714)"; + } + 715 + { + title = "Slope Backside Ceiling by 3 Tagged Vertex Things"; + prefix = "(715)"; + } + 720 + { + title = "Copy Frontside Floor Slope from Line Tag"; + prefix = "(720)"; + } + 721 + { + title = "Copy Frontside Ceiling Slope from Line Tag"; + prefix = "(721)"; + } + 722 + { + title = "Copy Frontside Floor and Ceiling Slope from Line Tag"; + prefix = "(722)"; + } + 799 + { + title = "Set Tagged Dynamic Slope Vertex to Front Sector Height"; + prefix = "(799)"; + } + } + + transwall + { + title = "Translucent Wall"; + + 900 + { + title = "90% Opaque"; + prefix = "(900)"; + } + 901 + { + title = "80% Opaque"; + prefix = "(901)"; + } + 902 + { + title = "70% Opaque"; + prefix = "(902)"; + } + 903 + { + title = "60% Opaque"; + prefix = "(903)"; + } + 904 + { + title = "50% Opaque"; + prefix = "(904)"; + } + 905 + { + title = "40% Opaque"; + prefix = "(905)"; + } + 906 + { + title = "30% Opaque"; + prefix = "(906)"; + } + 907 + { + title = "20% Opaque"; + prefix = "(907)"; + } + 908 + { + title = "10% Opaque"; + prefix = "(908)"; + } + 909 + { + title = "Fog Wall"; + prefix = "(909)"; + } + } +} + +udmf +{ + misc + { + title = "Miscellaneous"; + + 0 + { + title = "None"; + prefix = "(0)"; + } + } + + polyobject + { + title = "PolyObject"; + + 20 + { + title = "First Line"; + prefix = "(20)"; + arg0 + { + title = "PolyObject ID"; + type = 14; + } + arg1 + { + title = "Parent ID"; + type = 14; + } + arg2 + { + title = "Translucency"; + } + arg3 + { + title = "Flags"; + type = 12; + enum + { + 1 = "Don't render insides"; + 2 = "Intangible"; + 4 = "Stopped by pushables"; + 8 = "Don't render planes"; + 16 = "Trigger linedef executor on touch"; + 32 = "Crush player"; + 64 = "Cut cyan flat pixels"; + } + } + arg4 + { + title = "Trigger linedef tag"; + type = 15; + } + } + } + + fof + { + title = "FOF"; + + 100 + { + title = "Solid"; + prefix = "(100)"; + arg0 + { + title = "Target sector tag"; + type = 13; + } + arg1 + { + title = "Visibility"; + type = 12; + enum + { + 1 = "Don't render planes"; + 2 = "Don't render sides"; + } + } + arg2 + { + title = "Translucency"; + type = 11; + enum + { + 0 = "Opaque"; + 1 = "Translucent, no insides"; + 2 = "Translucent, render insides"; + } + } + arg3 + { + title = "Tangibility"; + type = 12; + enum = "tangibility"; + } + arg4 + { + title = "Cast shadow?"; + type = 11; + enum = "yesno"; + } + } + + 120 + { + title = "Water"; + prefix = "(120)"; + arg0 + { + title = "Target sector tag"; + type = 13; + } + arg1 + { + title = "Flags"; + type = 12; + enum + { + 1 = "Opaque"; + 2 = "Don't render sides"; + 4 = "Render separate light level"; + 8 = "Use target light level"; + 16 = "No ripple effect"; + 32 = "Goo physics"; + } + } + } + } + + linedefexecmisc + { + title = "Linedef Executor (misc.)"; + + 443 + { + title = "Call Lua Function"; + prefix = "(443)"; + stringarg0 + { + title = "Function name"; + type = 2; + } + } + + 447 + { + title = "Change Tagged Sector's Colormap"; + prefix = "(447)"; + arg0 + { + title = "Target sector tag"; + type = 13; + } + arg1 + { + title = "Colormap sector tag"; + type = 13; + } + arg2 + { + title = "Flags"; + type = 12; + enum + { + 1 = "Add to existing colormap"; + 2 = "Subtract light R"; + 4 = "Subtract light G"; + 8 = "Subtract light B"; + 16 = "Subtract light A"; + 32 = "Subtract fade R"; + 64 = "Subtract fade G"; + 128 = "Subtract fade B"; + 256 = "Subtract fade A"; + 512 = "Subtract fadestart"; + 1024 = "Subtract fadeend"; + 2048 = "Ignore flags"; + } + } + } + + 455 + { + title = "Fade Tagged Sector's Colormap"; + prefix = "(455)"; + arg0 + { + title = "Target sector tag"; + type = 13; + } + arg1 + { + title = "Colormap sector tag"; + type = 13; + } + arg2 + { + title = "Fade duration"; + } + arg3 + { + title = "Flags"; + type = 12; + enum + { + 1 = "Add to existing colormap"; + 2 = "Subtract light R"; + 4 = "Subtract light G"; + 8 = "Subtract light B"; + 16 = "Subtract light A"; + 32 = "Subtract fade R"; + 64 = "Subtract fade G"; + 128 = "Subtract fade B"; + 256 = "Subtract fade A"; + 512 = "Subtract fadestart"; + 1024 = "Subtract fadeend"; + 2048 = "Ignore flags"; + 4096 = "Fade from invisible black"; + 8192 = "Interrupt ongoing fades"; + } + } + } + + 456 + { + title = "Stop Fading Tagged Sector's Colormap"; + prefix = "(456)"; + arg0 + { + title = "Target sector tag"; + type = 13; + } + } + + 465 + { + title = "Set Linedef Executor Delay"; + prefix = "(465)"; + arg0 + { + title = "Linedef tag"; + type = 15; + } + arg1 + { + title = "Value"; + } + arg2 + { + title = "Set/add?"; + type = 11; + enum + { + 0 = "Set"; + 1 = "Add"; + } + } + } + } + + light + { + 606 + { + title = "Copy Colormap"; + prefix = "(606)"; + arg0 + { + title = "Target sector tag"; + type = 13; + } + arg1 + { + title = "Colormap sector tag"; + type = 13; + } + } + } + + slope + { + title = "Slope"; + + 700 + { + title = "Create Sector-Based Slope"; + prefix = "(700)"; + id = "plane_align"; + arg0 + { + title = "Floor"; + type = 11; + enum = "frontback"; + } + arg1 + { + title = "Ceiling"; + type = 11; + enum = "frontback"; + } + arg2 + { + title = "Flags"; + type = 12; + enum + { + 1 = "No physics"; + 2 = "Dynamic"; + } + } + } + + 704 + { + title = "Create Vertex-Based Slope"; + prefix = "(704)"; + arg0 + { + title = "Plane"; + type = 11; + enum + { + 0 = "Front floor"; + 1 = "Front ceiling"; + 2 = "Back floor"; + 3 = "Back ceiling"; + } + } + arg1 + { + title = "Vertex 1 tag"; + type = 14; + } + arg2 + { + title = "Vertex 2 tag"; + type = 14; + } + arg3 + { + title = "Vertex 3 tag"; + type = 14; + } + arg4 + { + title = "Flags"; + type = 12; + enum + { + 1 = "No physics"; + 2 = "Dynamic"; + } + } + } + + 720 + { + title = "Copy Slope"; + prefix = "(720)"; + arg0 + { + title = "Front floor tag"; + type = 13; + } + arg1 + { + title = "Front ceiling tag"; + type = 13; + } + arg2 + { + title = "Back floor tag"; + type = 13; + } + arg3 + { + title = "Back ceiling tag"; + type = 13; + } + arg4 + { + title = "Share slope"; + type = 12; + enum + { + 1 = "Front floor to back sector"; + 2 = "Back floor to front sector"; + 4 = "Front ceiling to back sector"; + 8 = "Back ceiling to front sector"; + } + } + } + } +} \ No newline at end of file diff --git a/extras/conf/udb/Includes/SRB222_misc.cfg b/extras/conf/udb/Includes/SRB222_misc.cfg new file mode 100644 index 000000000..68629149e --- /dev/null +++ b/extras/conf/udb/Includes/SRB222_misc.cfg @@ -0,0 +1,625 @@ +linedefflags +{ + 1 = "[0] Impassable"; + 2 = "[1] Block Enemies"; + 4 = "[2] Double-Sided"; + 8 = "[3] Upper Unpegged"; + 16 = "[4] Lower Unpegged"; + 32 = "[5] Slope Skew (E1)"; + 64 = "[6] Not Climbable"; + 128 = "[7] No Midtexture Skew (E2)"; + 256 = "[8] Peg Midtexture (E3)"; + 512 = "[9] Solid Midtexture (E4)"; + 1024 = "[10] Repeat Midtexture (E5)"; + 2048 = "[11] Netgame Only"; + 4096 = "[12] No Netgame"; + 8192 = "[13] Effect 6"; + 16384 = "[14] Bouncy Wall"; + 32768 = "[15] Transfer Line"; +} + + +// Linedef flags UDMF translation table +// This is needed for copy/paste and prefabs to work properly +// When the UDMF field name is prefixed with ! it is inverted +linedefflagstranslation +{ + 1 = "blocking"; + 2 = "blockmonsters"; + 4 = "twosided"; + 8 = "dontpegtop"; + 16 = "dontpegbottom"; + 32 = "skewtd"; + 64 = "noclimb"; + 128 = "noskew"; + 256 = "midpeg"; + 512 = "midsolid"; + 1024 = "wrapmidtex"; + 2048 = "netonly"; + 4096 = "nonet"; + 8192 = "effect6"; + 16384 = "bouncy"; + 32768 = "transfer"; +} + + +linedefflags_udmf +{ + blocking = "Impassable"; + blockmonsters = "Block Enemies"; + twosided = "Double-Sided"; + dontpegtop = "Upper Unpegged"; + dontpegbottom = "Lower Unpegged"; + skewtd = "Slope Skew"; + noclimb = "Not Climbable"; + noskew = "No Midtexture Skew"; + midpeg = "Peg Midtexture"; + midsolid = "Solid Midtexture"; + wrapmidtex = "Repeat Midtexture"; + netonly = "Netgame Only"; + nonet = "No Netgame"; + effect6 = "Effect 6"; + bouncy = "Bouncy Wall"; + transfer = "Transfer Line"; +} + +/*linedefrenderstyles +{ + translucent = "Translucent"; + fog = "Fog"; +}*/ + +sectorflags +{ + colormapfog = "Fog Planes in Colormap"; + colormapfadesprites = "Fade Fullbright in Colormap"; + colormapprotected = "Protected Colormap"; +} + +thingflags +{ + 1 = "[1] Extra"; + 2 = "[2] Flip"; + 4 = "[4] Special"; + 8 = "[8] Ambush"; +} + +// THING FLAGS +thingflags_udmf +{ + extra = "Extra"; + flip = "Flip"; + special = "Special"; + ambush = "Ambush"; +} + + +// Thing flags UDMF translation table +// This is needed for copy/paste and prefabs to work properly +// When the UDMF field name is prefixed with ! it is inverted +thingflagstranslation +{ + 1 = "extra"; + 2 = "flip"; + 4 = "special"; + 8 = "ambush"; +} + + +// DEFAULT SECTOR BRIGHTNESS LEVELS +sectorbrightness +{ + 255; + 248; + 240; + 232; + 224; + 216; + 208; + 200; + 192; + 184; + 176; + 168; + 160; + 152; + 144; + 136; + 128; + 120; + 112; + 104; + 96; + 88; + 80; + 72; + 64; + 56; + 48; + 40; + 32; + 24; + 16; + 8; + 0; +} + +/* +TEXTURES AND FLAT SOURCES +This tells Doom Builder where to find the information for textures +and flats in the IWAD file, Addition WAD file and Map WAD file. + +Start and end lumps must be given in a structure (of which the +key name doesnt matter) and any textures or flats in between them +are loaded in either the textures category or flats category. + +For textures: PNAMES, TEXTURE1 and TEXTURE2 are loaded by default. +*/ +textures +{ + zdoom1 + { + start = "TX_START"; + end = "TX_END"; + } +} + +/* +ADDITIONAL UNIVERSAL DOOM MAP FORMAT FIELD DEFINITIONS +Only add fields here that Doom Builder does not edit with its own user-interface! +The "default" field must match the UDMF specifications! + +Field data types: +0 = integer * +1 = float +2 = string +3 = bool +4 = linedef action (integer) * +5 = sector effect (integer) * +6 = texture (string) +7 = flat (string) +8 = angle in degrees (integer) +9 = angle in radians (float) +10 = XXRRGGBB color (integer) +11 = enum option (integer) * +12 = enum bits (integer) * +13 = sector tag (integer) * +14 = thing tag (integer) * +15 = linedef tag (integer) * +16 = enum option (string) +17 = angle in degrees (float) +22 = byte angle (integer) +*/ +universalfields +{ + sector + { + lightalpha + { + type = 0; + default = 25; + } + + fadealpha + { + type = 0; + default = 25; + } + + fadestart + { + type = 0; + default = 0; + } + + fadeend + { + type = 0; + default = 33; + } + + foglighting + { + type = 3; + default = false; + } + } + + linedef + { + arg5 + { + type = 0; + default = 0; + } + stringarg0 + { + type = 2; + default = ""; + } + stringarg1 + { + type = 2; + default = ""; + } + executordelay + { + type = 0; + default = 0; + } + } + + sidedef + { + repeatcnt + { + type = 0; + default = 0; + } + } + + thing + { + } +} + +/* +MAP LUMP NAMES +Map lumps are loaded with the map as long as they are right after each other. When the editor +meets a lump which is not defined in this list it will ignore the map if not satisfied. +The order of items defines the order in which lumps will be written to WAD file on save. +To indicate the map header lump, use ~MAP + +Legenda: +required = Lump is required to exist. +blindcopy = Lump will be copied along with the map blindly. (useful for lumps Doom Builder doesn't use) +nodebuild = The nodebuilder generates this lump. +allowempty = The nodebuilder is allowed to leave this lump empty. +scriptbuild = This lump is a text-based script, which should be compiled using current script compiler; +script = This lump is a text-based script. Specify the filename of the script configuration to use. +*/ + +doommaplumpnames +{ + ~MAP + { + required = true; + blindcopy = true; + nodebuild = false; + } + + THINGS + { + required = true; + nodebuild = true; + allowempty = true; + } + + LINEDEFS + { + required = true; + nodebuild = true; + allowempty = false; + } + + SIDEDEFS + { + required = true; + nodebuild = true; + allowempty = false; + } + + VERTEXES + { + required = true; + nodebuild = true; + allowempty = false; + } + + SEGS + { + required = false; + nodebuild = true; + allowempty = false; + } + + SSECTORS + { + required = false; + nodebuild = true; + allowempty = false; + } + + NODES + { + required = false; + nodebuild = true; + allowempty = false; + } + + SECTORS + { + required = true; + nodebuild = true; + allowempty = false; + } + + REJECT + { + required = false; + nodebuild = true; + allowempty = false; + } + + BLOCKMAP + { + required = false; + nodebuild = true; + allowempty = true; + } +} + +udmfmaplumpnames +{ + ZNODES + { + required = false; + nodebuild = true; + allowempty = false; + } + + REJECT + { + required = false; + nodebuild = true; + allowempty = false; + } + + BLOCKMAP + { + required = false; + nodebuild = true; + allowempty = true; + } +} + +// ENUMERATIONS +// These are enumerated lists for linedef types and UDMF fields. +// Reserved names are: angledeg, anglerad, color, texture, flat +enums +{ + falsetrue + { + 0 = "False"; + 1 = "True"; + } + + yesno + { + 0 = "Yes"; + 1 = "No"; + } + + noyes + { + 0 = "No"; + 1 = "Yes"; + } + + onoff + { + 0 = "On"; + 1 = "Off"; + } + + offon + { + 0 = "Off"; + 1 = "On"; + } + + updown + { + 0 = "Up"; + 1 = "Down"; + } + + downup + { + 0 = "Down"; + 1 = "Up"; + } + + frontback + { + 0 = "None"; + 1 = "Front"; + 2 = "Back"; + } + + tangibility + { + 1 = "Intangible from top"; + 2 = "Intangible from bottom"; + 4 = "Don't block players"; + 8 = "Don't block non-players"; + } +} + +//Default things filters +thingsfilters +{ + + filter0 + { + name = "Player starts"; + category = "starts"; + type = -1; + } + + + filter1 + { + name = "Enemies"; + category = "enemies"; + type = -1; + + } + + + filter2 + { + name = "NiGHTS Track"; + category = "nightstrk"; + type = -1; + + } + + + filter3 + { + name = "Normal Gravity"; + category = ""; + type = -1; + + fields + { + 2 = false; + } + + } + + + filter4 + { + name = "Reverse Gravity"; + category = ""; + type = -1; + + fields + { + 2 = true; + } + + } +} + +// Special linedefs +speciallinedefs +{ + soundlinedefflag = 64; // See linedefflags + singlesidedflag = 1; // See linedefflags + doublesidedflag = 4; // See linedefflags + impassableflag = 1; + upperunpeggedflag = 8; + lowerunpeggedflag = 16; + repeatmidtextureflag = 1024; + pegmidtextureflag = 256; +} + +speciallinedefs_udmf +{ + soundlinedefflag = "noclimb"; + singlesidedflag = "blocking"; + doublesidedflag = "twosided"; + impassableflag = "blocking"; + upperunpeggedflag = "dontpegtop"; + lowerunpeggedflag = "dontpegbottom"; + repeatmidtextureflag = "wrapmidtex"; + pegmidtextureflag = "midpeg"; +} + +scriptlumpnames +{ + MAINCFG + { + script = "SOC.cfg"; + } + + OBJCTCFG + { + script = "SOC.cfg"; + } + + SOC_ + { + script = "SOC.cfg"; + isprefix = true; + } + + LUA_ + { + script = "Lua.cfg"; + isprefix = true; + } +} + +// Texture sources +textures +{ + zdoom1 + { + start = "TX_START"; + end = "TX_END"; + } +} + +// Patch sources +patches +{ + standard1 + { + start = "P_START"; + end = "P_END"; + } + + standard2 + { + start = "PP_START"; + end = "PP_END"; + } +} + +// Sprite sources +sprites +{ + standard1 + { + start = "S_START"; + end = "S_END"; + } + + standard2 + { + start = "SS_START"; + end = "SS_END"; + } +} + +// Flat sources +flats +{ + standard1 + { + start = "F_START"; + end = "F_END"; + } + + standard2 + { + start = "FF_START"; + end = "FF_END"; + } + + standard3 + { + start = "FF_START"; + end = "F_END"; + } + + standard4 + { + start = "F_START"; + end = "FF_END"; + } +} \ No newline at end of file diff --git a/extras/conf/udb/Includes/SRB222_sectors.cfg b/extras/conf/udb/Includes/SRB222_sectors.cfg new file mode 100644 index 000000000..5cc14ad0f --- /dev/null +++ b/extras/conf/udb/Includes/SRB222_sectors.cfg @@ -0,0 +1,109 @@ +sectortypes +{ + 0 = "Normal"; + 1 = "Damage"; + 2 = "Damage (Water)"; + 3 = "Damage (Fire)"; + 4 = "Damage (Electrical)"; + 5 = "Spikes"; + 6 = "Death Pit (Camera Tilt)"; + 7 = "Death Pit (No Camera Tilt)"; + 8 = "Instant Kill"; + 9 = "Ring Drainer (Floor Touch)"; + 10 = "Ring Drainer (Anywhere in Sector)"; + 11 = "Special Stage Damage"; + 12 = "Space Countdown"; + 13 = "Ramp Sector (double step-up/down)"; + 14 = "Non-Ramp Sector (no step-down)"; + 15 = "Bouncy FOF"; + 16 = "Trigger Line Ex. (Pushable Objects)"; + 32 = "Trigger Line Ex. (Anywhere, All Players)"; + 48 = "Trigger Line Ex. (Floor Touch, All Players)"; + 64 = "Trigger Line Ex. (Anywhere in Sector)"; + 80 = "Trigger Line Ex. (Floor Touch)"; + 96 = "Trigger Line Ex. (Emerald Check)"; + 112 = "Trigger Line Ex. (NiGHTS Mare)"; + 128 = "Check for Linedef Executor on FOFs"; + 144 = "Egg Capsule"; + 160 = "Special Stage Time/Spheres Parameters"; + 176 = "Custom Global Gravity"; + 512 = "Wind/Current"; + 1024 = "Conveyor Belt"; + 1280 = "Speed Pad"; + 4096 = "Star Post Activator"; + 8192 = "Exit/Special Stage Pit/Return Flag"; + 12288 = "CTF Red Team Base"; + 16384 = "CTF Blue Team Base"; + 20480 = "Fan Sector"; + 24576 = "Super Sonic Transform"; + 28672 = "Force Spin"; + 32768 = "Zoom Tube Start"; + 36864 = "Zoom Tube End"; + 40960 = "Circuit Finish Line"; + 45056 = "Rope Hang"; + 49152 = "Intangible to the Camera"; +} + +gen_sectortypes +{ + first + { + 0 = "Normal"; + 1 = "Damage"; + 2 = "Damage (Water)"; + 3 = "Damage (Fire)"; + 4 = "Damage (Electrical)"; + 5 = "Spikes"; + 6 = "Death Pit (Camera Tilt)"; + 7 = "Death Pit (No Camera Tilt)"; + 8 = "Instant Kill"; + 9 = "Ring Drainer (Floor Touch)"; + 10 = "Ring Drainer (Anywhere in Sector)"; + 11 = "Special Stage Damage"; + 12 = "Space Countdown"; + 13 = "Ramp Sector (double step-up/down)"; + 14 = "Non-Ramp Sector (no step-down)"; + 15 = "Bouncy FOF"; + } + + second + { + 0 = "Normal"; + 16 = "Trigger Line Ex. (Pushable Objects)"; + 32 = "Trigger Line Ex. (Anywhere, All Players)"; + 48 = "Trigger Line Ex. (Floor Touch, All Players)"; + 64 = "Trigger Line Ex. (Anywhere in Sector)"; + 80 = "Trigger Line Ex. (Floor Touch)"; + 96 = "Trigger Line Ex. (Emerald Check)"; + 112 = "Trigger Line Ex. (NiGHTS Mare)"; + 128 = "Check for Linedef Executor on FOFs"; + 144 = "Egg Capsule"; + 160 = "Special Stage Time/Spheres Parameters"; + 176 = "Custom Global Gravity"; + } + + third + { + 0 = "Normal"; + 512 = "Wind/Current"; + 1024 = "Conveyor Belt"; + 1280 = "Speed Pad"; + } + + fourth + { + 0 = "Normal"; + 4096 = "Star Post Activator"; + 8192 = "Exit/Special Stage Pit/Return Flag"; + 12288 = "CTF Red Team Base"; + 16384 = "CTF Blue Team Base"; + 20480 = "Fan Sector"; + 24576 = "Super Sonic Transform"; + 28672 = "Force Spin"; + 32768 = "Zoom Tube Start"; + 36864 = "Zoom Tube End"; + 40960 = "Circuit Finish Line"; + 45056 = "Rope Hang"; + 49152 = "Intangible to the Camera"; + } +} \ No newline at end of file diff --git a/extras/conf/udb/Includes/SRB222_things.cfg b/extras/conf/udb/Includes/SRB222_things.cfg new file mode 100644 index 000000000..0ea452155 --- /dev/null +++ b/extras/conf/udb/Includes/SRB222_things.cfg @@ -0,0 +1,3141 @@ +// THING TYPES------------------------------------------------------------------ +// Color values: 1-Dark_Blue 2-Dark_Green 3-Turqoise 4-Dark_Red 5-Purple 6-Brown 7-Gray +// 8-Dark_Gray 9-Blue 10-Green 11-Cyan 12-Red 13-Magenta +// 14-Yellow 15-White 16-Pink 17-Orange 18-Gold 19-Cream + +editor +{ + color = 15; // White + arrow = 1; + title = ""; + error = -1; + width = 8; + height = 16; + sort = 1; + + 3328 = "3D Mode Start"; +} + +starts +{ + color = 1; // Blue + arrow = 1; + title = "Player Starts"; + width = 16; + height = 48; + sprite = "PLAYA0"; + + 1 + { + title = "Player 01 Start"; + sprite = "PLAYA0"; + } + 2 + { + title = "Player 02 Start"; + sprite = "PLAYA0"; + } + 3 + { + title = "Player 03 Start"; + sprite = "PLAYA0"; + } + 4 + { + title = "Player 04 Start"; + sprite = "PLAYA0"; + } + 5 + { + title = "Player 05 Start"; + sprite = "PLAYA0"; + } + 6 + { + title = "Player 06 Start"; + sprite = "PLAYA0"; + } + 7 + { + title = "Player 07 Start"; + sprite = "PLAYA0"; + } + 8 + { + title = "Player 08 Start"; + sprite = "PLAYA0"; + } + 9 + { + title = "Player 09 Start"; + sprite = "PLAYA0"; + } + 10 + { + title = "Player 10 Start"; + sprite = "PLAYA0"; + } + 11 + { + title = "Player 11 Start"; + sprite = "PLAYA0"; + } + 12 + { + title = "Player 12 Start"; + sprite = "PLAYA0"; + } + 13 + { + title = "Player 13 Start"; + sprite = "PLAYA0"; + } + 14 + { + title = "Player 14 Start"; + sprite = "PLAYA0"; + } + 15 + { + title = "Player 15 Start"; + sprite = "PLAYA0"; + } + 16 + { + title = "Player 16 Start"; + sprite = "PLAYA0"; + } + 17 + { + title = "Player 17 Start"; + sprite = "PLAYA0"; + } + 18 + { + title = "Player 18 Start"; + sprite = "PLAYA0"; + } + 19 + { + title = "Player 19 Start"; + sprite = "PLAYA0"; + } + 20 + { + title = "Player 20 Start"; + sprite = "PLAYA0"; + } + 21 + { + title = "Player 21 Start"; + sprite = "PLAYA0"; + } + 22 + { + title = "Player 22 Start"; + sprite = "PLAYA0"; + } + 23 + { + title = "Player 23 Start"; + sprite = "PLAYA0"; + } + 24 + { + title = "Player 24 Start"; + sprite = "PLAYA0"; + } + 25 + { + title = "Player 25 Start"; + sprite = "PLAYA0"; + } + 26 + { + title = "Player 26 Start"; + sprite = "PLAYA0"; + } + 27 + { + title = "Player 27 Start"; + sprite = "PLAYA0"; + } + 28 + { + title = "Player 28 Start"; + sprite = "PLAYA0"; + } + 29 + { + title = "Player 29 Start"; + sprite = "PLAYA0"; + } + 30 + { + title = "Player 30 Start"; + sprite = "PLAYA0"; + } + 31 + { + title = "Player 31 Start"; + sprite = "PLAYA0"; + } + 32 + { + title = "Player 32 Start"; + sprite = "PLAYA0"; + } + 33 + { + title = "Match Start"; + sprite = "NDRNA2A8"; + } + 34 + { + title = "CTF Red Team Start"; + sprite = "SIGNG0"; + } + 35 + { + title = "CTF Blue Team Start"; + sprite = "SIGNE0"; + } +} + +enemies +{ + color = 9; // Light_Blue + arrow = 1; + title = "Enemies"; + + 100 + { + title = "Crawla (Blue)"; + sprite = "POSSA1"; + width = 24; + height = 32; + } + 101 + { + title = "Crawla (Red)"; + sprite = "SPOSA1"; + width = 24; + height = 32; + } + 102 + { + title = "Stupid Dumb Unnamed RoboFish"; + sprite = "FISHA0"; + width = 8; + height = 28; + } + 103 + { + title = "Buzz (Gold)"; + sprite = "BUZZA1"; + width = 28; + height = 40; + } + 104 + { + title = "Buzz (Red)"; + sprite = "RBUZA1"; + width = 28; + height = 40; + } + 108 + { + title = "Deton"; + sprite = "DETNA1"; + width = 20; + height = 32; + } + 110 + { + title = "Turret"; + sprite = "TRETA1"; + width = 16; + height = 32; + } + 111 + { + title = "Pop-up Turret"; + sprite = "TURRI1"; + width = 12; + height = 64; + } + 122 + { + title = "Spring Shell (Green)"; + sprite = "SSHLA1"; + width = 24; + height = 40; + } + 125 + { + title = "Spring Shell (Yellow)"; + sprite = "SSHLI1"; + width = 24; + height = 40; + } + 109 + { + title = "Skim"; + sprite = "SKIMA1"; + width = 16; + height = 24; + } + 113 + { + title = "Jet Jaw"; + sprite = "JJAWA3A7"; + width = 12; + height = 20; + } + 126 + { + title = "Crushstacean"; + sprite = "CRABA0"; + width = 24; + height = 32; + } + 138 + { + title = "Banpyura"; + sprite = "CR2BA0"; + width = 24; + height = 32; + } + 117 + { + title = "Robo-Hood"; + sprite = "ARCHA1"; + width = 24; + height = 32; + } + 118 + { + title = "Lance-a-Bot"; + sprite = "CBFSA1"; + width = 32; + height = 72; + } + 1113 + { + title = "Suspicious Lance-a-Bot Statue"; + sprite = "CBBSA1"; + width = 32; + height = 72; + } + 119 + { + title = "Egg Guard"; + sprite = "ESHIA1"; + width = 16; + height = 48; + } + 115 + { + title = "Bird Aircraft Strike Hazard"; + sprite = "VLTRF1"; + width = 12; + height = 24; + } + 120 + { + title = "Green Snapper"; + sprite = "GSNPA1"; + width = 24; + height = 24; + } + 121 + { + title = "Minus"; + sprite = "MNUSA0"; + width = 24; + height = 32; + } + 134 + { + title = "Canarivore"; + sprite = "CANAA0"; + width = 12; + height = 80; + hangs = 1; + } + 123 + { + title = "Unidus"; + sprite = "UNIDA1"; + width = 18; + height = 36; + } + 135 + { + title = "Pterabyte Spawner"; + sprite = "PTERA2A8"; + width = 16; + height = 16; + } + 136 + { + title = "Pyre Fly"; + sprite = "PYREA0"; + width = 24; + height = 34; + } + 137 + { + title = "Dragonbomber"; + sprite = "DRABA1"; + width = 28; + height = 48; + } + 105 + { + title = "Jetty-Syn Bomber"; + sprite = "JETBB1"; + width = 20; + height = 50; + } + 106 + { + title = "Jetty-Syn Gunner"; + sprite = "JETGB1"; + width = 20; + height = 48; + } + 112 + { + title = "Spincushion"; + sprite = "SHRPA1"; + width = 16; + height = 24; + } + 114 + { + title = "Snailer"; + sprite = "SNLRA3A7"; + width = 24; + height = 48; + } + 129 + { + title = "Penguinator"; + sprite = "PENGA1"; + width = 24; + height = 32; + } + 130 + { + title = "Pophat"; + sprite = "POPHA1"; + width = 24; + height = 32; + } + 107 + { + title = "Crawla Commander"; + sprite = "CCOMA1"; + width = 16; + height = 32; + } + 131 + { + title = "Spinbobert"; + sprite = "SBOBB0"; + width = 32; + height = 32; + } + 132 + { + title = "Cacolantern"; + sprite = "CACOA0"; + width = 32; + height = 32; + } + 133 + { + title = "Hangster"; + sprite = "HBATC1"; + width = 24; + height = 24; + hangs = 1; + } + 127 + { + title = "Hive Elemental"; + sprite = "HIVEA0"; + width = 32; + height = 80; + } + 128 + { + title = "Bumblebore"; + sprite = "BUMBA1"; + width = 16; + height = 32; + } + 124 + { + title = "Buggle"; + sprite = "BBUZA1"; + width = 20; + height = 24; + } + 116 + { + title = "Pointy"; + sprite = "PNTYA1"; + width = 8; + height = 16; + } +} + +bosses +{ + color = 8; // Dark_Gray + arrow = 1; + title = "Bosses"; + + 200 + { + title = "Egg Mobile"; + sprite = "EGGMA1"; + width = 24; + height = 76; + } + 201 + { + title = "Egg Slimer"; + sprite = "EGGNA1"; + width = 24; + height = 76; + } + 202 + { + title = "Sea Egg"; + sprite = "EGGOA1"; + width = 32; + height = 116; + } + 203 + { + title = "Egg Colosseum"; + sprite = "EGGPA1"; + width = 24; + height = 76; + } + 204 + { + title = "Fang"; + sprite = "FANGA1"; + width = 24; + height = 60; + } + 206 + { + title = "Brak Eggman (Old)"; + sprite = "BRAKB1"; + width = 48; + height = 160; + } + 207 + { + title = "Metal Sonic (Race)"; + sprite = "METLI1"; + width = 16; + height = 48; + } + 208 + { + title = "Metal Sonic (Battle)"; + sprite = "METLC1"; + width = 16; + height = 48; + } + 209 + { + title = "Brak Eggman"; + sprite = "BRAK01"; + width = 48; + height = 160; + } + 290 + { + arrow = 0; + title = "Boss Escape Point"; + width = 8; + height = 16; + sprite = "internal:eggmanend"; + } + 291 + { + arrow = 0; + title = "Egg Capsule Center"; + width = 8; + height = 16; + sprite = "internal:capsule"; + } + 292 + { + arrow = 0; + title = "Boss Waypoint"; + width = 8; + height = 16; + sprite = "internal:eggmanway"; + } + 293 + { + title = "Metal Sonic Gather Point"; + sprite = "internal:metal"; + width = 8; + height = 16; + } + 294 + { + title = "Fang Waypoint"; + sprite = "internal:eggmanway"; + width = 8; + height = 16; + } +} + +rings +{ + color = 14; // Yellow + title = "Rings and Weapon Panels"; + width = 24; + height = 24; + sprite = "RINGA0"; + + 300 + { + title = "Ring"; + sprite = "RINGA0"; + width = 16; + } + 301 + { + title = "Bounce Ring"; + sprite = "internal:RNGBA0"; + } + 302 + { + title = "Rail Ring"; + sprite = "internal:RNGRA0"; + } + 303 + { + title = "Infinity Ring"; + sprite = "internal:RNGIA0"; + } + 304 + { + title = "Automatic Ring"; + sprite = "internal:RNGAA0"; + } + 305 + { + title = "Explosion Ring"; + sprite = "internal:RNGEA0"; + } + 306 + { + title = "Scatter Ring"; + sprite = "internal:RNGSA0"; + } + 307 + { + title = "Grenade Ring"; + sprite = "internal:RNGGA0"; + } + 308 + { + title = "CTF Team Ring (Red)"; + sprite = "internal:RRNGA0"; + width = 16; + } + 309 + { + title = "CTF Team Ring (Blue)"; + sprite = "internal:BRNGA0"; + width = 16; + } + 330 + { + title = "Bounce Ring Panel"; + sprite = "internal:PIKBA0"; + } + 331 + { + title = "Rail Ring Panel"; + sprite = "internal:PIKRA0"; + } + 332 + { + title = "Automatic Ring Panel"; + sprite = "internal:PIKAA0"; + } + 333 + { + title = "Explosion Ring Panel"; + sprite = "internal:PIKEA0"; + } + 334 + { + title = "Scatter Ring Panel"; + sprite = "internal:PIKSA0"; + } + 335 + { + title = "Grenade Ring Panel"; + sprite = "internal:PIKGA0"; + } +} + +collectibles +{ + color = 10; // Light_Green + title = "Other Collectibles"; + width = 16; + height = 32; + sort = 1; + sprite = "CEMGA0"; + + 310 + { + title = "CTF Red Flag"; + sprite = "RFLGA0"; + width = 24; + height = 64; + } + 311 + { + title = "CTF Blue Flag"; + sprite = "BFLGA0"; + width = 24; + height = 64; + } + 312 + { + title = "Emerald Token"; + sprite = "TOKEA0"; + width = 16; + height = 32; + } + 313 + { + title = "Chaos Emerald 1 (Green)"; + sprite = "CEMGA0"; + } + 314 + { + title = "Chaos Emerald 2 (Purple)"; + sprite = "CEMGB0"; + } + 315 + { + title = "Chaos Emerald 3 (Blue)"; + sprite = "CEMGC0"; + } + 316 + { + title = "Chaos Emerald 4 (Cyan)"; + sprite = "CEMGD0"; + } + 317 + { + title = "Chaos Emerald 5 (Orange)"; + sprite = "CEMGE0"; + } + 318 + { + title = "Chaos Emerald 6 (Red)"; + sprite = "CEMGF0"; + } + 319 + { + title = "Chaos Emerald 7 (Gray)"; + sprite = "CEMGG0"; + } + 320 + { + title = "Emerald Hunt Location"; + sprite = "SHRDA0"; + } + 321 + { + title = "Match Chaos Emerald Spawn"; + sprite = "CEMGA0"; + } + 322 + { + title = "Emblem"; + sprite = "EMBMA0"; + width = 16; + height = 30; + } +} + +boxes +{ + color = 7; // Gray + blocking = 2; + title = "Monitors"; + width = 18; + height = 40; + + 400 + { + title = "Super Ring (10 Rings)"; + sprite = "TVRIA0"; + } + 401 + { + title = "Pity Shield"; + sprite = "TVPIA0"; + } + 402 + { + title = "Attraction Shield"; + sprite = "TVATA0"; + } + 403 + { + title = "Force Shield"; + sprite = "TVFOA0"; + } + 404 + { + title = "Armageddon Shield"; + sprite = "TVARA0"; + } + 405 + { + title = "Whirlwind Shield"; + sprite = "TVWWA0"; + } + 406 + { + title = "Elemental Shield"; + sprite = "TVELA0"; + } + 407 + { + title = "Super Sneakers"; + sprite = "TVSSA0"; + } + 408 + { + title = "Invincibility"; + sprite = "TVIVA0"; + } + 409 + { + title = "Extra Life"; + sprite = "TV1UA0"; + } + 410 + { + title = "Eggman"; + sprite = "TVEGA0"; + } + 411 + { + title = "Teleporter"; + sprite = "TVMXA0"; + } + 413 + { + title = "Gravity Boots"; + sprite = "TVGVA0"; + } + 414 + { + title = "CTF Team Ring Monitor (Red)"; + sprite = "TRRIA0"; + } + 415 + { + title = "CTF Team Ring Monitor (Blue)"; + sprite = "TBRIA0"; + } + 416 + { + title = "Recycler"; + sprite = "TVRCA0"; + } + 418 + { + title = "Score (1,000 Points)"; + sprite = "TV1KA0"; + } + 419 + { + title = "Score (10,000 Points)"; + sprite = "TVTKA0"; + } + 420 + { + title = "Flame Shield"; + sprite = "TVFLA0"; + } + 421 + { + title = "Water Shield"; + sprite = "TVBBA0"; + } + 422 + { + title = "Lightning Shield"; + sprite = "TVZPA0"; + } +} + +boxes2 +{ + color = 18; // Gold + blocking = 2; + title = "Monitors (Respawning)"; + width = 20; + height = 44; + + 431 + { + title = "Pity Shield (Respawn)"; + sprite = "TVPIB0"; + } + 432 + { + title = "Attraction Shield (Respawn)"; + sprite = "TVATB0"; + } + 433 + { + title = "Force Shield (Respawn)"; + sprite = "TVFOB0"; + } + 434 + { + title = "Armageddon Shield (Respawn)"; + sprite = "TVARB0"; + } + 435 + { + title = "Whirlwind Shield (Respawn)"; + sprite = "TVWWB0"; + } + 436 + { + title = "Elemental Shield (Respawn)"; + sprite = "TVELB0"; + } + 437 + { + title = "Super Sneakers (Respawn)"; + sprite = "TVSSB0"; + } + 438 + { + title = "Invincibility (Respawn)"; + sprite = "TVIVB0"; + } + 440 + { + title = "Eggman (Respawn)"; + sprite = "TVEGB0"; + } + 443 + { + title = "Gravity Boots (Respawn)"; + sprite = "TVGVB0"; + } + 450 + { + title = "Flame Shield (Respawn)"; + sprite = "TVFLB0"; + } + 451 + { + title = "Water Shield (Respawn)"; + sprite = "TVBBB0"; + } + 452 + { + title = "Lightning Shield (Respawn)"; + sprite = "TVZPB0"; + } +} + +generic +{ + color = 11; // Light_Cyan + title = "Generic Items & Hazards"; + + 500 + { + title = "Air Bubble Patch"; + sprite = "BUBLE0"; + width = 8; + height = 16; + } + 501 + { + title = "Signpost"; + sprite = "SIGND0"; + width = 8; + height = 32; + } + 502 + { + arrow = 1; + title = "Star Post"; + sprite = "STPTA0M0"; + width = 64; + height = 128; + } + 520 + { + title = "Bomb Sphere"; + sprite = "SPHRD0"; + width = 16; + height = 24; + } + 521 + { + title = "Spikeball"; + sprite = "SPIKA0"; + width = 12; + height = 8; + } + 522 + { + title = "Wall Spike"; + sprite = "WSPKALAR"; + width = 16; + height = 14; + arrow = 1; + } + 523 + { + title = "Spike"; + sprite = "USPKA0"; + width = 8; + height = 32; + } + 1130 + { + title = "Small Mace"; + sprite = "SMCEA0"; + width = 17; + height = 34; + } + 1131 + { + title = "Big Mace"; + sprite = "BMCEA0"; + width = 34; + height = 68; + } + 1136 + { + title = "Small Fireball"; + sprite = "SFBRA0"; + width = 17; + height = 34; + } + 1137 + { + title = "Large Fireball"; + sprite = "BFBRA0"; + width = 34; + height = 68; + } +} + +springs +{ + color = 12; // Light_Red + title = "Springs and Fans"; + width = 20; + height = 16; + sprite = "RSPRD2"; + + 540 + { + title = "Fan"; + sprite = "FANSA0D0"; + width = 16; + height = 8; + } + 541 + { + title = "Gas Jet"; + sprite = "STEMD0"; + width = 32; + } + 542 + { + title = "Bumper"; + sprite = "BUMPA0"; + width = 32; + height = 64; + } + 543 + { + title = "Balloon"; + sprite = "BLONA0"; + width = 32; + height = 64; + } + 550 + { + title = "Yellow Spring"; + sprite = "SPRYA0"; + } + 551 + { + title = "Red Spring"; + sprite = "SPRRA0"; + } + 552 + { + title = "Blue Spring"; + sprite = "SPRBA0"; + } + 555 + { + arrow = 1; + title = "Diagonal Yellow Spring"; + sprite = "YSPRD2"; + width = 16; + } + 556 + { + arrow = 1; + title = "Diagonal Red Spring"; + sprite = "RSPRD2"; + width = 16; + } + 557 + { + arrow = 1; + title = "Diagonal Blue Spring"; + sprite = "BSPRD2"; + width = 16; + } + 558 + { + arrow = 1; + title = "Horizontal Yellow Spring"; + sprite = "SSWYD2D8"; + width = 16; + height = 32; + } + 559 + { + arrow = 1; + title = "Horizontal Red Spring"; + sprite = "SSWRD2D8"; + width = 16; + height = 32; + } + 560 + { + arrow = 1; + title = "Horizontal Blue Spring"; + sprite = "SSWBD2D8"; + width = 16; + height = 32; + } + 1134 + { + title = "Yellow Spring Ball"; + sprite = "YSPBA0"; + width = 17; + height = 34; + } + 1135 + { + title = "Red Spring Ball"; + sprite = "RSPBA0"; + width = 17; + height = 34; + } + 544 + { + arrow = 1; + title = "Yellow Boost Panel"; + sprite = "BSTYA0"; + width = 28; + height = 2; + } + 545 + { + arrow = 1; + title = "Red Boost Panel"; + sprite = "BSTRA0"; + width = 28; + height = 2; + } +} + +patterns +{ + color = 5; // Magenta + arrow = 1; + title = "Special Placement Patterns"; + width = 16; + height = 384; + sprite = "RINGA0"; + + 600 + { + arrow = 0; + title = "5 Vertical Rings (Yellow Spring)"; + sprite = "RINGA0"; + } + 601 + { + arrow = 0; + title = "5 Vertical Rings (Red Spring)"; + sprite = "RINGA0"; + height = 1024; + } + 602 + { + title = "5 Diagonal Rings (Yellow Spring)"; + sprite = "RINGA0"; + height = 32; + } + 603 + { + title = "10 Diagonal Rings (Red Spring)"; + sprite = "RINGA0"; + height = 32; + } + 604 + { + title = "Circle of Rings"; + sprite = "RINGA0"; + width = 96; + height = 192; + } + 605 + { + title = "Circle of Rings (Big)"; + sprite = "RINGA0"; + width = 192; + } + 606 + { + title = "Circle of Blue Spheres"; + sprite = "SPHRA0"; + width = 96; + height = 192; + } + 607 + { + title = "Circle of Blue Spheres (Big)"; + sprite = "SPHRA0"; + width = 192; + } + 608 + { + title = "Circle of Rings and Spheres"; + sprite = "SPHRA0"; + width = 96; + height = 192; + 609 + { + title = "Circle of Rings and Spheres (Big)"; + sprite = "SPHRA0"; + width = 192; + } +} + +invisible +{ + color = 15; // White + title = "Misc. Invisible"; + width = 0; + height = 0; + sprite = "UNKNA0"; + sort = 1; + fixedsize = true; + blocking = 0; + + 700 + { + title = "Water Ambience A (Large)"; + sprite = "internal:ambiance"; + } + + 701 + { + title = "Water Ambience B (Large)"; + sprite = "internal:ambiance"; + } + + 702 + { + title = "Water Ambience C (Medium)"; + sprite = "internal:ambiance"; + } + + 703 + { + title = "Water Ambience D (Medium)"; + sprite = "internal:ambiance"; + } + + 704 + { + title = "Water Ambience E (Small)"; + sprite = "internal:ambiance"; + } + + 705 + { + title = "Water Ambience F (Small)"; + sprite = "internal:ambiance"; + } + + 706 + { + title = "Water Ambience G (Extra Large)"; + sprite = "internal:ambiance"; + } + + 707 + { + title = "Water Ambience H (Extra Large)"; + sprite = "internal:ambiance"; + } + + 708 + { + title = "Disco Ambience"; + sprite = "internal:ambiance"; + } + + 709 + { + title = "Volcano Ambience"; + sprite = "internal:ambiance"; + } + + 710 + { + title = "Machine Ambience"; + sprite = "internal:ambiance"; + } + + 750 + { + title = "Slope Vertex"; + sprite = "internal:vertexslope"; + } + + 751 + { + arrow = 1; + title = "Teleport Destination"; + sprite = "internal:tele"; + } + + 752 + { + arrow = 1; + title = "Alternate View Point"; + sprite = "internal:view"; + } + + 753 + { + title = "Zoom Tube Waypoint"; + sprite = "internal:zoom"; + } + + 754 + { + title = "Push Point"; + sprite = "GWLGA0"; + } + 755 + { + title = "Pull Point"; + sprite = "GWLRA0"; + } + 756 + { + title = "Blast Linedef Executor"; + sprite = "TOADA0"; + width = 32; + height = 16; + } + 757 + { + title = "Fan Particle Generator"; + sprite = "PRTLA0"; + width = 8; + height = 16; + } + 758 + { + title = "Object Angle Anchor"; + sprite = "internal:view"; + } + 760 + { + title = "PolyObject Anchor"; + sprite = "internal:polyanchor"; + } + 761 + { + title = "PolyObject Spawn Point"; + sprite = "internal:polycenter"; + } + 762 + { + title = "PolyObject Spawn Point (Crush)"; + sprite = "internal:polycentercrush"; + } + 780 + { + title = "Skybox View Point"; + sprite = "internal:skyb"; + } +} + +greenflower +{ + color = 10; // Green + title = "Greenflower"; + + 800 + { + title = "GFZ Flower"; + sprite = "FWR1A0"; + width = 16; + height = 40; + } + 801 + { + title = "Sunflower"; + sprite = "FWR2A0"; + width = 16; + height = 96; + } + 802 + { + title = "Budding Flower"; + sprite = "FWR3A0"; + width = 8; + height = 32; + } + 803 + { + title = "Blueberry Bush"; + sprite = "BUS3A0"; + width = 16; + height = 32; + } + 804 + { + title = "Berry Bush"; + sprite = "BUS1A0"; + width = 16; + height = 32; + } + 805 + { + title = "Bush"; + sprite = "BUS2A0"; + width = 16; + height = 32; + } + 806 + { + title = "GFZ Tree"; + sprite = "TRE1A0"; + width = 20; + height = 128; + } + 807 + { + title = "GFZ Berry Tree"; + sprite = "TRE1B0"; + width = 20; + height = 128; + } + 808 + { + title = "GFZ Cherry Tree"; + sprite = "TRE1C0"; + width = 20; + height = 128; + } + 809 + { + title = "Checkered Tree"; + sprite = "TRE2A0"; + width = 20; + height = 200; + } + 810 + { + title = "Checkered Tree (Sunset)"; + sprite = "TRE2B0"; + width = 20; + height = 200; + } + 811 + { + title = "Polygon Tree"; + sprite = "TRE4A0"; + width = 20; + height = 200; + } + 812 + { + title = "Bush Tree"; + sprite = "TRE5A0"; + width = 20; + height = 200; + } + 813 + { + title = "Red Bush Tree"; + sprite = "TRE5B0"; + width = 20; + height = 200; + } +} + +technohill +{ + color = 10; // Green + title = "Techno Hill"; + + 900 + { + title = "THZ Steam Flower"; + sprite = "THZPA0"; + width = 8; + height = 32; + } + 901 + { + title = "Alarm"; + sprite = "ALRMA0"; + width = 8; + height = 16; + hangs = 1; + } + 902 + { + title = "THZ Spin Flower (Red)"; + sprite = "FWR5A0"; + width = 16; + height = 64; + } + 903 + { + title = "THZ Spin Flower (Yellow)"; + sprite = "FWR6A0"; + width = 16; + height = 64; + } + 904 + { + arrow = 1; + title = "Whistlebush"; + sprite = "THZTA0"; + width = 16; + height = 64; + } +} + +deepsea +{ + color = 10; // Green + title = "Deep Sea"; + + 1000 + { + arrow = 1; + blocking = 2; + title = "Gargoyle"; + sprite = "GARGA1"; + width = 16; + height = 40; + } + 1009 + { + arrow = 1; + blocking = 2; + title = "Gargoyle (Big)"; + sprite = "GARGB1"; + width = 32; + height = 80; + } + 1001 + { + title = "Seaweed"; + sprite = "SEWEA0"; + width = 24; + height = 56; + } + 1002 + { + title = "Dripping Water"; + sprite = "DRIPD0"; + width = 8; + height = 16; + hangs = 1; + } + 1003 + { + title = "Coral (Green)"; + sprite = "CORLA0"; + width = 29; + height = 40; + } + 1004 + { + title = "Coral (Red)"; + sprite = "CORLB0"; + width = 30; + height = 53; + } + 1005 + { + title = "Coral (Orange)"; + sprite = "CORLC0"; + width = 28; + height = 41; + } + 1006 + { + title = "Blue Crystal"; + sprite = "BCRYA1"; + width = 8; + height = 16; + } + 1007 + { + title = "Kelp"; + sprite = "KELPA0"; + width = 16; + height = 292; + } + 1008 + { + title = "Stalagmite (DSZ1)"; + sprite = "DSTGA0"; + width = 8; + height = 116; + } + 1010 + { + arrow = 1; + title = "Light Beam"; + sprite = "LIBEARAL"; + width = 16; + height = 16; + } + 1011 + { + title = "Stalagmite (DSZ2)"; + sprite = "DSTGA0"; + width = 8; + height = 116; + } + 1012 + { + arrow = 1; + title = "Big Floating Mine"; + width = 28; + height = 56; + sprite = "BMNEA1"; + } + 1013 + { + title = "Animated Kelp"; + sprite = "ALGAA0"; + width = 48; + height = 120; + } + 1014 + { + title = "Large Coral (Brown)"; + sprite = "CORLD0"; + width = 56; + height = 112; + } + 1015 + { + title = "Large Coral (Beige)"; + sprite = "CORLE0"; + width = 56; + height = 112; + } +} + +castleeggman +{ + color = 10; // Green + title = "Castle Eggman"; + + 1100 + { + title = "Chain (Decorative)"; + sprite = "CHANA0"; + width = 4; + height = 128; + hangs = 1; + } + 1101 + { + title = "Torch"; + sprite = "FLAMA0E0"; + width = 8; + height = 32; + } + 1102 + { + arrow = 1; + blocking = 2; + title = "Eggman Statue"; + sprite = "ESTAA1"; + width = 32; + height = 240; + } + 1103 + { + title = "CEZ Flower"; + sprite = "FWR4A0"; + width = 16; + height = 40; + } + 1104 + { + title = "Mace Spawnpoint"; + sprite = "SMCEA0"; + width = 17; + height = 34; + } + 1105 + { + title = "Chain with Maces Spawnpoint"; + sprite = "SMCEA0"; + width = 17; + height = 34; + } + 1106 + { + title = "Chained Spring Spawnpoint"; + sprite = "YSPBA0"; + width = 17; + height = 34; + } + 1107 + { + title = "Chain Spawnpoint"; + sprite = "BMCHA0"; + width = 17; + height = 34; + } + 1108 + { + arrow = 1; + title = "Hidden Chain Spawnpoint"; + sprite = "internal:chain3"; + width = 17; + height = 34; + } + 1109 + { + title = "Firebar Spawnpoint"; + sprite = "BFBRA0"; + width = 17; + height = 34; + } + 1110 + { + title = "Custom Mace Spawnpoint"; + sprite = "SMCEA0"; + width = 17; + height = 34; + } + 1111 + { + arrow = 1; + blocking = 2; + title = "Crawla Statue"; + sprite = "CSTAA1"; + width = 16; + height = 40; + } + 1112 + { + arrow = 1; + blocking = 2; + title = "Lance-a-Bot Statue"; + sprite = "CBBSA1"; + width = 32; + height = 72; + } + 1114 + { + title = "Pine Tree"; + sprite = "PINEA0"; + width = 16; + height = 628; + } + 1115 + { + title = "CEZ Shrub (Small)"; + sprite = "CEZBA0"; + width = 16; + height = 24; + } + 1116 + { + title = "CEZ Shrub (Large)"; + sprite = "CEZBB0"; + width = 32; + height = 48; + } + 1117 + { + arrow = 1; + title = "Pole Banner (Red)"; + sprite = "BANRA0"; + width = 40; + height = 224; + } + 1118 + { + arrow = 1; + title = "Pole Banner (Blue)"; + sprite = "BANRA0"; + width = 40; + height = 224; + } + 1119 + { + title = "Candle"; + sprite = "CNDLA0"; + width = 8; + height = 48; + } + 1120 + { + title = "Candle Pricket"; + sprite = "CNDLB0"; + width = 8; + height = 176; + } + 1121 + { + title = "Flame Holder"; + sprite = "FLMHA0"; + width = 24; + height = 80; + } + 1122 + { + title = "Fire Torch"; + sprite = "CTRCA0"; + width = 16; + height = 80; + } + 1123 + { + title = "Cannonball Launcher"; + sprite = "internal:cannonball"; + width = 8; + height = 16; + } + 1124 + { + blocking = 2; + title = "Cannonball"; + sprite = "CBLLA0"; + width = 20; + height = 40; + } + 1125 + { + title = "Brambles"; + sprite = "CABRALAR"; + width = 48; + height = 32; + } + 1126 + { + title = "Invisible Lockon Object"; + sprite = "LCKNC0"; + width = 16; + height = 32; + } + 1127 + { + title = "Spectator Eggrobo"; + sprite = "EGR1A1"; + width = 20; + height = 72; + } + 1128 + { + arrow = 1; + title = "Waving Flag (Red)"; + sprite = "CFLGA0"; + width = 8; + height = 208; + } + 1129 + { + arrow = 1; + title = "Waving Flag (Blue)"; + sprite = "CFLGA0"; + width = 8; + height = 208; + } +} + +aridcanyon +{ + color = 10; // Green + title = "Arid Canyon"; + + 1200 + { + title = "Tumbleweed (Big)"; + sprite = "BTBLA0"; + width = 24; + height = 48; + } + 1201 + { + title = "Tumbleweed (Small)"; + sprite = "STBLA0"; + width = 12; + height = 24; + } + 1202 + { + arrow = 1; + title = "Rock Spawner"; + sprite = "ROIAA0"; + width = 8; + height = 16; + } + 1203 + { + title = "Tiny Red Flower Cactus"; + sprite = "CACTA0"; + width = 13; + height = 24; + } + 1204 + { + title = "Small Red Flower Cactus"; + sprite = "CACTB0"; + width = 15; + height = 52; + } + 1205 + { + title = "Tiny Blue Flower Cactus"; + sprite = "CACTC0"; + width = 13; + height = 24; + } + 1206 + { + title = "Small Blue Flower Cactus"; + sprite = "CACTD0"; + width = 15; + height = 52; + } + 1207 + { + title = "Prickly Pear"; + sprite = "CACTE0"; + width = 32; + height = 96; + } + 1208 + { + title = "Barrel Cactus"; + sprite = "CACTF0"; + width = 20; + height = 128; + } + 1209 + { + title = "Tall Barrel Cactus"; + sprite = "CACTG0"; + width = 24; + height = 224; + } + 1210 + { + title = "Armed Cactus"; + sprite = "CACTH0"; + width = 24; + height = 256; + } + 1211 + { + title = "Ball Cactus"; + sprite = "CACTI0"; + width = 48; + height = 96; + } + 1212 + { + title = "Caution Sign"; + sprite = "WWSGAR"; + width = 22; + height = 64; + } + 1213 + { + title = "Cacti Sign"; + sprite = "WWS2AR"; + width = 22; + height = 64; + } + 1214 + { + title = "Sharp Turn Sign"; + sprite = "WWS3ALAR"; + width = 16; + height = 192; + } + 1215 + { + title = "Mine Oil Lamp"; + sprite = "OILLA0"; + width = 22; + height = 64; + hangs = 1; + } + 1216 + { + title = "TNT Barrel"; + sprite = "BARRA1"; + width = 24; + height = 63; + } + 1217 + { + title = "TNT Proximity Shell"; + sprite = "REMTA0"; + width = 64; + height = 40; + } + 1218 + { + title = "Dust Devil"; + sprite = "TAZDCR"; + width = 80; + height = 416; + } + 1219 + { + title = "Minecart Spawner"; + sprite = "MCRTCLFR"; + width = 22; + height = 32; + } + 1220 + { + title = "Minecart Stopper"; + sprite = "MCRTIR"; + width = 32; + height = 32; + } + 1221 + { + title = "Minecart Saloon Door"; + sprite = "SALDARAL"; + width = 96; + height = 160; + } + 1222 + { + title = "Train Cameo Spawner"; + sprite = "TRAEBRBL"; + width = 28; + height = 32; + } + 1223 + { + title = "Train Dust Spawner"; + sprite = "ADSTA0"; + width = 4; + height = 4; + } + 1224 + { + title = "Train Steam Spawner"; + sprite = "STEAA0"; + width = 4; + height = 4; + } + 1229 + { + title = "Minecart Switch Point"; + sprite = "internal:zoom"; + width = 8; + height = 16; + } + 1230 + { + title = "Tiny Cactus"; + sprite = "CACTJ0"; + width = 13; + height = 28; + } + 1231 + { + title = "Small Cactus"; + sprite = "CACTK0"; + width = 15; + height = 60; + } +} + +redvolcano +{ + color = 10; // Green + title = "Red Volcano"; + + 1300 + { + arrow = 1; + title = "Flame Jet (Horizontal)"; + sprite = "internal:flameh"; + width = 16; + height = 40; + } + 1301 + { + title = "Flame Jet (Vertical)"; + sprite = "internal:flamev"; + width = 16; + height = 40; + } + 1302 + { + title = "Spinning Flame Jet (Counter-Clockwise)"; + sprite = "internal:flame2"; + width = 16; + height = 24; + } + 1303 + { + title = "Spinning Flame Jet (Clockwise)"; + sprite = "internal:flame1"; + width = 16; + height = 24; + } + 1304 + { + title = "Lavafall"; + sprite = "LFALF0"; + width = 30; + height = 32; + } + 1305 + { + title = "Rollout Rock"; + sprite = "PUMIA1A5"; + width = 30; + height = 60; + } + 1306 + { + title = "Big Fern"; + sprite = "JPLAB0"; + width = 32; + height = 48; + } + 1307 + { + title = "Jungle Palm"; + sprite = "JPLAC0"; + width = 32; + height = 48; + } + 1308 + { + title = "Torch Flower"; + sprite = "TFLOA0"; + width = 14; + height = 110; + } + 1309 + { + title = "RVZ1 Wall Vine (Long)"; + sprite = "WVINALAR"; + width = 1; + height = 288; + } + 1310 + { + title = "RVZ1 Wall Vine (Short)"; + sprite = "WVINBLBR"; + width = 1; + height = 288; + } +} + +botanicserenity +{ + color = 10; // Green + title = "Botanic Serenity"; + width = 16; + height = 32; + sprite = "BSZ1A0"; + 1400 + { + title = "Tall Flower (Red)"; + sprite = "BSZ1A0"; + } + 1401 + { + title = "Tall Flower (Purple)"; + sprite = "BSZ1B0"; + } + 1402 + { + title = "Tall Flower (Blue)"; + sprite = "BSZ1C0"; + } + 1403 + { + title = "Tall Flower (Cyan)"; + sprite = "BSZ1D0"; + } + 1404 + { + title = "Tall Flower (Yellow)"; + sprite = "BSZ1E0"; + } + 1405 + { + title = "Tall Flower (Orange)"; + sprite = "BSZ1F0"; + } + 1410 + { + title = "Medium Flower (Red)"; + sprite = "BSZ2A0"; + } + 1411 + { + title = "Medium Flower (Purple)"; + sprite = "BSZ2B0"; + } + 1412 + { + title = "Medium Flower (Blue)"; + sprite = "BSZ2C0"; + } + 1413 + { + title = "Medium Flower (Cyan)"; + sprite = "BSZ2D0"; + } + 1414 + { + title = "Medium Flower (Yellow)"; + sprite = "BSZ2E0"; + } + 1415 + { + title = "Medium Flower (Orange)"; + sprite = "BSZ2F0"; + } + 1420 + { + title = "Short Flower (Red)"; + sprite = "BSZ3A0"; + } + 1421 + { + title = "Short Flower (Purple)"; + sprite = "BSZ3B0"; + } + 1422 + { + title = "Short Flower (Blue)"; + sprite = "BSZ3C0"; + } + 1423 + { + title = "Short Flower (Cyan)"; + sprite = "BSZ3D0"; + } + 1424 + { + title = "Short Flower (Yellow)"; + sprite = "BSZ3E0"; + } + 1425 + { + title = "Short Flower (Orange)"; + sprite = "BSZ3F0"; + } + 1430 + { + title = "Tulip (Red)"; + sprite = "BST1A0"; + } + 1431 + { + title = "Tulip (Purple)"; + sprite = "BST2A0"; + } + 1432 + { + title = "Tulip (Blue)"; + sprite = "BST3A0"; + } + 1433 + { + title = "Tulip (Cyan)"; + sprite = "BST4A0"; + } + 1434 + { + title = "Tulip (Yellow)"; + sprite = "BST5A0"; + } + 1435 + { + title = "Tulip (Orange)"; + sprite = "BST6A0"; + } + 1440 + { + title = "Cluster (Red)"; + sprite = "BSZ5A0"; + } + 1441 + { + title = "Cluster (Purple)"; + sprite = "BSZ5B0"; + } + 1442 + { + title = "Cluster (Blue)"; + sprite = "BSZ5C0"; + } + 1443 + { + title = "Cluster (Cyan)"; + sprite = "BSZ5D0"; + } + 1444 + { + title = "Cluster (Yellow)"; + sprite = "BSZ5E0"; + } + 1445 + { + title = "Cluster (Orange)"; + sprite = "BSZ5F0"; + } + 1450 + { + title = "Bush (Red)"; + sprite = "BSZ6A0"; + } + 1451 + { + title = "Bush (Purple)"; + sprite = "BSZ6B0"; + } + 1452 + { + title = "Bush (Blue)"; + sprite = "BSZ6C0"; + } + 1453 + { + title = "Bush (Cyan)"; + sprite = "BSZ6D0"; + } + 1454 + { + title = "Bush (Yellow)"; + sprite = "BSZ6E0"; + } + 1455 + { + title = "Bush (Orange)"; + sprite = "BSZ6F0"; + } + 1460 + { + title = "Vine (Red)"; + sprite = "BSZ7A0"; + } + 1461 + { + title = "Vine (Purple)"; + sprite = "BSZ7B0"; + } + 1462 + { + title = "Vine (Blue)"; + sprite = "BSZ7C0"; + } + 1463 + { + title = "Vine (Cyan)"; + sprite = "BSZ7D0"; + } + 1464 + { + title = "Vine (Yellow)"; + sprite = "BSZ7E0"; + } + 1465 + { + title = "Vine (Orange)"; + sprite = "BSZ7F0"; + } + 1470 + { + title = "BSZ Shrub"; + sprite = "BSZ8A0"; + } + 1471 + { + title = "BSZ Clover"; + sprite = "BSZ8B0"; + } + 1473 + { + title = "Palm Tree (Big)"; + width = 16; + height = 160; + sprite = "BSZ8D0"; + } + 1475 + { + title = "Palm Tree (Small)"; + width = 16; + height = 80; + sprite = "BSZ8F0"; + } +} + +azuretemple +{ + color = 10; // Green + title = "Azure Temple"; + + 1500 + { + arrow = 1; + blocking = 2; + title = "Glaregoyle"; + sprite = "BGARA1"; + width = 16; + height = 40; + } + 1501 + { + arrow = 1; + blocking = 2; + title = "Glaregoyle (Up)"; + sprite = "BGARA1"; + width = 16; + height = 40; + } + 1502 + { + arrow = 1; + blocking = 2; + title = "Glaregoyle (Down)"; + sprite = "BGARA1"; + width = 16; + height = 40; + } + 1503 + { + arrow = 1; + blocking = 2; + title = "Glaregoyle (Long)"; + sprite = "BGARA1"; + width = 16; + height = 40; + } + 1504 + { + title = "ATZ Target"; + sprite = "RCRYB0"; + width = 24; + height = 32; + } + 1505 + { + title = "Green Flame"; + sprite = "CFLMA0E0"; + width = 8; + height = 32; + } + 1506 + { + arrow = 1; + blocking = 2; + title = "Blue Gargoyle"; + sprite = "BGARD1"; + width = 16; + height = 40; + } +} + +dreamhill +{ + color = 10; // Green + title = "Dream Hill"; + + 1600 + { + title = "Spring Tree"; + sprite = "TRE6A0"; + width = 16; + height = 32; + } + 1601 + { + title = "Shleep"; + sprite = "SHLPA0"; + width = 24; + height = 32; + } + 1602 + { + title = "Pian"; + sprite = "NTPNALAR"; + width = 16; + height = 32; + } +} + +nightstrk +{ + color = 13; // Pink + title = "NiGHTS Track"; + width = 8; + height = 4096; + sprite = "UNKNA0"; + + 1700 + { + title = "Axis"; + sprite = "internal:axis1"; + circle = 1; + } + 1701 + { + title = "Axis Transfer"; + sprite = "internal:axis2"; + } + 1702 + { + title = "Axis Transfer Line"; + sprite = "internal:axis3"; + } + 1710 + { + title = "Ideya Capture"; + sprite = "CAPSA0"; + width = 72; + height = 144; + } +} + +nights +{ + color = 13; // Pink + title = "NiGHTS Items"; + width = 16; + height = 32; + + 1703 + { + title = "Ideya Drone"; + sprite = "NDRNA1"; + width = 16; + height = 56; + } + 1704 + { + arrow = 1; + title = "NiGHTS Bumper"; + sprite = "NBMPG3G7"; + width = 32; + height = 64; + } + 1705 + { + arrow = 1; + title = "Hoop (Generic)"; + sprite = "HOOPA0"; + width = 80; + height = 160; + } + 1706 + { + title = "Blue Sphere"; + sprite = "SPHRA0"; + width = 16; + height = 24; + } + 1707 + { + title = "Super Paraloop"; + sprite = "NPRUA0"; + } + 1708 + { + title = "Drill Refill"; + sprite = "NPRUB0"; + } + 1709 + { + title = "Nightopian Helper"; + sprite = "NPRUC0"; + } + 1711 + { + title = "Extra Time"; + sprite = "NPRUD0"; + } + 1712 + { + title = "Link Freeze"; + sprite = "NPRUE0"; + } + 1713 + { + arrow = 1; + title = "Hoop (Customizable)"; + sprite = "HOOPA0"; + width = 80; + height = 160; + } + 1714 + { + title = "Ideya Anchor Point"; + sprite = "internal:axis1"; + width = 8; + height = 16; + } +} + +mario +{ + color = 6; // Brown + title = "Mario"; + + 1800 + { + title = "Coin"; + sprite = "COINA0"; + width = 16; + height = 24; + } + 1801 + { + arrow = 1; + title = "Goomba"; + sprite = "GOOMA0"; + width = 24; + height = 32; + } + 1802 + { + arrow = 1; + title = "Goomba (Blue)"; + sprite = "BGOMA0"; + width = 24; + height = 32; + } + 1803 + { + title = "Fire Flower"; + sprite = "FFWRB0"; + width = 16; + height = 32; + } + 1804 + { + title = "Koopa Shell"; + sprite = "SHLLA1"; + width = 16; + height = 20; + } + 1805 + { + title = "Puma (Jumping Fireball)"; + sprite = "PUMAA0"; + width = 8; + height = 16; + } + 1806 + { + title = "King Bowser"; + sprite = "KOOPA0"; + width = 16; + height = 48; + } + 1807 + { + title = "Axe"; + sprite = "MAXEA0"; + width = 8; + height = 16; + } + 1808 + { + title = "Bush (Short)"; + sprite = "MUS1A0"; + width = 16; + height = 32; + } + 1809 + { + title = "Bush (Tall)"; + sprite = "MUS2A0"; + width = 16; + height = 32; + } + 1810 + { + title = "Toad"; + sprite = "TOADA0"; + width = 8; + height = 32; + } +} + +christmasdisco +{ + color = 10; // Green + title = "Christmas & Disco"; + + 1850 + { + title = "Christmas Pole"; + sprite = "XMS1A0"; + width = 16; + height = 40; + } + 1851 + { + title = "Candy Cane"; + sprite = "XMS2A0"; + width = 8; + height = 32; + } + 1852 + { + blocking = 2; + title = "Snowman"; + sprite = "XMS3A0"; + width = 16; + height = 64; + } + 1853 + { + blocking = 2; + title = "Snowman (With Hat)"; + sprite = "XMS3B0"; + width = 16; + height = 80; + } + 1854 + { + title = "Lamp Post"; + sprite = "XMS4A0"; + width = 8; + height = 120; + } + 1855 + { + title = "Lamp Post (Snow)"; + sprite = "XMS4B0"; + width = 8; + height = 120; + } + 1856 + { + title = "Hanging Star"; + sprite = "XMS5A0"; + width = 4; + height = 80; + hangs = 1; + } + 1857 + { + title = "Berry Bush (Snow)"; + sprite = "BUS1B0"; + width = 16; + height = 32; + } + 1858 + { + title = "Bush (Snow)"; + sprite = "BUS2B0"; + width = 16; + height = 32; + } + 1859 + { + title = "Blueberry Bush (Snow)"; + sprite = "BUS3B0"; + width = 16; + height = 32; + } + 1875 + { + title = "Disco Ball"; + sprite = "DBALA0"; + width = 16; + height = 54; + hangs = 1; + } + 1876 + { + arrow = 1; + blocking = 2; + title = "Eggman Disco Statue"; + sprite = "ESTAB1"; + width = 20; + height = 96; + } +} + +stalagmites +{ + color = 10; // Green + title = "Stalagmites"; + width = 16; + height = 40; + + 1900 + { + title = "Brown Stalagmite (Tall)"; + sprite = "STLGA0"; + width = 16; + height = 40; + } + 1901 + { + title = "Brown Stalagmite"; + sprite = "STLGB0"; + width = 16; + height = 40; + } + 1902 + { + title = "Orange Stalagmite (Tall)"; + sprite = "STLGC0"; + width = 16; + height = 40; + } + 1903 + { + title = "Orange Stalagmite"; + sprite = "STLGD0"; + width = 16; + height = 40; + } + 1904 + { + title = "Red Stalagmite (Tall)"; + sprite = "STLGE0"; + width = 16; + height = 40; + } + 1905 + { + title = "Red Stalagmite"; + sprite = "STLGF0"; + width = 16; + height = 40; + } + 1906 + { + title = "Gray Stalagmite (Tall)"; + sprite = "STLGG0"; + width = 24; + height = 96; + } + 1907 + { + title = "Gray Stalagmite"; + sprite = "STLGH0"; + width = 16; + height = 40; + } + 1908 + { + title = "Blue Stalagmite (Tall)"; + sprite = "STLGI0"; + width = 16; + height = 40; + } + 1909 + { + title = "Blue Stalagmite"; + sprite = "STLGJ0"; + width = 16; + height = 40; + } +} + +hauntedheights +{ + color = 10; // Green + title = "Haunted Heights"; + + 2000 + { + title = "Smashing Spikeball"; + sprite = "FMCEA0"; + width = 18; + height = 28; + } + 2001 + { + title = "HHZ Grass"; + sprite = "HHZMA0"; + width = 16; + height = 40; + } + 2002 + { + title = "HHZ Tentacle 1"; + sprite = "HHZMB0"; + width = 16; + height = 40; + } + 2003 + { + title = "HHZ Tentacle 2"; + sprite = "HHZMC0"; + width = 16; + height = 40; + } + 2004 + { + title = "HHZ Stalagmite (Tall)"; + sprite = "HHZME0"; + width = 16; + height = 40; + } + 2005 + { + title = "HHZ Stalagmite (Short)"; + sprite = "HHZMF0"; + width = 16; + height = 40; + } + 2006 + { + title = "Jack-o'-lantern 1"; + sprite = "PUMKA0"; + width = 16; + height = 40; + } + 2007 + { + title = "Jack-o'-lantern 2"; + sprite = "PUMKB0"; + width = 16; + height = 40; + } + 2008 + { + title = "Jack-o'-lantern 3"; + sprite = "PUMKC0"; + width = 16; + height = 40; + } + 2009 + { + title = "Purple Mushroom"; + sprite = "SHRMD0"; + width = 16; + height = 48; + } + 2010 + { + title = "HHZ Tree"; + sprite = "HHPLC0"; + width = 12; + height = 40; + } +} + +frozenhillside +{ + color = 10; // Green + title = "Frozen Hillside"; + + 2100 + { + title = "Ice Shard (Small)"; + sprite = "FHZIA0"; + width = 8; + height = 32; + } + 2101 + { + title = "Ice Shard (Large)"; + sprite = "FHZIB0"; + width = 8; + height = 32; + } + 2102 + { + title = "Crystal Tree (Aqua)"; + sprite = "TRE3A0"; + width = 20; + height = 200; + } + 2103 + { + title = "Crystal Tree (Pink)"; + sprite = "TRE3B0"; + width = 20; + height = 200; + } + 2104 + { + title = "Amy Cameo"; + sprite = "ROSYA1"; + width = 16; + height = 48; + } + 2105 + { + title = "Mistletoe"; + sprite = "XMS6A0"; + width = 52; + height = 106; + } +} + +flickies +{ + color = 10; // Green + title = "Flickies"; + width = 8; + height = 20; + + 2200 + { + title = "Bluebird"; + sprite = "FL01A1"; + } + 2201 + { + title = "Rabbit"; + sprite = "FL02A1"; + } + 2202 + { + title = "Chicken"; + sprite = "FL03A1"; + } + 2203 + { + title = "Seal"; + sprite = "FL04A1"; + } + 2204 + { + title = "Pig"; + sprite = "FL05A1"; + } + 2205 + { + title = "Chipmunk"; + sprite = "FL06A1"; + } + 2206 + { + title = "Penguin"; + sprite = "FL07A1"; + } + 2207 + { + title = "Fish"; + sprite = "FL08A1"; + } + 2208 + { + title = "Ram"; + sprite = "FL09A1"; + } + 2209 + { + title = "Puffin"; + sprite = "FL10A1"; + } + 2210 + { + title = "Cow"; + sprite = "FL11A1"; + } + 2211 + { + title = "Rat"; + sprite = "FL12A1"; + } + 2212 + { + title = "Bear"; + sprite = "FL13A1"; + } + 2213 + { + title = "Dove"; + sprite = "FL14A1"; + } + 2214 + { + title = "Cat"; + sprite = "FL15A1"; + } + 2215 + { + title = "Canary"; + sprite = "FL16A1"; + } + 2216 + { + title = "Spider"; + sprite = "FS01A1"; + } + 2217 + { + title = "Bat"; + sprite = "FS02A0"; + } +} \ No newline at end of file diff --git a/extras/conf/udb/SRB2_22Doom.cfg b/extras/conf/udb/SRB2_22Doom.cfg new file mode 100644 index 000000000..891b9d507 --- /dev/null +++ b/extras/conf/udb/SRB2_22Doom.cfg @@ -0,0 +1,38 @@ +/************************************************************************\ + Ultimate Doom Builder Game Configuration for Sonic Robo Blast 2 Version 2.2 +\************************************************************************/ + +// This is required to prevent accidental use of a different configuration +type = "Doom Builder 2 Game Configuration"; + +// This is the title to show for this game +game = "Sonic Robo Blast 2 - 2.2 (Doom format)"; + +// This is the simplified game engine/sourceport name +engine = "zdoom"; + +// Settings common to all games and all map formats +include("Includes\\SRB222_common.cfg", "common"); + +// Settings common to Doom map format +include("Includes\\SRB222_common.cfg", "mapformat_doom"); + +include("Includes\\Game_SRB222.cfg"); + +// Script lumps detection +scriptlumpnames +{ + include("Includes\\SRB222_misc.cfg", "scriptlumpnames"); +} + +// THING TYPES +thingtypes +{ + include("Includes\\SRB222_things.cfg"); +} + +//Default things filters +thingsfilters +{ + include("Includes\\SRB222_misc.cfg", "thingsfilters"); +} \ No newline at end of file diff --git a/extras/conf/udb/SRB2_22UDMF.cfg b/extras/conf/udb/SRB2_22UDMF.cfg new file mode 100644 index 000000000..749cf499a --- /dev/null +++ b/extras/conf/udb/SRB2_22UDMF.cfg @@ -0,0 +1,47 @@ +/************************************************************************\ + Ultimate Doom Builder Game Configuration for Sonic Robo Blast 2 Version 2.2 +\************************************************************************/ + +// This is required to prevent accidental use of a different configuration +type = "Doom Builder 2 Game Configuration"; + +// This is the title to show for this game +game = "Sonic Robo Blast 2 - 2.2 (UDMF)"; + +// This is the simplified game engine/sourceport name +engine = "zdoom"; + +// Settings common to all games and all map formats +include("Includes\\SRB222_common.cfg", "common"); + +// Settings common to text map format +include("Includes\\SRB222_common.cfg", "mapformat_udmf"); + +include("Includes\\Game_SRB222.cfg"); + +// Script lumps detection +scriptlumpnames +{ + include("Includes\\SRB222_misc.cfg", "scriptlumpnames"); +} + +// THING TYPES +thingtypes +{ + include("Includes\\SRB222_things.cfg"); +} + +//Default things filters +thingsfilters +{ + include("Includes\\SRB222_misc.cfg", "thingsfilters"); +} + +// ENUMERATIONS +// Each engine has its own additional thing types +// These are enumerated lists for linedef types and UDMF fields. +enums +{ + // Basic game enums + include("Includes\\SRB222_misc.cfg", "enums"); +} \ No newline at end of file diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 2823eadba..d3fde6c2e 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -228,6 +228,12 @@ set(SRB2_CONFIG_HAVE_OPENMPT ON CACHE BOOL "Enable OpenMPT support.") set(SRB2_CONFIG_HAVE_CURL ON CACHE BOOL "Enable curl support, used for downloading files via HTTP.") +if(${CMAKE_SYSTEM} MATCHES Windows) + set(SRB2_CONFIG_HAVE_MIXERX ON CACHE BOOL + "Enable SDL Mixer X support.") +else() + set(SRB2_CONFIG_HAVE_MIXERX OFF) +endif() set(SRB2_CONFIG_HWRENDER ON CACHE BOOL "Enable hardware rendering through OpenGL.") set(SRB2_CONFIG_USEASM OFF CACHE BOOL @@ -368,6 +374,30 @@ if(${SRB2_CONFIG_HAVE_OPENMPT}) endif() endif() +if(${SRB2_CONFIG_HAVE_MIXERX}) + if(${SRB2_CONFIG_USE_INTERNAL_LIBRARIES}) + set(MIXERX_FOUND ON) + set(MIXERX_INCLUDE_DIRS ${CMAKE_SOURCE_DIR}/libs/SDLMixerX/i686-w64-mingw32/include/SDL2) + if(${SRB2_SYSTEM_BITS} EQUAL 64) + set(MIXERX_LIBRARIES "-L${CMAKE_SOURCE_DIR}/libs/SDLMixerX/x86_64-w64-mingw32/lib -lSDL2_mixer_ext") + else() # 32-bit + set(MIXERX_LIBRARIES "-L${CMAKE_SOURCE_DIR}/libs/SDLMixerX/i686-w64-mingw32/lib -lSDL2_mixer_ext") + endif() + else() + # No support for non-Windows (yet?) + #find_package(MIXERX) + message(WARNING "SDL Mixer X is not supported as an external library.") + set(MIXERX_FOUND OFF) + endif() + if(${MIXERX_FOUND}) + set(SRB2_HAVE_MIXERX ON) + set(SRB2_SDL2_SOUNDIMPL mixer_sound.c) + add_definitions(-DHAVE_MIXERX) + else() + message(WARNING "You have specified that SDL Mixer X is available but it was not found.") + endif() +endif() + if(${SRB2_CONFIG_HAVE_ZLIB}) if(${SRB2_CONFIG_USE_INTERNAL_LIBRARIES}) set(ZLIB_FOUND ON) @@ -515,6 +545,27 @@ endif() # Targets +# If using CCACHE, then force it. +# https://github.com/Cockatrice/Cockatrice/pull/3052/files +if (${CMAKE_SYSTEM} MATCHES "Darwin") + get_property(RULE_LAUNCH_COMPILE GLOBAL PROPERTY RULE_LAUNCH_COMPILE) + if(RULE_LAUNCH_COMPILE) + MESSAGE(STATUS "Force enabling CCache usage under macOS") + # Set up wrapper scripts + configure_file(${CMAKE_CURRENT_SOURCE_DIR}/../cmake/launch-c.in ${CMAKE_BINARY_DIR}/launch-c) + configure_file(${CMAKE_CURRENT_SOURCE_DIR}/../cmake/launch-cxx.in ${CMAKE_BINARY_DIR}/launch-cxx) + execute_process(COMMAND chmod a+rx + "${CMAKE_BINARY_DIR}/launch-c" + "${CMAKE_BINARY_DIR}/launch-cxx") + + # Set Xcode project attributes to route compilation through our scripts + set(CMAKE_XCODE_ATTRIBUTE_CC "${CMAKE_BINARY_DIR}/launch-c") + set(CMAKE_XCODE_ATTRIBUTE_CXX "${CMAKE_BINARY_DIR}/launch-cxx") + set(CMAKE_XCODE_ATTRIBUTE_LD "${CMAKE_BINARY_DIR}/launch-c") + set(CMAKE_XCODE_ATTRIBUTE_LDPLUSPLUS "${CMAKE_BINARY_DIR}/launch-cxx") + endif() +endif() + # Compatibility flag with later versions of GCC # We should really fix our code to not need this if ("${CMAKE_CXX_COMPILER_ID}" STREQUAL "GNU") diff --git a/src/Makefile.cfg b/src/Makefile.cfg index 4a2c0687b..5c56978e7 100644 --- a/src/Makefile.cfg +++ b/src/Makefile.cfg @@ -12,14 +12,15 @@ # to avoid a false positive with the version detection... SUPPORTED_GCC_VERSIONS:=\ - 91\ - 81 82 83\ - 71 72\ + 101 102\ + 91 92 93\ + 81 82 83 84\ + 71 72 73 74 75\ 61 62 63 64\ - 51 52 53 54\ + 51 52 53 54 55\ 40 41 42 43 44 45 46 47 48 49 -LATEST_GCC_VERSION=9.1 +LATEST_GCC_VERSION=10.2 # gcc or g++ ifdef PREFIX @@ -68,7 +69,27 @@ ifeq (,$(filter GCC%,$(.VARIABLES))) endif endif +ifdef GCC102 +GCC101=1 +endif + +ifdef GCC101 +GCC93=1 +endif + +ifdef GCC93 +GCC92=1 +endif + +ifdef GCC92 +GCC91=1 +endif + ifdef GCC91 +GCC84=1 +endif + +ifdef GCC84 GCC83=1 endif @@ -81,6 +102,18 @@ GCC81=1 endif ifdef GCC81 +GCC75=1 +endif + +ifdef GCC75 +GCC74=1 +endif + +ifdef GCC74 +GCC73=1 +endif + +ifdef GCC73 GCC72=1 endif @@ -105,6 +138,10 @@ GCC61=1 endif ifdef GCC61 +GCC55=1 +endif + +ifdef GCC55 GCC54=1 endif diff --git a/src/command.c b/src/command.c index 4973812e7..0a46839f3 100644 --- a/src/command.c +++ b/src/command.c @@ -33,6 +33,7 @@ #include "p_setup.h" #include "lua_script.h" #include "d_netfil.h" // findfile +#include "r_data.h" // Color_cons_t //======== // protos. @@ -818,6 +819,18 @@ static void COM_Help_f(void) CONS_Printf(" Yes or No (On or Off, 1 or 0)\n"); else if (cvar->PossibleValue == CV_OnOff) CONS_Printf(" On or Off (Yes or No, 1 or 0)\n"); + else if (cvar->PossibleValue == Color_cons_t) + { + for (i = 1; i < numskincolors; ++i) + { + if (skincolors[i].accessible) + { + CONS_Printf(" %-2d : %s\n", i, skincolors[i].name); + if (i == cvar->value) + cvalue = skincolors[i].name; + } + } + } else { #define MINVAL 0 diff --git a/src/d_clisrv.c b/src/d_clisrv.c index c4e127e5e..7ccb4ef92 100644 --- a/src/d_clisrv.c +++ b/src/d_clisrv.c @@ -3664,6 +3664,9 @@ static void Got_KickCmd(UINT8 **p, INT32 playernum) CL_RemovePlayer(pnum, kickreason); } +static CV_PossibleValue_t netticbuffer_cons_t[] = {{0, "MIN"}, {3, "MAX"}, {0, NULL}}; +consvar_t cv_netticbuffer = {"netticbuffer", "1", CV_SAVE, netticbuffer_cons_t, NULL, 0, NULL, NULL, 0, 0, NULL}; + consvar_t cv_allownewplayer = {"allowjoin", "On", CV_NETVAR, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL }; consvar_t cv_joinnextround = {"joinnextround", "Off", CV_NETVAR, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL}; /// \todo not done static CV_PossibleValue_t maxplayers_cons_t[] = {{2, "MIN"}, {32, "MAX"}, {0, NULL}}; @@ -5428,6 +5431,10 @@ void TryRunTics(tic_t realtics) ExtraDataTicker(); gametic++; consistancy[gametic%BACKUPTICS] = Consistancy(); + + // Leave a certain amount of tics present in the net buffer as long as we've ran at least one tic this frame. + if (client && gamestate == GS_LEVEL && leveltime > 3 && neededtic <= gametic + cv_netticbuffer.value) + break; } } } diff --git a/src/d_clisrv.h b/src/d_clisrv.h index 44e0cca11..ce8d87adb 100644 --- a/src/d_clisrv.h +++ b/src/d_clisrv.h @@ -542,7 +542,7 @@ extern UINT32 realpingtable[MAXPLAYERS]; extern UINT32 playerpingtable[MAXPLAYERS]; extern tic_t servermaxping; -extern consvar_t cv_allownewplayer, cv_joinnextround, cv_maxplayers, cv_joindelay, cv_rejointimeout; +extern consvar_t cv_netticbuffer, cv_allownewplayer, cv_joinnextround, cv_maxplayers, cv_joindelay, cv_rejointimeout; extern consvar_t cv_resynchattempts, cv_blamecfail; extern consvar_t cv_maxsend, cv_noticedownload, cv_downloadspeed; diff --git a/src/d_netcmd.c b/src/d_netcmd.c index 592734067..6aa168aa7 100644 --- a/src/d_netcmd.c +++ b/src/d_netcmd.c @@ -701,6 +701,7 @@ void D_RegisterClientCommands(void) #endif CV_RegisterVar(&cv_rollingdemos); CV_RegisterVar(&cv_netstat); + CV_RegisterVar(&cv_netticbuffer); #ifdef NETGAME_DEVMODE CV_RegisterVar(&cv_fishcake); diff --git a/src/dehacked.c b/src/dehacked.c index d02dc3d24..9d6729dc2 100644 --- a/src/dehacked.c +++ b/src/dehacked.c @@ -806,8 +806,43 @@ static void readskincolor(MYFILE *f, INT32 num) if (fastcmp(word, "NAME")) { - deh_strlcpy(skincolors[num].name, word2, - sizeof (skincolors[num].name), va("Skincolor %d: name", num)); + size_t namesize = sizeof(skincolors[num].name); + char truncword[namesize]; + UINT16 dupecheck; + + deh_strlcpy(truncword, word2, namesize, va("Skincolor %d: name", num)); // truncate here to check for dupes + dupecheck = R_GetColorByName(truncword); + if (truncword[0] != '\0' && (!stricmp(truncword, skincolors[SKINCOLOR_NONE].name) || (dupecheck && dupecheck != num))) + { + size_t lastchar = strlen(truncword); + char oldword[lastchar+1]; + char dupenum = '1'; + + strlcpy(oldword, truncword, lastchar+1); + lastchar--; + if (lastchar == namesize-2) // exactly max length, replace last character with 0 + truncword[lastchar] = '0'; + else // append 0 + { + strcat(truncword, "0"); + lastchar++; + } + + while (R_GetColorByName(truncword)) + { + truncword[lastchar] = dupenum; + if (dupenum == '9') + dupenum = 'A'; + else if (dupenum == 'Z') // give up :? + break; + else + dupenum++; + } + + deh_warning("Skincolor %d: name %s is a duplicate of another skincolor's name - renamed to %s", num, oldword, truncword); + } + + strlcpy(skincolors[num].name, truncword, namesize); // already truncated } else if (fastcmp(word, "RAMP")) { @@ -818,10 +853,15 @@ static void readskincolor(MYFILE *f, INT32 num) if ((tmp = strtok(NULL,",")) == NULL) break; } + skincolor_modified[num] = true; } else if (fastcmp(word, "INVCOLOR")) { - skincolors[num].invcolor = (UINT16)get_number(word2); + UINT16 v = (UINT16)get_number(word2); + if (v < numskincolors) + skincolors[num].invcolor = v; + else + skincolors[num].invcolor = SKINCOLOR_GREEN; } else if (fastcmp(word, "INVSHADE")) { @@ -4688,11 +4728,11 @@ static void DEH_LoadDehackedFile(MYFILE *f, boolean mainfile) { if (i == 0 && word2[0] != '0') // If word2 isn't a number i = get_skincolor(word2); // find a skincolor by name - if (i < numskincolors && i >= (INT32)SKINCOLOR_FIRSTFREESLOT) + if (i && i < numskincolors) readskincolor(f, i); else { - deh_warning("Skincolor %d out of range (%d - %d)", i, SKINCOLOR_FIRSTFREESLOT, numskincolors-1); + deh_warning("Skincolor %d out of range (1 - %d)", i, numskincolors-1); ignorelines(f); } } @@ -8900,7 +8940,6 @@ static const char *const MOBJTYPE_LIST[] = { // array length left dynamic for s "MT_ANGLEMAN", "MT_POLYANCHOR", "MT_POLYSPAWN", - "MT_POLYSPAWNCRUSH", // Skybox objects "MT_SKYBOX", @@ -10628,7 +10667,7 @@ static inline int lib_freeslot(lua_State *L) CONS_Printf("State S_%s allocated.\n",word); FREE_STATES[i] = Z_Malloc(strlen(word)+1, PU_STATIC, NULL); strcpy(FREE_STATES[i],word); - lua_pushinteger(L, i); + lua_pushinteger(L, S_FIRSTFREESLOT + i); r++; break; } @@ -10643,7 +10682,7 @@ static inline int lib_freeslot(lua_State *L) CONS_Printf("MobjType MT_%s allocated.\n",word); FREE_MOBJS[i] = Z_Malloc(strlen(word)+1, PU_STATIC, NULL); strcpy(FREE_MOBJS[i],word); - lua_pushinteger(L, i); + lua_pushinteger(L, MT_FIRSTFREESLOT + i); r++; break; } @@ -10659,7 +10698,7 @@ static inline int lib_freeslot(lua_State *L) FREE_SKINCOLORS[i] = Z_Malloc(strlen(word)+1, PU_STATIC, NULL); strcpy(FREE_SKINCOLORS[i],word); M_AddMenuColor(numskincolors++); - lua_pushinteger(L, i); + lua_pushinteger(L, SKINCOLOR_FIRSTFREESLOT + i); r++; break; } @@ -10680,11 +10719,12 @@ static inline int lib_freeslot(lua_State *L) CONS_Printf("Sprite SPR2_%s allocated.\n",word); strncpy(spr2names[free_spr2],word,4); spr2defaults[free_spr2] = 0; + lua_pushinteger(L, free_spr2); + r++; spr2names[free_spr2++][4] = 0; } else CONS_Alert(CONS_WARNING, "Ran out of free SPR2 slots!\n"); } - r++; } else if (fastcmp(type, "TOL")) { diff --git a/src/doomdata.h b/src/doomdata.h index 77ed56bc2..f3890c846 100644 --- a/src/doomdata.h +++ b/src/doomdata.h @@ -23,6 +23,8 @@ // Some global defines, that configure the game. #include "doomdef.h" +#include "m_fixed.h" // See the mapthing_t scale. + // // Map level types. // The following data structures define the persistent format @@ -193,16 +195,24 @@ typedef struct #pragma pack() #endif +#define NUMMAPTHINGARGS 6 +#define NUMMAPTHINGSTRINGARGS 2 + // Thing definition, position, orientation and type, // plus visibility flags and attributes. typedef struct { INT16 x, y; - INT16 angle; + INT16 angle, pitch, roll; UINT16 type; UINT16 options; INT16 z; UINT8 extrainfo; + fixed_t scale; + INT16 tag; + INT32 args[NUMMAPTHINGARGS]; + char *stringargs[NUMMAPTHINGSTRINGARGS]; + struct mobj_s *mobj; } mapthing_t; diff --git a/src/g_demo.c b/src/g_demo.c index 6c58f12fb..57a955cb1 100644 --- a/src/g_demo.c +++ b/src/g_demo.c @@ -2382,9 +2382,12 @@ static void WriteDemoChecksum(void) static void G_StopDemoRecording(void) { boolean saved = false; - WRITEUINT8(demo_p, DEMOMARKER); // add the demo end marker - WriteDemoChecksum(); - saved = FIL_WriteFile(va(pandf, srb2home, demoname), demobuffer, demo_p - demobuffer); // finally output the file. + if (demo_p) + { + WRITEUINT8(demo_p, DEMOMARKER); // add the demo end marker + WriteDemoChecksum(); + saved = FIL_WriteFile(va(pandf, srb2home, demoname), demobuffer, demo_p - demobuffer); // finally output the file. + } free(demobuffer); demorecording = false; diff --git a/src/g_game.c b/src/g_game.c index cce4ac822..e165d5415 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -2013,7 +2013,9 @@ boolean G_Responder(event_t *ev) if (F_CreditResponder(ev)) { // Skip credits for everyone - if (!netgame || server || IsPlayerAdmin(consoleplayer)) + if (! serverrunning)/* hahahahahaha */ + F_StartGameEvaluation(); + else if (server || IsPlayerAdmin(consoleplayer)) SendNetXCmd(XD_EXITLEVEL, NULL, 0); return true; } diff --git a/src/hardware/hw_main.c b/src/hardware/hw_main.c index 0d7404c77..ddc935f0d 100644 --- a/src/hardware/hw_main.c +++ b/src/hardware/hw_main.c @@ -214,6 +214,9 @@ void HWR_Lighting(FSurfaceInfo *Surface, INT32 light_level, extracolormap_t *col poly_color.s.blue = (UINT8)blue; } + // Clamp the light level, since it can sometimes go out of the 0-255 range from animations + light_level = min(max(light_level, 0), 255); + Surface->PolyColor.rgba = poly_color.rgba; Surface->TintColor.rgba = tint_color.rgba; Surface->FadeColor.rgba = fade_color.rgba; @@ -491,7 +494,7 @@ static void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, bool if (angle) // Only needs to be done if there's an altered angle { - angle = (InvAngle(angle)+ANGLE_180)>>ANGLETOFINESHIFT; + angle = (InvAngle(angle))>>ANGLETOFINESHIFT; // This needs to be done so that it scrolls in a different direction after rotation like software /*tempxsow = FLOAT_TO_FIXED(scrollx); @@ -525,8 +528,6 @@ static void HWR_RenderPlane(subsector_t *subsector, extrasubsector_t *xsub, bool {\ tempxsow = FLOAT_TO_FIXED(vert->s);\ tempytow = FLOAT_TO_FIXED(vert->t);\ - if (texflat)\ - tempytow = -tempytow;\ vert->s = (FIXED_TO_FLOAT(FixedMul(tempxsow, FINECOSINE(angle)) - FixedMul(tempytow, FINESINE(angle))));\ vert->t = (FIXED_TO_FLOAT(FixedMul(tempxsow, FINESINE(angle)) + FixedMul(tempytow, FINECOSINE(angle))));\ }\ @@ -770,6 +771,7 @@ FBITFIELD HWR_TranstableToAlpha(INT32 transtablenum, FSurfaceInfo *pSurf) { switch (transtablenum) { + case 0 : pSurf->PolyColor.s.alpha = 0x00;return PF_Masked; case tr_trans10 : pSurf->PolyColor.s.alpha = 0xe6;return PF_Translucent; case tr_trans20 : pSurf->PolyColor.s.alpha = 0xcc;return PF_Translucent; case tr_trans30 : pSurf->PolyColor.s.alpha = 0xb3;return PF_Translucent; @@ -1438,37 +1440,10 @@ static void HWR_ProcessSeg(void) // Sort of like GLWall::Process in GZDoom wallVerts[1].y = FIXED_TO_FLOAT(l); } - // set alpha for transparent walls (new boom and legacy linedef types) + // set alpha for transparent walls // ooops ! this do not work at all because render order we should render it in backtofront order switch (gl_linedef->special) { - case 900: - blendmode = HWR_TranstableToAlpha(tr_trans10, &Surf); - break; - case 901: - blendmode = HWR_TranstableToAlpha(tr_trans20, &Surf); - break; - case 902: - blendmode = HWR_TranstableToAlpha(tr_trans30, &Surf); - break; - case 903: - blendmode = HWR_TranstableToAlpha(tr_trans40, &Surf); - break; - case 904: - blendmode = HWR_TranstableToAlpha(tr_trans50, &Surf); - break; - case 905: - blendmode = HWR_TranstableToAlpha(tr_trans60, &Surf); - break; - case 906: - blendmode = HWR_TranstableToAlpha(tr_trans70, &Surf); - break; - case 907: - blendmode = HWR_TranstableToAlpha(tr_trans80, &Surf); - break; - case 908: - blendmode = HWR_TranstableToAlpha(tr_trans90, &Surf); - break; // Translucent case 102: case 121: @@ -1489,7 +1464,10 @@ static void HWR_ProcessSeg(void) // Sort of like GLWall::Process in GZDoom blendmode = PF_Translucent; break; default: - blendmode = PF_Masked; + if (gl_linedef->alpha >= 0 && gl_linedef->alpha < FRACUNIT) + blendmode = HWR_TranstableToAlpha(R_GetLinedefTransTable(gl_linedef->alpha), &Surf); + else + blendmode = PF_Masked; break; } @@ -2280,8 +2258,8 @@ static void HWR_AddLine(seg_t * line) v2y = FLOAT_TO_FIXED(((polyvertex_t *)gl_curline->pv2)->y); // OPTIMIZE: quickly reject orthogonal back sides. - angle1 = R_PointToAngle(v1x, v1y); - angle2 = R_PointToAngle(v2x, v2y); + angle1 = R_PointToAngle64(v1x, v1y); + angle2 = R_PointToAngle64(v2x, v2y); #ifdef NEWCLIP // PrBoom: Back side, i.e. backface culling - read: endAngle >= startAngle! @@ -2574,8 +2552,8 @@ static boolean HWR_CheckBBox(fixed_t *bspcoord) py2 = bspcoord[checkcoord[boxpos][3]]; #ifdef NEWCLIP - angle1 = R_PointToAngle(px1, py1); - angle2 = R_PointToAngle(px2, py2); + angle1 = R_PointToAngle64(px1, py1); + angle2 = R_PointToAngle64(px2, py2); return gld_clipper_SafeCheckRange(angle2, angle1); #else // check clip list for an open space @@ -2757,8 +2735,11 @@ static void HWR_RenderPolyObjectPlane(polyobj_t *polysector, boolean isceiling, HWR_SetCurrentTexture(NULL); // reference point for flat texture coord for each vertex around the polygon - flatxref = (float)((polysector->origVerts[0].x & (~flatflag)) / fflatwidth); - flatyref = (float)((polysector->origVerts[0].y & (~flatflag)) / fflatheight); + flatxref = FIXED_TO_FLOAT(polysector->origVerts[0].x); + flatyref = FIXED_TO_FLOAT(polysector->origVerts[0].y); + + flatxref = (float)(((fixed_t)flatxref & (~flatflag)) / fflatwidth); + flatyref = (float)(((fixed_t)flatyref & (~flatflag)) / fflatheight); // transform v3d = planeVerts; @@ -2769,13 +2750,13 @@ static void HWR_RenderPolyObjectPlane(polyobj_t *polysector, boolean isceiling, { scrollx = FIXED_TO_FLOAT(FOFsector->floor_xoffs)/fflatwidth; scrolly = FIXED_TO_FLOAT(FOFsector->floor_yoffs)/fflatheight; - angle = FOFsector->floorpic_angle>>ANGLETOFINESHIFT; + angle = FOFsector->floorpic_angle; } else // it's a ceiling { scrollx = FIXED_TO_FLOAT(FOFsector->ceiling_xoffs)/fflatwidth; scrolly = FIXED_TO_FLOAT(FOFsector->ceiling_yoffs)/fflatheight; - angle = FOFsector->ceilingpic_angle>>ANGLETOFINESHIFT; + angle = FOFsector->ceilingpic_angle; } } else if (gl_frontsector) @@ -2784,23 +2765,25 @@ static void HWR_RenderPolyObjectPlane(polyobj_t *polysector, boolean isceiling, { scrollx = FIXED_TO_FLOAT(gl_frontsector->floor_xoffs)/fflatwidth; scrolly = FIXED_TO_FLOAT(gl_frontsector->floor_yoffs)/fflatheight; - angle = gl_frontsector->floorpic_angle>>ANGLETOFINESHIFT; + angle = gl_frontsector->floorpic_angle; } else // it's a ceiling { scrollx = FIXED_TO_FLOAT(gl_frontsector->ceiling_xoffs)/fflatwidth; scrolly = FIXED_TO_FLOAT(gl_frontsector->ceiling_yoffs)/fflatheight; - angle = gl_frontsector->ceilingpic_angle>>ANGLETOFINESHIFT; + angle = gl_frontsector->ceilingpic_angle; } } if (angle) // Only needs to be done if there's an altered angle { + angle = (InvAngle(angle))>>ANGLETOFINESHIFT; + // This needs to be done so that it scrolls in a different direction after rotation like software - tempxs = FLOAT_TO_FIXED(scrollx); + /*tempxs = FLOAT_TO_FIXED(scrollx); tempyt = FLOAT_TO_FIXED(scrolly); scrollx = (FIXED_TO_FLOAT(FixedMul(tempxs, FINECOSINE(angle)) - FixedMul(tempyt, FINESINE(angle)))); - scrolly = (FIXED_TO_FLOAT(FixedMul(tempxs, FINESINE(angle)) + FixedMul(tempyt, FINECOSINE(angle)))); + scrolly = (FIXED_TO_FLOAT(FixedMul(tempxs, FINESINE(angle)) + FixedMul(tempyt, FINECOSINE(angle))));*/ // This needs to be done so everything aligns after rotation // It would be done so that rotation is done, THEN the translation, but I couldn't get it to rotate AND scroll like software does @@ -2830,10 +2813,8 @@ static void HWR_RenderPolyObjectPlane(polyobj_t *polysector, boolean isceiling, { tempxs = FLOAT_TO_FIXED(v3d->s); tempyt = FLOAT_TO_FIXED(v3d->t); - if (texflat) - tempyt = -tempyt; v3d->s = (FIXED_TO_FLOAT(FixedMul(tempxs, FINECOSINE(angle)) - FixedMul(tempyt, FINESINE(angle)))); - v3d->t = (FIXED_TO_FLOAT(-FixedMul(tempxs, FINESINE(angle)) - FixedMul(tempyt, FINECOSINE(angle)))); + v3d->t = (FIXED_TO_FLOAT(FixedMul(tempxs, FINESINE(angle)) + FixedMul(tempyt, FINECOSINE(angle)))); } v3d->x = FIXED_TO_FLOAT(polysector->vertices[i]->x); diff --git a/src/hardware/r_opengl/r_opengl.c b/src/hardware/r_opengl/r_opengl.c index 08d688e1d..461966224 100644 --- a/src/hardware/r_opengl/r_opengl.c +++ b/src/hardware/r_opengl/r_opengl.c @@ -678,6 +678,29 @@ static INT32 shader_leveltime = 0; "gl_FragColor = final_color;\n" \ "}\0" +// same as above but multiplies results with the lighting value from the +// accompanying vertex shader (stored in gl_Color) +#define GLSL_SOFTWARE_MODEL_LIGHTING_FRAGMENT_SHADER \ + "uniform sampler2D tex;\n" \ + "uniform vec4 poly_color;\n" \ + "uniform vec4 tint_color;\n" \ + "uniform vec4 fade_color;\n" \ + "uniform float lighting;\n" \ + "uniform float fade_start;\n" \ + "uniform float fade_end;\n" \ + GLSL_DOOM_COLORMAP \ + GLSL_DOOM_LIGHT_EQUATION \ + "void main(void) {\n" \ + "vec4 texel = texture2D(tex, gl_TexCoord[0].st);\n" \ + "vec4 base_color = texel * poly_color;\n" \ + "vec4 final_color = base_color;\n" \ + GLSL_SOFTWARE_TINT_EQUATION \ + GLSL_SOFTWARE_FADE_EQUATION \ + "final_color *= gl_Color;\n" \ + "final_color.a = texel.a * poly_color.a;\n" \ + "gl_FragColor = final_color;\n" \ + "}\0" + // // Water surface shader // @@ -775,6 +798,9 @@ static const char *fragment_shaders[] = { "gl_FragColor = texture2D(tex, gl_TexCoord[0].st);\n" "}\0", + // Model fragment shader + diffuse lighting from above + GLSL_SOFTWARE_MODEL_LIGHTING_FRAGMENT_SHADER, + NULL, }; @@ -795,6 +821,20 @@ static const char *fragment_shaders[] = { "gl_ClipVertex = gl_ModelViewMatrix * gl_Vertex;\n" \ "}\0" +// replicates the way fixed function lighting is used by the model lighting option, +// stores the lighting result to gl_Color +// (ambient lighting of 0.75 and diffuse lighting from above) +#define GLSL_MODEL_LIGHTING_VERTEX_SHADER \ + "void main()\n" \ + "{\n" \ + "float nDotVP = dot(gl_Normal, vec3(0, 1, 0));\n" \ + "float light = 0.75 + max(nDotVP, 0.0);\n" \ + "gl_Position = gl_ProjectionMatrix * gl_ModelViewMatrix * gl_Vertex;\n" \ + "gl_FrontColor = vec4(light, light, light, 1.0);\n" \ + "gl_TexCoord[0].xy = gl_MultiTexCoord0.xy;\n" \ + "gl_ClipVertex = gl_ModelViewMatrix * gl_Vertex;\n" \ + "}\0" + static const char *vertex_shaders[] = { // Default vertex shader GLSL_DEFAULT_VERTEX_SHADER, @@ -820,6 +860,9 @@ static const char *vertex_shaders[] = { // Sky vertex shader GLSL_DEFAULT_VERTEX_SHADER, + // Model vertex shader + diffuse lighting from above + GLSL_MODEL_LIGHTING_VERTEX_SHADER, + NULL, }; @@ -1063,6 +1106,11 @@ EXPORT void HWRAPI(SetShader) (int shader) #ifdef GL_SHADERS if (gl_allowshaders) { + // If using model lighting, set the appropriate shader. + // However don't override a custom shader. + // Should use an enum or something... + if (shader == 4 && model_lighting && !gl_shaderprograms[4].custom) + shader = 8; if ((GLuint)shader != gl_currentshaderprogram) { gl_currentshaderprogram = shader; @@ -1535,7 +1583,7 @@ EXPORT void HWRAPI(SetBlend) (FBITFIELD PolyFlags) // Sryder: Fog // multiplies input colour by input alpha, and destination colour by input colour, then adds them pglBlendFunc(GL_SRC_ALPHA, GL_SRC_COLOR); - pglAlphaFunc(GL_NOTEQUAL, 0.0f); + pglAlphaFunc(GL_ALWAYS, 0.0f); // Don't discard zero alpha fragments break; default : // must be 0, otherwise it's an error // No blending @@ -2660,31 +2708,34 @@ static void DrawModelEx(model_t *model, INT32 frameIndex, INT32 duration, INT32 poly.alpha = byte2float[Surface->PolyColor.s.alpha]; #ifdef GL_LIGHT_MODEL_AMBIENT - if (model_lighting && (!gl_shadersenabled)) // doesn't work with shaders anyway + if (model_lighting) { - ambient[0] = poly.red; - ambient[1] = poly.green; - ambient[2] = poly.blue; - ambient[3] = poly.alpha; + if (!gl_shadersenabled) + { + ambient[0] = poly.red; + ambient[1] = poly.green; + ambient[2] = poly.blue; + ambient[3] = poly.alpha; - diffuse[0] = poly.red; - diffuse[1] = poly.green; - diffuse[2] = poly.blue; - diffuse[3] = poly.alpha; + diffuse[0] = poly.red; + diffuse[1] = poly.green; + diffuse[2] = poly.blue; + diffuse[3] = poly.alpha; - if (ambient[0] > 0.75f) - ambient[0] = 0.75f; - if (ambient[1] > 0.75f) - ambient[1] = 0.75f; - if (ambient[2] > 0.75f) - ambient[2] = 0.75f; + if (ambient[0] > 0.75f) + ambient[0] = 0.75f; + if (ambient[1] > 0.75f) + ambient[1] = 0.75f; + if (ambient[2] > 0.75f) + ambient[2] = 0.75f; - pglLightfv(GL_LIGHT0, GL_POSITION, LightPos); + pglLightfv(GL_LIGHT0, GL_POSITION, LightPos); + + pglEnable(GL_LIGHTING); + pglMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, ambient); + pglMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, diffuse); + } pglShadeModel(GL_SMOOTH); - - pglEnable(GL_LIGHTING); - pglMaterialfv(GL_FRONT_AND_BACK, GL_AMBIENT, ambient); - pglMaterialfv(GL_FRONT_AND_BACK, GL_DIFFUSE, diffuse); } #endif else @@ -2874,9 +2925,10 @@ static void DrawModelEx(model_t *model, INT32 frameIndex, INT32 duration, INT32 pglDisable(GL_NORMALIZE); #ifdef GL_LIGHT_MODEL_AMBIENT - if (model_lighting && (!gl_shadersenabled)) + if (model_lighting) { - pglDisable(GL_LIGHTING); + if (!gl_shadersenabled) + pglDisable(GL_LIGHTING); pglShadeModel(GL_FLAT); } #endif diff --git a/src/info.c b/src/info.c index 778f1f741..fccd1b269 100644 --- a/src/info.c +++ b/src/info.c @@ -20867,33 +20867,6 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] = S_NULL // raisestate }, - { // MT_POLYSPAWNCRUSH - 762, // doomednum - S_INVISIBLE, // spawnstate - 1, // spawnhealth - S_NULL, // seestate - sfx_None, // seesound - 0, // reactiontime - sfx_None, // attacksound - S_NULL, // painstate - 3, // painchance - sfx_None, // painsound - S_NULL, // meleestate - S_NULL, // missilestate - S_NULL, // deathstate - S_NULL, // xdeathstate - sfx_None, // deathsound - 0, // speed - 1*FRACUNIT, // radius - 1*FRACUNIT, // height - 0, // display offset - 1000, // mass - 8, // damage - sfx_None, // activesound - MF_NOBLOCKMAP|MF_NOSECTOR|MF_NOGRAVITY|MF_NOCLIP, // flags - S_NULL // raisestate - }, - { // MT_SKYBOX 780, // doomednum S_INVISIBLE, // spawnstate diff --git a/src/info.h b/src/info.h index 4d8e18d63..721ebf7f2 100644 --- a/src/info.h +++ b/src/info.h @@ -4774,7 +4774,6 @@ typedef enum mobj_type MT_ANGLEMAN, MT_POLYANCHOR, MT_POLYSPAWN, - MT_POLYSPAWNCRUSH, // Skybox objects MT_SKYBOX, diff --git a/src/lua_baselib.c b/src/lua_baselib.c index 23aa060fe..6b25e32ea 100644 --- a/src/lua_baselib.c +++ b/src/lua_baselib.c @@ -176,6 +176,11 @@ static const struct { {META_SECTORLINES, "sector_t.lines"}, {META_SIDENUM, "line_t.sidenum"}, + {META_LINEARGS, "line_t.args"}, + {META_LINESTRINGARGS, "line_t.stringargs"}, + + {META_THINGARGS, "mapthing.args"}, + {META_THINGSTRINGARGS, "mapthing.stringargs"}, #ifdef HAVE_LUA_SEGS {META_NODEBBOX, "node_t.bbox"}, {META_NODECHILDREN, "node_t.children"}, @@ -1113,6 +1118,16 @@ static int lib_pPlayerCanDamage(lua_State *L) return 1; } +static int lib_pPlayerFullbright(lua_State *L) +{ + player_t *player = *((player_t **)luaL_checkudata(L, 1, META_PLAYER)); + INLEVEL + if (!player) + return LUA_ErrInvalid(L, "player_t"); + lua_pushboolean(L, P_PlayerFullbright(player)); + return 1; +} + static int lib_pIsObjectInGoop(lua_State *L) { @@ -2550,6 +2565,14 @@ static int lib_rGetColorByName(lua_State *L) return 1; } +static int lib_rGetSuperColorByName(lua_State *L) +{ + const char* colorname = luaL_checkstring(L, 1); + //HUDSAFE + lua_pushinteger(L, R_GetSuperColorByName(colorname)); + return 1; +} + // Lua exclusive function, returns the name of a color from the SKINCOLOR_ constant. // SKINCOLOR_GREEN > "Green" for example static int lib_rGetNameByColor(lua_State *L) @@ -3108,6 +3131,117 @@ static int lib_gBuildMapTitle(lua_State *L) return 1; } +static void +Lpushdim (lua_State *L, int c, struct searchdim *v) +{ + int i; + lua_createtable(L, c, 0);/* I guess narr is numeric indices??? */ + for (i = 0; i < c; ++i) + { + lua_createtable(L, 0, 2);/* and hashed indices (field)... */ + lua_pushnumber(L, v[i].pos); + lua_setfield(L, -2, "pos"); + + lua_pushnumber(L, v[i].siz); + lua_setfield(L, -2, "siz"); + lua_rawseti(L, -2, 1 + i); + } +} + +/* +I decided to make this return a table because userdata +is scary and tables let the user set their own fields. +*/ +/* +Returns: + +[1] => map number +[2] => map title +[3] => search frequency table + +The frequency table is unsorted. It has the following format: + +{ + ['mapnum'], + + ['matchd'] => matches in map title string + ['keywhd'] => matches in map keywords + + The above two tables have the following format: + + { + ['pos'] => offset from start of string + ['siz'] => length of match + }... + + ['total'] => the total matches +}... +*/ +static int lib_gFindMap(lua_State *L) +{ + const char *query = luaL_checkstring(L, 1); + + INT32 map; + char *realname; + INT32 frc; + mapsearchfreq_t *frv; + + INT32 i; + + map = G_FindMap(query, &realname, &frv, &frc); + + lua_settop(L, 0); + + lua_pushnumber(L, map); + lua_pushstring(L, realname); + + lua_createtable(L, frc, 0); + for (i = 0; i < frc; ++i) + { + lua_createtable(L, 0, 4); + lua_pushnumber(L, frv[i].mapnum); + lua_setfield(L, -2, "mapnum"); + + Lpushdim(L, frv[i].matchc, frv[i].matchd); + lua_setfield(L, -2, "matchd"); + + Lpushdim(L, frv[i].keywhc, frv[i].keywhd); + lua_setfield(L, -2, "keywhd"); + + lua_pushnumber(L, frv[i].total); + lua_setfield(L, -2, "total"); + lua_rawseti(L, -2, 1 + i); + } + + G_FreeMapSearch(frv, frc); + Z_Free(realname); + + return 3; +} + +/* +Returns: + +[1] => map number +[2] => map title +*/ +static int lib_gFindMapByNameOrCode(lua_State *L) +{ + const char *query = luaL_checkstring(L, 1); + INT32 map; + char *realname; + map = G_FindMapByNameOrCode(query, &realname); + lua_pushnumber(L, map); + if (map) + { + lua_pushstring(L, realname); + Z_Free(realname); + return 2; + } + else + return 1; +} + static int lib_gDoReborn(lua_State *L) { INT32 playernum = luaL_checkinteger(L, 1); @@ -3378,6 +3512,7 @@ static luaL_Reg lib[] = { {"P_DoPlayerPain",lib_pDoPlayerPain}, {"P_ResetPlayer",lib_pResetPlayer}, {"P_PlayerCanDamage",lib_pPlayerCanDamage}, + {"P_PlayerFullbright",lib_pPlayerFullbright}, {"P_IsObjectInGoop",lib_pIsObjectInGoop}, {"P_IsObjectOnGround",lib_pIsObjectOnGround}, {"P_InSpaceSector",lib_pInSpaceSector}, @@ -3493,6 +3628,7 @@ static luaL_Reg lib[] = { // r_draw {"R_GetColorByName", lib_rGetColorByName}, + {"R_GetSuperColorByName", lib_rGetSuperColorByName}, {"R_GetNameByColor", lib_rGetNameByColor}, // s_sound @@ -3519,6 +3655,8 @@ static luaL_Reg lib[] = { {"G_AddGametype", lib_gAddGametype}, {"G_BuildMapName",lib_gBuildMapName}, {"G_BuildMapTitle",lib_gBuildMapTitle}, + {"G_FindMap",lib_gFindMap}, + {"G_FindMapByNameOrCode",lib_gFindMapByNameOrCode}, {"G_DoReborn",lib_gDoReborn}, {"G_SetCustomExitVars",lib_gSetCustomExitVars}, {"G_EnoughPlayersFinished",lib_gEnoughPlayersFinished}, diff --git a/src/lua_consolelib.c b/src/lua_consolelib.c index 4fe234dee..fae4f2d14 100644 --- a/src/lua_consolelib.c +++ b/src/lua_consolelib.c @@ -236,15 +236,14 @@ static int lib_comAddCommand(lua_State *L) static int lib_comBufAddText(lua_State *L) { int n = lua_gettop(L); /* number of arguments */ - player_t *plr; + player_t *plr = NULL; if (n < 2) return luaL_error(L, "COM_BufAddText requires two arguments: player and text."); NOHUD lua_settop(L, 2); - plr = *((player_t **)luaL_checkudata(L, 1, META_PLAYER)); - if (!plr) - return LUA_ErrInvalid(L, "player_t"); - if (plr != &players[consoleplayer]) + if (!lua_isnoneornil(L, 1)) + plr = *((player_t **)luaL_checkudata(L, 1, META_PLAYER)); + if (plr && plr != &players[consoleplayer]) return 0; COM_BufAddTextEx(va("%s\n", luaL_checkstring(L, 2)), COM_SAFE); return 0; @@ -253,15 +252,14 @@ static int lib_comBufAddText(lua_State *L) static int lib_comBufInsertText(lua_State *L) { int n = lua_gettop(L); /* number of arguments */ - player_t *plr; + player_t *plr = NULL; if (n < 2) return luaL_error(L, "COM_BufInsertText requires two arguments: player and text."); NOHUD lua_settop(L, 2); - plr = *((player_t **)luaL_checkudata(L, 1, META_PLAYER)); - if (!plr) - return LUA_ErrInvalid(L, "player_t"); - if (plr != &players[consoleplayer]) + if (!lua_isnoneornil(L, 1)) + plr = *((player_t **)luaL_checkudata(L, 1, META_PLAYER)); + if (plr && plr != &players[consoleplayer]) return 0; COM_BufInsertTextEx(va("%s\n", luaL_checkstring(L, 2)), COM_SAFE); return 0; @@ -444,7 +442,7 @@ static int lib_consPrintf(lua_State *L) if (n < 2) return luaL_error(L, "CONS_Printf requires at least two arguments: player and text."); //HUDSAFE - INLEVEL + plr = *((player_t **)luaL_checkudata(L, 1, META_PLAYER)); if (!plr) return LUA_ErrInvalid(L, "player_t"); diff --git a/src/lua_hooklib.c b/src/lua_hooklib.c index 5cfd1bd3d..ebf6f9deb 100644 --- a/src/lua_hooklib.c +++ b/src/lua_hooklib.c @@ -1186,7 +1186,7 @@ boolean LUAh_LinedefExecute(line_t *line, mobj_t *mo, sector_t *sector) for (hookp = linedefexecutorhooks; hookp; hookp = hookp->next) { - if (strcmp(hookp->s.str, line->text)) + if (strcmp(hookp->s.str, line->stringargs[0])) continue; if (lua_gettop(gL) == 1) diff --git a/src/lua_infolib.c b/src/lua_infolib.c index 81a215c53..830d97625 100644 --- a/src/lua_infolib.c +++ b/src/lua_infolib.c @@ -19,14 +19,15 @@ #include "z_zone.h" #include "r_patch.h" #include "r_things.h" +#include "r_draw.h" // R_GetColorByName #include "doomstat.h" // luabanks[] #include "lua_script.h" #include "lua_libs.h" #include "lua_hud.h" // hud_running errors -extern CV_PossibleValue_t Color_cons_t[MAXSKINCOLORS+1]; -extern void R_FlushTranslationColormapCache(void); +extern CV_PossibleValue_t Color_cons_t[]; +extern UINT8 skincolor_modified[]; boolean LUA_CallAction(const char *action, mobj_t *actor); state_t *astate; @@ -1490,7 +1491,7 @@ static void setRamp(lua_State *L, skincolor_t* c) { UINT32 i; lua_pushnil(L); for (i=0; i= numskincolors) - return luaL_error(L, "skincolors[] index %d out of range (%d - %d)", cnum, SKINCOLOR_FIRSTFREESLOT, numskincolors-1); + if (!cnum || cnum >= numskincolors) + return luaL_error(L, "skincolors[] index %d out of range (1 - %d)", cnum, numskincolors-1); info = &skincolors[cnum]; // get the skincolor to assign to. } luaL_checktype(L, 2, LUA_TTABLE); // check that we've been passed a table. @@ -1540,7 +1541,16 @@ static int lib_setSkinColor(lua_State *L) const char* n = luaL_checkstring(L, 3); strlcpy(info->name, n, MAXCOLORNAME+1); if (strlen(n) > MAXCOLORNAME) - CONS_Alert(CONS_WARNING, "skincolor_t field 'name' ('%s') longer than %d chars; shortened to %s.\n", n, MAXCOLORNAME, info->name); + CONS_Alert(CONS_WARNING, "skincolor_t field 'name' ('%s') longer than %d chars; clipped to %s.\n", n, MAXCOLORNAME, info->name); + if (strchr(info->name, ' ') != NULL) + CONS_Alert(CONS_WARNING, "skincolor_t field 'name' ('%s') contains spaces.\n", info->name); + + if (info->name[0] != '\0') // don't check empty string for dupe + { + UINT16 dupecheck = R_GetColorByName(info->name); + if (!stricmp(info->name, skincolors[SKINCOLOR_NONE].name) || (dupecheck && (dupecheck != info-skincolors))) + CONS_Alert(CONS_WARNING, "skincolor_t field 'name' ('%s') is a duplicate of another skincolor's name.\n", info->name); + } } else if (i == 2 || (str && fastcmp(str,"ramp"))) { if (!lua_istable(L, 3) && luaL_checkudata(L, 3, META_COLORRAMP) == NULL) return luaL_error(L, LUA_QL("skincolor_t") " field 'ramp' must be a table or array."); @@ -1549,17 +1559,20 @@ static int lib_setSkinColor(lua_State *L) else for (j=0; jramp[j] = (*((UINT8 **)luaL_checkudata(L, 3, META_COLORRAMP)))[j]; - R_FlushTranslationColormapCache(); - } else if (i == 3 || (str && fastcmp(str,"invcolor"))) - info->invcolor = (UINT16)luaL_checkinteger(L, 3); - else if (i == 4 || (str && fastcmp(str,"invshade"))) + skincolor_modified[cnum] = true; + } else if (i == 3 || (str && fastcmp(str,"invcolor"))) { + UINT16 v = (UINT16)luaL_checkinteger(L, 3); + if (v >= numskincolors) + return luaL_error(L, "skincolor_t field 'invcolor' out of range (1 - %d)", numskincolors-1); + info->invcolor = v; + } else if (i == 4 || (str && fastcmp(str,"invshade"))) info->invshade = (UINT8)luaL_checkinteger(L, 3)%COLORRAMPSIZE; else if (i == 5 || (str && fastcmp(str,"chatcolor"))) info->chatcolor = (UINT16)luaL_checkinteger(L, 3); else if (i == 6 || (str && fastcmp(str,"accessible"))) { - boolean v = lua_isboolean(L,3) ? lua_toboolean(L, 3) : true; + boolean v = lua_toboolean(L, 3); if (cnum < FIRSTSUPERCOLOR && v != skincolors[cnum].accessible) - return luaL_error(L, "skincolors[] index %d is a standard color; accessibility changes are prohibited.", i); + return luaL_error(L, "skincolors[] index %d is a standard color; accessibility changes are prohibited.", cnum); else info->accessible = v; } @@ -1607,20 +1620,28 @@ static int skincolor_set(lua_State *L) UINT32 i; skincolor_t *info = *((skincolor_t **)luaL_checkudata(L, 1, META_SKINCOLOR)); const char *field = luaL_checkstring(L, 2); + UINT16 cnum = (UINT16)(info-skincolors); I_Assert(info != NULL); I_Assert(info >= skincolors); - if (info-skincolors < SKINCOLOR_FIRSTFREESLOT || info-skincolors >= numskincolors) - return luaL_error(L, "skincolors[] index %d out of range (%d - %d)", info-skincolors, SKINCOLOR_FIRSTFREESLOT, numskincolors-1); + if (!cnum || cnum >= numskincolors) + return luaL_error(L, "skincolors[] index %d out of range (1 - %d)", cnum, numskincolors-1); if (fastcmp(field,"name")) { const char* n = luaL_checkstring(L, 3); - if (strchr(n, ' ') != NULL) - CONS_Alert(CONS_WARNING, "skincolor_t field 'name' ('%s') contains spaces.\n", n); strlcpy(info->name, n, MAXCOLORNAME+1); if (strlen(n) > MAXCOLORNAME) CONS_Alert(CONS_WARNING, "skincolor_t field 'name' ('%s') longer than %d chars; clipped to %s.\n", n, MAXCOLORNAME, info->name); + if (strchr(info->name, ' ') != NULL) + CONS_Alert(CONS_WARNING, "skincolor_t field 'name' ('%s') contains spaces.\n", info->name); + + if (info->name[0] != '\0') // don't check empty string for dupe + { + UINT16 dupecheck = R_GetColorByName(info->name); + if (!stricmp(info->name, skincolors[SKINCOLOR_NONE].name) || (dupecheck && (dupecheck != cnum))) + CONS_Alert(CONS_WARNING, "skincolor_t field 'name' ('%s') is a duplicate of another skincolor's name.\n", info->name); + } } else if (fastcmp(field,"ramp")) { if (!lua_istable(L, 3) && luaL_checkudata(L, 3, META_COLORRAMP) == NULL) return luaL_error(L, LUA_QL("skincolor_t") " field 'ramp' must be a table or array."); @@ -1629,16 +1650,23 @@ static int skincolor_set(lua_State *L) else for (i=0; iramp[i] = (*((UINT8 **)luaL_checkudata(L, 3, META_COLORRAMP)))[i]; - R_FlushTranslationColormapCache(); - } else if (fastcmp(field,"invcolor")) - info->invcolor = (UINT16)luaL_checkinteger(L, 3); - else if (fastcmp(field,"invshade")) + skincolor_modified[cnum] = true; + } else if (fastcmp(field,"invcolor")) { + UINT16 v = (UINT16)luaL_checkinteger(L, 3); + if (v >= numskincolors) + return luaL_error(L, "skincolor_t field 'invcolor' out of range (1 - %d)", numskincolors-1); + info->invcolor = v; + } else if (fastcmp(field,"invshade")) info->invshade = (UINT8)luaL_checkinteger(L, 3)%COLORRAMPSIZE; else if (fastcmp(field,"chatcolor")) info->chatcolor = (UINT16)luaL_checkinteger(L, 3); - else if (fastcmp(field,"accessible")) - info->accessible = lua_isboolean(L,3); - else + else if (fastcmp(field,"accessible")) { + boolean v = lua_toboolean(L, 3); + if (cnum < FIRSTSUPERCOLOR && v != skincolors[cnum].accessible) + return luaL_error(L, "skincolors[] index %d is a standard color; accessibility changes are prohibited.", cnum); + else + info->accessible = v; + } else CONS_Debug(DBG_LUA, M_GetText("'%s' has no field named '%s'; returning nil.\n"), "skincolor_t", field); return 1; } @@ -1670,17 +1698,17 @@ static int colorramp_get(lua_State *L) static int colorramp_set(lua_State *L) { UINT8 *colorramp = *((UINT8 **)luaL_checkudata(L, 1, META_COLORRAMP)); - UINT16 cnum = (UINT16)(((uint8_t*)colorramp - (uint8_t*)(skincolors[0].ramp))/sizeof(skincolor_t)); + UINT16 cnum = (UINT16)(((UINT8*)colorramp - (UINT8*)(skincolors[0].ramp))/sizeof(skincolor_t)); UINT32 n = luaL_checkinteger(L, 2); UINT8 i = (UINT8)luaL_checkinteger(L, 3); - if (cnum < SKINCOLOR_FIRSTFREESLOT || cnum >= numskincolors) - return luaL_error(L, "skincolors[] index %d out of range (%d - %d)", cnum, SKINCOLOR_FIRSTFREESLOT, numskincolors-1); + if (!cnum || cnum >= numskincolors) + return luaL_error(L, "skincolors[] index %d out of range (1 - %d)", cnum, numskincolors-1); if (n >= COLORRAMPSIZE) return luaL_error(L, LUA_QL("skincolor_t") " field 'ramp' index %d out of range (0 - %d)", n, COLORRAMPSIZE-1); if (hud_running) return luaL_error(L, "Do not alter skincolor_t in HUD rendering code!"); colorramp[n] = i; - R_FlushTranslationColormapCache(); + skincolor_modified[cnum] = true; return 0; } diff --git a/src/lua_libs.h b/src/lua_libs.h index a78128e9f..f987c79fd 100644 --- a/src/lua_libs.h +++ b/src/lua_libs.h @@ -54,6 +54,10 @@ extern lua_State *gL; #define META_SECTORLINES "SECTOR_T*LINES" #define META_SIDENUM "LINE_T*SIDENUM" +#define META_LINEARGS "LINE_T*ARGS" +#define META_LINESTRINGARGS "LINE_T*STRINGARGS" +#define META_THINGARGS "MAPTHING_T*ARGS" +#define META_THINGSTRINGARGS "MAPTHING_T*STRINGARGS" #ifdef HAVE_LUA_SEGS #define META_NODEBBOX "NODE_T*BBOX" #define META_NODECHILDREN "NODE_T*CHILDREN" diff --git a/src/lua_maplib.c b/src/lua_maplib.c index 144a6b3f1..216818d29 100644 --- a/src/lua_maplib.c +++ b/src/lua_maplib.c @@ -85,9 +85,13 @@ enum line_e { line_flags, line_special, line_tag, + line_args, + line_stringargs, line_sidenum, line_frontside, line_backside, + line_alpha, + line_executordelay, line_slopetype, line_frontsector, line_backsector, @@ -106,9 +110,13 @@ static const char *const line_opt[] = { "flags", "special", "tag", + "args", + "stringargs", "sidenum", "frontside", "backside", + "alpha", + "executordelay", "slopetype", "frontsector", "backsector", @@ -691,6 +699,42 @@ static int subsector_num(lua_State *L) // line_t // //////////// +// args, i -> args[i] +static int lineargs_get(lua_State *L) +{ + INT32 *args = *((INT32**)luaL_checkudata(L, 1, META_LINEARGS)); + int i = luaL_checkinteger(L, 2); + if (i < 0 || i >= NUMLINEARGS) + return luaL_error(L, LUA_QL("line_t.args") " index cannot be %d", i); + lua_pushinteger(L, args[i]); + return 1; +} + +// #args -> NUMLINEARGS +static int lineargs_len(lua_State* L) +{ + lua_pushinteger(L, NUMLINEARGS); + return 1; +} + +// stringargs, i -> stringargs[i] +static int linestringargs_get(lua_State *L) +{ + char **stringargs = *((char***)luaL_checkudata(L, 1, META_LINESTRINGARGS)); + int i = luaL_checkinteger(L, 2); + if (i < 0 || i >= NUMLINESTRINGARGS) + return luaL_error(L, LUA_QL("line_t.stringargs") " index cannot be %d", i); + lua_pushstring(L, stringargs[i]); + return 1; +} + +// #stringargs -> NUMLINESTRINGARGS +static int linestringargs_len(lua_State *L) +{ + lua_pushinteger(L, NUMLINESTRINGARGS); + return 1; +} + static int line_get(lua_State *L) { line_t *line = *((line_t **)luaL_checkudata(L, 1, META_LINE)); @@ -731,6 +775,12 @@ static int line_get(lua_State *L) case line_tag: lua_pushinteger(L, line->tag); return 1; + case line_args: + LUA_PushUserdata(L, line->args, META_LINEARGS); + return 1; + case line_stringargs: + LUA_PushUserdata(L, line->stringargs, META_LINESTRINGARGS); + return 1; case line_sidenum: LUA_PushUserdata(L, line->sidenum, META_SIDENUM); return 1; @@ -742,6 +792,12 @@ static int line_get(lua_State *L) return 0; LUA_PushUserdata(L, &sides[line->sidenum[1]], META_SIDE); return 1; + case line_alpha: + lua_pushfixed(L, line->alpha); + return 1; + case line_executordelay: + lua_pushinteger(L, line->executordelay); + return 1; case line_slopetype: switch(line->slopetype) { @@ -2143,6 +2199,22 @@ int LUA_MapLib(lua_State *L) lua_setfield(L, -2, "__len"); lua_pop(L, 1); + luaL_newmetatable(L, META_LINEARGS); + lua_pushcfunction(L, lineargs_get); + lua_setfield(L, -2, "__index"); + + lua_pushcfunction(L, lineargs_len); + lua_setfield(L, -2, "__len"); + lua_pop(L, 1); + + luaL_newmetatable(L, META_LINESTRINGARGS); + lua_pushcfunction(L, linestringargs_get); + lua_setfield(L, -2, "__index"); + + lua_pushcfunction(L, linestringargs_len); + lua_setfield(L, -2, "__len"); + lua_pop(L, 1); + luaL_newmetatable(L, META_SIDENUM); lua_pushcfunction(L, sidenum_get); lua_setfield(L, -2, "__index"); diff --git a/src/lua_mobjlib.c b/src/lua_mobjlib.c index 129339b96..4fa938ea5 100644 --- a/src/lua_mobjlib.c +++ b/src/lua_mobjlib.c @@ -31,6 +31,8 @@ enum mobj_e { mobj_snext, mobj_sprev, mobj_angle, + mobj_pitch, + mobj_roll, mobj_rollangle, mobj_sprite, mobj_frame, @@ -98,6 +100,8 @@ static const char *const mobj_opt[] = { "snext", "sprev", "angle", + "pitch", + "roll", "rollangle", "sprite", "frame", @@ -165,14 +169,15 @@ static int mobj_get(lua_State *L) enum mobj_e field = Lua_optoption(L, 2, NULL, mobj_opt); lua_settop(L, 2); - INLEVEL - - if (!mo) { + if (!mo || !ISINLEVEL) { if (field == mobj_valid) { lua_pushboolean(L, 0); return 1; } - return LUA_ErrInvalid(L, "mobj_t"); + if (!mo) { + return LUA_ErrInvalid(L, "mobj_t"); + } else + return luaL_error(L, "Do not access an mobj_t field outside a level!"); } switch(field) @@ -200,6 +205,12 @@ static int mobj_get(lua_State *L) case mobj_angle: lua_pushangle(L, mo->angle); break; + case mobj_pitch: + lua_pushangle(L, mo->pitch); + break; + case mobj_roll: + lua_pushangle(L, mo->roll); + break; case mobj_rollangle: lua_pushangle(L, mo->rollangle); break; @@ -457,6 +468,12 @@ static int mobj_set(lua_State *L) if (mo->player) P_SetPlayerAngle(mo->player, mo->angle); break; + case mobj_pitch: + mo->pitch = luaL_checkangle(L, 3); + break; + case mobj_roll: + mo->roll = luaL_checkangle(L, 3); + break; case mobj_rollangle: mo->rollangle = luaL_checkangle(L, 3); break; @@ -752,6 +769,42 @@ static int mobj_set(lua_State *L) #undef NOSETPOS #undef NOFIELD +// args, i -> args[i] +static int thingargs_get(lua_State *L) +{ + INT32 *args = *((INT32**)luaL_checkudata(L, 1, META_THINGARGS)); + int i = luaL_checkinteger(L, 2); + if (i < 0 || i >= NUMMAPTHINGARGS) + return luaL_error(L, LUA_QL("mapthing_t.args") " index cannot be %d", i); + lua_pushinteger(L, args[i]); + return 1; +} + +// #args -> NUMMAPTHINGARGS +static int thingargs_len(lua_State* L) +{ + lua_pushinteger(L, NUMMAPTHINGARGS); + return 1; +} + +// stringargs, i -> stringargs[i] +static int thingstringargs_get(lua_State *L) +{ + char **stringargs = *((char***)luaL_checkudata(L, 1, META_THINGSTRINGARGS)); + int i = luaL_checkinteger(L, 2); + if (i < 0 || i >= NUMMAPTHINGSTRINGARGS) + return luaL_error(L, LUA_QL("mapthing_t.stringargs") " index cannot be %d", i); + lua_pushstring(L, stringargs[i]); + return 1; +} + +// #stringargs -> NUMMAPTHINGSTRINGARGS +static int thingstringargs_len(lua_State *L) +{ + lua_pushinteger(L, NUMMAPTHINGSTRINGARGS); + return 1; +} + static int mapthing_get(lua_State *L) { mapthing_t *mt = *((mapthing_t **)luaL_checkudata(L, 1, META_MAPTHING)); @@ -777,14 +830,32 @@ static int mapthing_get(lua_State *L) number = mt->y; else if(fastcmp(field,"angle")) number = mt->angle; + else if(fastcmp(field,"pitch")) + number = mt->pitch; + else if(fastcmp(field,"roll")) + number = mt->roll; else if(fastcmp(field,"type")) number = mt->type; else if(fastcmp(field,"options")) number = mt->options; + else if(fastcmp(field,"scale")) + number = mt->scale; else if(fastcmp(field,"z")) number = mt->z; else if(fastcmp(field,"extrainfo")) number = mt->extrainfo; + else if(fastcmp(field,"tag")) + number = mt->tag; + else if(fastcmp(field,"args")) + { + LUA_PushUserdata(L, mt->args, META_THINGARGS); + return 1; + } + else if(fastcmp(field,"stringargs")) + { + LUA_PushUserdata(L, mt->stringargs, META_THINGSTRINGARGS); + return 1; + } else if(fastcmp(field,"mobj")) { LUA_PushUserdata(L, mt->mobj, META_MOBJ); return 1; @@ -814,10 +885,16 @@ static int mapthing_set(lua_State *L) mt->y = (INT16)luaL_checkinteger(L, 3); else if(fastcmp(field,"angle")) mt->angle = (INT16)luaL_checkinteger(L, 3); + else if(fastcmp(field,"pitch")) + mt->pitch = (INT16)luaL_checkinteger(L, 3); + else if(fastcmp(field,"roll")) + mt->roll = (INT16)luaL_checkinteger(L, 3); else if(fastcmp(field,"type")) mt->type = (UINT16)luaL_checkinteger(L, 3); else if(fastcmp(field,"options")) mt->options = (UINT16)luaL_checkinteger(L, 3); + else if(fastcmp(field,"scale")) + mt->scale = luaL_checkfixed(L, 3); else if(fastcmp(field,"z")) mt->z = (INT16)luaL_checkinteger(L, 3); else if(fastcmp(field,"extrainfo")) @@ -827,6 +904,8 @@ static int mapthing_set(lua_State *L) return luaL_error(L, "mapthing_t extrainfo set %d out of range (%d - %d)", extrainfo, 0, 15); mt->extrainfo = (UINT8)extrainfo; } + else if (fastcmp(field,"tag")) + mt->tag = (INT16)luaL_checkinteger(L, 3); else if(fastcmp(field,"mobj")) mt->mobj = *((mobj_t **)luaL_checkudata(L, 3, META_MOBJ)); else @@ -902,6 +981,22 @@ int LUA_MobjLib(lua_State *L) lua_setfield(L, -2, "__newindex"); lua_pop(L,1); + luaL_newmetatable(L, META_THINGARGS); + lua_pushcfunction(L, thingargs_get); + lua_setfield(L, -2, "__index"); + + lua_pushcfunction(L, thingargs_len); + lua_setfield(L, -2, "__len"); + lua_pop(L, 1); + + luaL_newmetatable(L, META_THINGSTRINGARGS); + lua_pushcfunction(L, thingstringargs_get); + lua_setfield(L, -2, "__index"); + + lua_pushcfunction(L, thingstringargs_len); + lua_setfield(L, -2, "__len"); + lua_pop(L, 1); + luaL_newmetatable(L, META_MAPTHING); lua_pushcfunction(L, mapthing_get); lua_setfield(L, -2, "__index"); diff --git a/src/lua_script.c b/src/lua_script.c index 9d7d536b9..0260f018a 100644 --- a/src/lua_script.c +++ b/src/lua_script.c @@ -136,6 +136,9 @@ int LUA_PushGlobals(lua_State *L, const char *word) if (fastcmp(word,"gamemap")) { lua_pushinteger(L, gamemap); return 1; + } else if (fastcmp(word,"udmf")) { + lua_pushboolean(L, udmf); + return 1; } else if (fastcmp(word,"maptol")) { lua_pushinteger(L, maptol); return 1; diff --git a/src/m_menu.c b/src/m_menu.c index 41f663c19..57d2ed023 100644 --- a/src/m_menu.c +++ b/src/m_menu.c @@ -1489,21 +1489,23 @@ static menuitem_t OP_OpenGLLightingMenu[] = static menuitem_t OP_SoundOptionsMenu[] = { {IT_HEADER, NULL, "Game Audio", NULL, 0}, - {IT_STRING | IT_CVAR, NULL, "Sound Effects", &cv_gamesounds, 12}, - {IT_STRING | IT_CVAR | IT_CV_SLIDER, NULL, "Sound Volume", &cv_soundvolume, 22}, + {IT_STRING | IT_CVAR, NULL, "Sound Effects", &cv_gamesounds, 6}, + {IT_STRING | IT_CVAR | IT_CV_SLIDER, NULL, "Sound Volume", &cv_soundvolume, 11}, - {IT_STRING | IT_CVAR, NULL, "Digital Music", &cv_gamedigimusic, 42}, - {IT_STRING | IT_CVAR | IT_CV_SLIDER, NULL, "Digital Music Volume", &cv_digmusicvolume, 52}, + {IT_STRING | IT_CVAR, NULL, "Digital Music", &cv_gamedigimusic, 21}, + {IT_STRING | IT_CVAR | IT_CV_SLIDER, NULL, "Digital Music Volume", &cv_digmusicvolume, 26}, - {IT_STRING | IT_CVAR, NULL, "MIDI Music", &cv_gamemidimusic, 72}, - {IT_STRING | IT_CVAR | IT_CV_SLIDER, NULL, "MIDI Music Volume", &cv_midimusicvolume, 82}, + {IT_STRING | IT_CVAR, NULL, "MIDI Music", &cv_gamemidimusic, 36}, + {IT_STRING | IT_CVAR | IT_CV_SLIDER, NULL, "MIDI Music Volume", &cv_midimusicvolume, 41}, + + {IT_STRING | IT_CVAR, NULL, "Music Preference", &cv_musicpref, 51}, - {IT_HEADER, NULL, "Miscellaneous", NULL, 102}, - {IT_STRING | IT_CVAR, NULL, "Closed Captioning", &cv_closedcaptioning, 114}, - {IT_STRING | IT_CVAR, NULL, "Reset Music Upon Dying", &cv_resetmusic, 124}, - {IT_STRING | IT_CVAR, NULL, "Default 1-Up sound", &cv_1upsound, 134}, + {IT_HEADER, NULL, "Miscellaneous", NULL, 61}, + {IT_STRING | IT_CVAR, NULL, "Closed Captioning", &cv_closedcaptioning, 67}, + {IT_STRING | IT_CVAR, NULL, "Reset Music Upon Dying", &cv_resetmusic, 72}, + {IT_STRING | IT_CVAR, NULL, "Default 1-Up sound", &cv_1upsound, 77}, - {IT_STRING | IT_SUBMENU, NULL, "Advanced Settings...", &OP_SoundAdvancedDef, 154}, + {IT_STRING | IT_SUBMENU, NULL, "Advanced Settings...", &OP_SoundAdvancedDef, 87}, }; #ifdef HAVE_OPENMPT @@ -2202,7 +2204,7 @@ menu_t OP_ColorOptionsDef = 0, NULL }; -menu_t OP_SoundOptionsDef = DEFAULTMENUSTYLE( +menu_t OP_SoundOptionsDef = DEFAULTSCROLLMENUSTYLE( MTREE2(MN_OP_MAIN, MN_OP_SOUND), "M_SOUND", OP_SoundOptionsMenu, &OP_MainDef, 30, 30); menu_t OP_SoundAdvancedDef = DEFAULTMENUSTYLE( diff --git a/src/p_local.h b/src/p_local.h index b6c34f357..4077fecf6 100644 --- a/src/p_local.h +++ b/src/p_local.h @@ -142,6 +142,7 @@ void P_SetPlayerAngle(player_t *player, angle_t angle); angle_t P_GetLocalAngle(player_t *player); void P_SetLocalAngle(player_t *player, angle_t angle); void P_ForceLocalAngle(player_t *player, angle_t angle); +boolean P_PlayerFullbright(player_t *player); boolean P_IsObjectInGoop(mobj_t *mo); boolean P_IsObjectOnGround(mobj_t *mo); diff --git a/src/p_mobj.c b/src/p_mobj.c index 6f3f53559..fcba1f690 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -442,7 +442,7 @@ boolean P_SetPlayerMobjState(mobj_t *mobj, statenum_t state) mobj->sprite2 = spr2; mobj->frame = frame|(st->frame&~FF_FRAMEMASK); - if (player->powers[pw_super] || (player->powers[pw_carry] == CR_NIGHTSMODE && (player->charflags & (SF_SUPER|SF_NONIGHTSSUPER)) == SF_SUPER)) // Super colours? Super bright! + if (P_PlayerFullbright(player)) mobj->frame |= FF_FULLBRIGHT; } // Regular sprites @@ -2882,8 +2882,7 @@ static boolean P_PlayerPolyObjectZMovement(mobj_t *mo) continue; // We're landing on a PO, so check for a linedef executor. - // Trigger tags are 32000 + the PO's ID number. - P_LinedefExecute((INT16)(32000 + po->id), mo, NULL); + P_LinedefExecute(po->triggertag, mo, NULL); } } } @@ -11615,7 +11614,7 @@ void P_MovePlayerToStarpost(INT32 playernum) mapthing_t *huntemeralds[MAXHUNTEMERALDS]; INT32 numhuntemeralds; -fixed_t P_GetMobjSpawnHeight(const mobjtype_t mobjtype, const fixed_t x, const fixed_t y, const fixed_t offset, const boolean flip) +fixed_t P_GetMobjSpawnHeight(const mobjtype_t mobjtype, const fixed_t x, const fixed_t y, const fixed_t dz, const fixed_t offset, const boolean flip, const fixed_t scale) { const subsector_t *ss = R_PointInSubsector(x, y); @@ -11625,14 +11624,15 @@ fixed_t P_GetMobjSpawnHeight(const mobjtype_t mobjtype, const fixed_t x, const f // Establish height. if (flip) - return P_GetSectorCeilingZAt(ss->sector, x, y) - offset - mobjinfo[mobjtype].height; + return P_GetSectorCeilingZAt(ss->sector, x, y) - dz - FixedMul(scale, offset + mobjinfo[mobjtype].height); else - return P_GetSectorFloorZAt(ss->sector, x, y) + offset; + return P_GetSectorFloorZAt(ss->sector, x, y) + dz + FixedMul(scale, offset); } fixed_t P_GetMapThingSpawnHeight(const mobjtype_t mobjtype, const mapthing_t* mthing, const fixed_t x, const fixed_t y) { - fixed_t offset = mthing->z << FRACBITS; + fixed_t dz = mthing->z << FRACBITS; // Base offset from the floor. + fixed_t offset = 0; // Specific scaling object offset. boolean flip = (!!(mobjinfo[mobjtype].flags & MF_SPAWNCEILING) ^ !!(mthing->options & MTF_OBJECTFLIP)); switch (mobjtype) @@ -11648,17 +11648,17 @@ fixed_t P_GetMapThingSpawnHeight(const mobjtype_t mobjtype, const mapthing_t* mt case MT_JETTBOMBER: case MT_JETTGUNNER: case MT_EGGMOBILE2: - if (!offset) - offset = 33*FRACUNIT; + if (!dz) + dz = 33*FRACUNIT; break; case MT_EGGMOBILE: - if (!offset) - offset = 128*FRACUNIT; + if (!dz) + dz = 128*FRACUNIT; break; case MT_GOLDBUZZ: case MT_REDBUZZ: - if (!offset) - offset = 288*FRACUNIT; + if (!dz) + dz = 288*FRACUNIT; break; // Horizontal springs, may float additional units with MTF_AMBUSH. @@ -11691,7 +11691,7 @@ fixed_t P_GetMapThingSpawnHeight(const mobjtype_t mobjtype, const mapthing_t* mt offset += mthing->options & MTF_AMBUSH ? 24*FRACUNIT : 0; } - if (!offset) // Snap to the surfaces when there's no offset set. + if (!(dz + offset)) // Snap to the surfaces when there's no offset set. { if (flip) return ONCEILINGZ; @@ -11699,7 +11699,7 @@ fixed_t P_GetMapThingSpawnHeight(const mobjtype_t mobjtype, const mapthing_t* mt return ONFLOORZ; } - return P_GetMobjSpawnHeight(mobjtype, x, y, offset, flip); + return P_GetMobjSpawnHeight(mobjtype, x, y, dz, offset, flip, mthing->scale); } static boolean P_SpawnNonMobjMapThing(mapthing_t *mthing) @@ -12583,10 +12583,16 @@ static boolean P_SetupSpawnedMapThing(mapthing_t *mthing, mobj_t *mobj, boolean break; } case MT_SKYBOX: + if (mthing->tag < 0 || mthing->tag > 15) + { + CONS_Debug(DBG_GAMELOGIC, "P_SetupSpawnedMapThing: Skybox ID %d of mapthing %s is not between 0 and 15!\n", mthing->tag, sizeu1((size_t)(mthing - mapthings))); + break; + } + if (mthing->options & MTF_OBJECTSPECIAL) - skyboxcenterpnts[mthing->extrainfo] = mobj; + skyboxcenterpnts[mthing->tag] = mobj; else - skyboxviewpnts[mthing->extrainfo] = mobj; + skyboxviewpnts[mthing->tag] = mobj; break; case MT_EGGSTATUE: if (mthing->options & MTF_EXTRA) @@ -13074,12 +13080,18 @@ static mobj_t *P_SpawnMobjFromMapThing(mapthing_t *mthing, fixed_t x, fixed_t y, mobj = P_SpawnMobj(x, y, z, i); mobj->spawnpoint = mthing; + P_SetScale(mobj, mthing->scale); + mobj->destscale = mthing->scale; + if (!P_SetupSpawnedMapThing(mthing, mobj, &doangle)) return mobj; if (doangle) mobj->angle = FixedAngle(mthing->angle << FRACBITS); + mobj->pitch = FixedAngle(mthing->pitch << FRACBITS); + mobj->roll = FixedAngle(mthing->roll << FRACBITS); + mthing->mobj = mobj; // ignore MTF_ flags and return early @@ -13176,7 +13188,7 @@ static void P_SpawnHoopInternal(mapthing_t *mthing, INT32 hoopsize, fixed_t size TVector v, *res; fixed_t x = mthing->x << FRACBITS; fixed_t y = mthing->y << FRACBITS; - fixed_t z = P_GetMobjSpawnHeight(MT_HOOP, x, y, mthing->z << FRACBITS, false); + fixed_t z = P_GetMobjSpawnHeight(MT_HOOP, x, y, mthing->z << FRACBITS, 0, false, mthing->scale); hoopcenter = P_SpawnMobj(x, y, z, MT_HOOPCENTER); hoopcenter->spawnpoint = mthing; @@ -13321,7 +13333,7 @@ static void P_SpawnItemRow(mapthing_t *mthing, mobjtype_t* itemtypes, UINT8 numi itemtypes[r] = P_GetMobjtypeSubstitute(&dummything, itemtypes[r]); } } - z = P_GetMobjSpawnHeight(itemtypes[0], x, y, z, mthing->options & MTF_OBJECTFLIP); + z = P_GetMobjSpawnHeight(itemtypes[0], x, y, z, 0, mthing->options & MTF_OBJECTFLIP, mthing->scale); for (r = 0; r < numitems; r++) { @@ -13379,7 +13391,7 @@ static void P_SpawnItemCircle(mapthing_t *mthing, mobjtype_t *itemtypes, UINT8 n itemtypes[i] = P_GetMobjtypeSubstitute(&dummything, itemtypes[i]); } } - z = P_GetMobjSpawnHeight(itemtypes[0], x, y, z, false); + z = P_GetMobjSpawnHeight(itemtypes[0], x, y, z, 0, false, mthing->scale); for (i = 0; i < numitems; i++) { diff --git a/src/p_mobj.h b/src/p_mobj.h index 643e3d04c..27a6ef4f0 100644 --- a/src/p_mobj.h +++ b/src/p_mobj.h @@ -278,7 +278,7 @@ typedef struct mobj_s struct mobj_s **sprev; // killough 8/11/98: change to ptr-to-ptr // More drawing info: to determine current sprite. - angle_t angle; // orientation + angle_t angle, pitch, roll; // orientation angle_t rollangle; spritenum_t sprite; // used to find patch_t and flip value UINT32 frame; // frame number, plus bits see p_pspr.h @@ -399,7 +399,7 @@ typedef struct precipmobj_s struct precipmobj_s **sprev; // killough 8/11/98: change to ptr-to-ptr // More drawing info: to determine current sprite. - angle_t angle; // orientation + angle_t angle, pitch, roll; // orientation angle_t rollangle; spritenum_t sprite; // used to find patch_t and flip value UINT32 frame; // frame number, plus bits see p_pspr.h @@ -452,7 +452,7 @@ void P_MovePlayerToSpawn(INT32 playernum, mapthing_t *mthing); void P_MovePlayerToStarpost(INT32 playernum); void P_AfterPlayerSpawn(INT32 playernum); -fixed_t P_GetMobjSpawnHeight(const mobjtype_t mobjtype, const fixed_t x, const fixed_t y, const fixed_t offset, const boolean flip); +fixed_t P_GetMobjSpawnHeight(const mobjtype_t mobjtype, const fixed_t x, const fixed_t y, const fixed_t dz, const fixed_t offset, const boolean flip, const fixed_t scale); fixed_t P_GetMapThingSpawnHeight(const mobjtype_t mobjtype, const mapthing_t* mthing, const fixed_t x, const fixed_t y); mobj_t *P_SpawnMapThing(mapthing_t *mthing); diff --git a/src/p_polyobj.c b/src/p_polyobj.c index ccf8519f6..b0a794ddf 100644 --- a/src/p_polyobj.c +++ b/src/p_polyobj.c @@ -204,47 +204,44 @@ boolean P_BBoxInsidePolyobj(polyobj_t *po, fixed_t *bbox) return true; } -// Finds the 'polyobject settings' linedef for a polyobject -// the polyobject's id should be set as its tag -static void Polyobj_GetInfo(polyobj_t *po) +// Gets the polyobject's settings from its first line +// args[0] of the first line should be the polyobject's id +static void Polyobj_GetInfo(polyobj_t *po, line_t *line) { - INT32 i = P_FindSpecialLineFromTag(POLYINFO_SPECIALNUM, po->id, -1); - - po->flags = POF_SOLID|POF_TESTHEIGHT|POF_RENDERSIDES; - - if (i == -1) - return; // no extra settings to apply, let's leave it - - po->parent = lines[i].frontsector->special; + po->parent = line->args[1]; if (po->parent == po->id) // do not allow a self-reference po->parent = -1; - po->translucency = (lines[i].flags & ML_DONTPEGTOP) - ? (sides[lines[i].sidenum[0]].textureoffset>>FRACBITS) - : ((lines[i].frontsector->floorheight>>FRACBITS) / 100); + po->translucency = max(min(line->args[2], NUMTRANSMAPS), 0); - po->translucency = max(min(po->translucency, NUMTRANSMAPS), 0); + po->flags = POF_SOLID|POF_TESTHEIGHT|POF_RENDERSIDES|POF_RENDERPLANES; - if (lines[i].flags & ML_EFFECT1) + if (line->args[3] & TMPF_NOINSIDES) po->flags |= POF_ONESIDE; - if (lines[i].flags & ML_EFFECT2) + if (line->args[3] & TMPF_INTANGIBLE) po->flags &= ~POF_SOLID; - if (lines[i].flags & ML_EFFECT3) + if (line->args[3] & TMPF_PUSHABLESTOP) po->flags |= POF_PUSHABLESTOP; - if (lines[i].flags & ML_EFFECT4) - po->flags |= POF_RENDERPLANES; + if (line->args[3] & TMPF_INVISIBLEPLANES) + po->flags &= ~POF_RENDERPLANES; - /*if (lines[i].flags & ML_EFFECT5) + /*if (line->args[3] & TMPF_DONTCLIPPLANES) po->flags &= ~POF_CLIPPLANES;*/ - if (lines[i].flags & ML_EFFECT6) + if (line->args[3] & TMPF_SPLAT) po->flags |= POF_SPLAT; - if (lines[i].flags & ML_NOCLIMB) // Has a linedef executor + if (line->args[3] & TMPF_EXECUTOR) // Has a linedef executor po->flags |= POF_LDEXEC; + + // TODO: support customized damage somehow? + if (line->args[3] & TMPF_CRUSH) + po->damage = 3; + + po->triggertag = line->args[4]; } // Reallocating array maintenance @@ -483,10 +480,6 @@ static void Polyobj_spawnPolyObj(INT32 num, mobj_t *spawnSpot, INT32 id) po->id = id; - // TODO: support customized damage somehow? - if (spawnSpot->info->doomednum == POLYOBJ_SPAWNCRUSH_DOOMEDNUM) - po->damage = 3; - // set to default thrust; may be modified by attached thinkers // TODO: support customized thrust? po->thrust = FRACUNIT; @@ -508,10 +501,10 @@ static void Polyobj_spawnPolyObj(INT32 num, mobj_t *spawnSpot, INT32 id) if (seg->linedef->special != POLYOBJ_START_LINE) continue; - if (seg->linedef->tag != po->id) + if (seg->linedef->args[0] != po->id) continue; - Polyobj_GetInfo(po); // apply extra settings if they exist! + Polyobj_GetInfo(po, seg->linedef); // apply extra settings if they exist! // save original flags and translucency to reference later for netgames! po->spawnflags = po->flags; @@ -564,9 +557,9 @@ static void Polyobj_moveToSpawnSpot(mapthing_t *anchor) vertex_t dist, sspot; size_t i; - if (!(po = Polyobj_GetForNum(anchor->angle))) + if (!(po = Polyobj_GetForNum(anchor->tag))) { - CONS_Debug(DBG_POLYOBJ, "Bad polyobject %d for anchor point\n", anchor->angle); + CONS_Debug(DBG_POLYOBJ, "Bad polyobject %d for anchor point\n", anchor->tag); return; } @@ -1314,8 +1307,7 @@ void Polyobj_InitLevel(void) mo = (mobj_t *)th; - if (mo->info->doomednum == POLYOBJ_SPAWN_DOOMEDNUM || - mo->info->doomednum == POLYOBJ_SPAWNCRUSH_DOOMEDNUM) + if (mo->info->doomednum == POLYOBJ_SPAWN_DOOMEDNUM) { ++numPolyObjects; @@ -1350,7 +1342,7 @@ void Polyobj_InitLevel(void) { qitem = (mobjqitem_t *)M_QueueIterator(&spawnqueue); - Polyobj_spawnPolyObj(i, qitem->mo, qitem->mo->spawnpoint->angle); + Polyobj_spawnPolyObj(i, qitem->mo, qitem->mo->spawnpoint->tag); } // move polyobjects to spawn points diff --git a/src/p_polyobj.h b/src/p_polyobj.h index c6ae716f4..f24caca4e 100644 --- a/src/p_polyobj.h +++ b/src/p_polyobj.h @@ -26,10 +26,8 @@ #define POLYOBJ_ANCHOR_DOOMEDNUM 760 #define POLYOBJ_SPAWN_DOOMEDNUM 761 -#define POLYOBJ_SPAWNCRUSH_DOOMEDNUM 762 // todo: REMOVE #define POLYOBJ_START_LINE 20 -#define POLYINFO_SPECIALNUM 22 typedef enum { @@ -52,6 +50,18 @@ typedef enum POF_SPLAT = 0x2000, ///< Use splat flat renderer (treat cyan pixels as invisible). } polyobjflags_e; +typedef enum +{ + TMPF_NOINSIDES = 1, + TMPF_INTANGIBLE = 1<<1, + TMPF_PUSHABLESTOP = 1<<2, + TMPF_INVISIBLEPLANES = 1<<3, + TMPF_EXECUTOR = 1<<4, + TMPF_CRUSH = 1<<5, + TMPF_SPLAT = 1<<6, + //TMPF_DONTCLIPPLANES = 1<<7, +} textmappolyobjectflags_t; + // // Polyobject Structure // @@ -97,6 +107,7 @@ typedef struct polyobj_s UINT8 isBad; // a bad polyobject: should not be rendered/manipulated INT32 translucency; // index to translucency tables + INT16 triggertag; // Tag of linedef executor to trigger on touch struct visplane_s *visplane; // polyobject's visplane, for ease of putting into the list later diff --git a/src/p_saveg.c b/src/p_saveg.c index dd4ade115..276b3eb05 100644 --- a/src/p_saveg.c +++ b/src/p_saveg.c @@ -787,10 +787,38 @@ static void P_NetUnArchiveWaypoints(void) #define LD_DIFF2 0x80 // diff2 flags -#define LD_S2TEXOFF 0x01 -#define LD_S2TOPTEX 0x02 -#define LD_S2BOTTEX 0x04 -#define LD_S2MIDTEX 0x08 +#define LD_S2TEXOFF 0x01 +#define LD_S2TOPTEX 0x02 +#define LD_S2BOTTEX 0x04 +#define LD_S2MIDTEX 0x08 +#define LD_ARGS 0x10 +#define LD_STRINGARGS 0x20 +#define LD_EXECUTORDELAY 0x40 + +static boolean P_AreArgsEqual(const line_t *li, const line_t *spawnli) +{ + UINT8 i; + for (i = 0; i < NUMLINEARGS; i++) + if (li->args[i] != spawnli->args[i]) + return false; + + return true; +} + +static boolean P_AreStringArgsEqual(const line_t *li, const line_t *spawnli) +{ + UINT8 i; + for (i = 0; i < NUMLINESTRINGARGS; i++) + { + if (!li->stringargs[i]) + return !spawnli->stringargs[i]; + + if (strcmp(li->stringargs[i], spawnli->stringargs[i])) + return false; + } + + return true; +} #define FD_FLAGS 0x01 #define FD_ALPHA 0x02 @@ -1085,6 +1113,15 @@ static void ArchiveLines(void) if (spawnli->special == 321 || spawnli->special == 322) // only reason li->callcount would be non-zero is if either of these are involved diff |= LD_CLLCOUNT; + if (!P_AreArgsEqual(li, spawnli)) + diff2 |= LD_ARGS; + + if (!P_AreStringArgsEqual(li, spawnli)) + diff2 |= LD_STRINGARGS; + + if (li->executordelay != spawnli->executordelay) + diff2 |= LD_EXECUTORDELAY; + if (li->sidenum[0] != 0xffff) { si = &sides[li->sidenum[0]]; @@ -1111,10 +1148,11 @@ static void ArchiveLines(void) diff2 |= LD_S2BOTTEX; if (si->midtexture != spawnsi->midtexture) diff2 |= LD_S2MIDTEX; - if (diff2) - diff |= LD_DIFF2; } + if (diff2) + diff |= LD_DIFF2; + if (diff) { WRITEINT16(save_p, i); @@ -1147,6 +1185,33 @@ static void ArchiveLines(void) WRITEINT32(save_p, si->bottomtexture); if (diff2 & LD_S2MIDTEX) WRITEINT32(save_p, si->midtexture); + if (diff2 & LD_ARGS) + { + UINT8 j; + for (j = 0; j < NUMLINEARGS; j++) + WRITEINT32(save_p, li->args[j]); + } + if (diff2 & LD_STRINGARGS) + { + UINT8 j; + for (j = 0; j < NUMLINESTRINGARGS; j++) + { + size_t len, k; + + if (!li->stringargs[j]) + { + WRITEINT32(save_p, 0); + continue; + } + + len = strlen(li->stringargs[j]); + WRITEINT32(save_p, len); + for (k = 0; k < len; k++) + WRITECHAR(save_p, li->stringargs[j][k]); + } + } + if (diff2 & LD_EXECUTORDELAY) + WRITEINT32(save_p, li->executordelay); } } WRITEUINT16(save_p, 0xffff); @@ -1202,6 +1267,36 @@ static void UnArchiveLines(void) si->bottomtexture = READINT32(save_p); if (diff2 & LD_S2MIDTEX) si->midtexture = READINT32(save_p); + if (diff2 & LD_ARGS) + { + UINT8 j; + for (j = 0; j < NUMLINEARGS; j++) + li->args[j] = READINT32(save_p); + } + if (diff2 & LD_STRINGARGS) + { + UINT8 j; + for (j = 0; j < NUMLINESTRINGARGS; j++) + { + size_t len = READINT32(save_p); + size_t k; + + if (!len) + { + Z_Free(li->stringargs[j]); + li->stringargs[j] = NULL; + continue; + } + + li->stringargs[j] = Z_Realloc(li->stringargs[j], len + 1, PU_LEVEL, NULL); + for (k = 0; k < len; k++) + li->stringargs[j][k] = READCHAR(save_p); + li->stringargs[j][len] = '\0'; + } + } + if (diff2 & LD_EXECUTORDELAY) + li->executordelay = READINT32(save_p); + } } @@ -1400,7 +1495,9 @@ static void SaveMobjThinker(const thinker_t *th, const UINT8 type) if ((mobj->x != mobj->spawnpoint->x << FRACBITS) || (mobj->y != mobj->spawnpoint->y << FRACBITS) || - (mobj->angle != FixedAngle(mobj->spawnpoint->angle*FRACUNIT))) + (mobj->angle != FixedAngle(mobj->spawnpoint->angle*FRACUNIT)) || + (mobj->pitch != FixedAngle(mobj->spawnpoint->pitch*FRACUNIT)) || + (mobj->roll != FixedAngle(mobj->spawnpoint->roll*FRACUNIT)) ) diff |= MD_POS; if (mobj->info->doomednum != mobj->spawnpoint->type) @@ -1556,6 +1653,8 @@ static void SaveMobjThinker(const thinker_t *th, const UINT8 type) WRITEFIXED(save_p, mobj->x); WRITEFIXED(save_p, mobj->y); WRITEANGLE(save_p, mobj->angle); + WRITEANGLE(save_p, mobj->pitch); + WRITEANGLE(save_p, mobj->roll); } if (diff & MD_MOM) { @@ -2513,12 +2612,16 @@ static thinker_t* LoadMobjThinker(actionf_p1 thinker) mobj->x = READFIXED(save_p); mobj->y = READFIXED(save_p); mobj->angle = READANGLE(save_p); + mobj->pitch = READANGLE(save_p); + mobj->roll = READANGLE(save_p); } else { mobj->x = mobj->spawnpoint->x << FRACBITS; mobj->y = mobj->spawnpoint->y << FRACBITS; mobj->angle = FixedAngle(mobj->spawnpoint->angle*FRACUNIT); + mobj->pitch = FixedAngle(mobj->spawnpoint->pitch*FRACUNIT); + mobj->roll = FixedAngle(mobj->spawnpoint->roll*FRACUNIT); } if (diff & MD_MOM) { diff --git a/src/p_setup.c b/src/p_setup.c index 2fd7ba5b0..ceb96df40 100644 --- a/src/p_setup.c +++ b/src/p_setup.c @@ -92,6 +92,7 @@ unsigned char mapmd5[16]; // Store VERTEXES, LINEDEFS, SIDEDEFS, etc. // +boolean udmf; size_t numvertexes, numsegs, numsectors, numsubsectors, numnodes, numlines, numsides, nummapthings; vertex_t *vertexes; seg_t *segs; @@ -355,8 +356,8 @@ static void P_ClearSingleMapHeaderInfo(INT16 i) mapheaderinfo[num]->mustrack = 0; mapheaderinfo[num]->muspos = 0; mapheaderinfo[num]->musinterfadeout = 0; - mapheaderinfo[num]->musintername[0] = '\0'; - mapheaderinfo[num]->muspostbossname[6] = 0; + mapheaderinfo[num]->musintername[0] = 0; + mapheaderinfo[num]->muspostbossname[0] = 0; mapheaderinfo[num]->muspostbosstrack = 0; mapheaderinfo[num]->muspostbosspos = 0; mapheaderinfo[num]->muspostbossfadein = 0; @@ -1039,6 +1040,8 @@ static void P_LoadSectors(UINT8 *data) ss->floorpic_angle = ss->ceilingpic_angle = 0; + ss->colormap_protected = false; + P_InitializeSector(ss); } } @@ -1145,6 +1148,10 @@ static void P_LoadLinedefs(UINT8 *data) ld->flags = SHORT(mld->flags); ld->special = SHORT(mld->special); ld->tag = SHORT(mld->tag); + memset(ld->args, 0, NUMLINEARGS*sizeof(*ld->args)); + memset(ld->stringargs, 0x00, NUMLINESTRINGARGS*sizeof(*ld->stringargs)); + ld->alpha = FRACUNIT; + ld->executordelay = 0; P_SetLinedefV1(i, SHORT(mld->v1)); P_SetLinedefV2(i, SHORT(mld->v2)); @@ -1218,9 +1225,11 @@ static void P_LoadSidedefs(UINT8 *data) case 455: // Fade colormaps! mazmazz 9/12/2018 (:flag_us:) // SoM: R_CreateColormap will only create a colormap in software mode... // Perhaps we should just call it instead of doing the calculations here. - sd->colormap_data = R_CreateColormap(msd->toptexture, msd->midtexture, - msd->bottomtexture); - sd->toptexture = sd->midtexture = sd->bottomtexture = 0; + if (!udmf) + { + sd->colormap_data = R_CreateColormapFromLinedef(msd->toptexture, msd->midtexture, msd->bottomtexture); + sd->toptexture = sd->midtexture = sd->bottomtexture = 0; + } break; case 413: // Change music @@ -1371,6 +1380,11 @@ static void P_LoadThings(UINT8 *data) mt->type = READUINT16(data); mt->options = READUINT16(data); mt->extrainfo = (UINT8)(mt->type >> 12); + mt->scale = FRACUNIT; + mt->tag = 0; + memset(mt->args, 0, NUMMAPTHINGARGS*sizeof(*mt->args)); + memset(mt->stringargs, 0x00, NUMMAPTHINGSTRINGARGS*sizeof(*mt->stringargs)); + mt->pitch = mt->roll = 0; mt->type &= 4095; @@ -1475,6 +1489,19 @@ static void ParseTextmapVertexParameter(UINT32 i, char *param, char *val) } } +typedef struct textmap_colormap_s { + boolean used; + INT32 lightcolor; + UINT8 lightalpha; + INT32 fadecolor; + UINT8 fadealpha; + UINT8 fadestart; + UINT8 fadeend; + UINT8 flags; +} textmap_colormap_t; + +textmap_colormap_t textmap_colormap = { false, 0, 25, 0, 25, 0, 31, 0 }; + static void ParseTextmapSectorParameter(UINT32 i, char *param, char *val) { if (fastcmp(param, "heightfloor")) @@ -1503,6 +1530,48 @@ static void ParseTextmapSectorParameter(UINT32 i, char *param, char *val) sectors[i].floorpic_angle = FixedAngle(FLOAT_TO_FIXED(atof(val))); else if (fastcmp(param, "rotationceiling")) sectors[i].ceilingpic_angle = FixedAngle(FLOAT_TO_FIXED(atof(val))); + else if (fastcmp(param, "lightcolor")) + { + textmap_colormap.used = true; + textmap_colormap.lightcolor = atol(val); + } + else if (fastcmp(param, "lightalpha")) + { + textmap_colormap.used = true; + textmap_colormap.lightalpha = atol(val); + } + else if (fastcmp(param, "fadecolor")) + { + textmap_colormap.used = true; + textmap_colormap.fadecolor = atol(val); + } + else if (fastcmp(param, "fadealpha")) + { + textmap_colormap.used = true; + textmap_colormap.fadealpha = atol(val); + } + else if (fastcmp(param, "fadestart")) + { + textmap_colormap.used = true; + textmap_colormap.fadestart = atol(val); + } + else if (fastcmp(param, "fadeend")) + { + textmap_colormap.used = true; + textmap_colormap.fadeend = atol(val); + } + else if (fastcmp(param, "colormapfog") && fastcmp("true", val)) + { + textmap_colormap.used = true; + textmap_colormap.flags |= CMF_FOG; + } + else if (fastcmp(param, "colormapfadesprites") && fastcmp("true", val)) + { + textmap_colormap.used = true; + textmap_colormap.flags |= CMF_FADEFULLBRIGHTSPRITES; + } + else if (fastcmp(param, "colormapprotected") && fastcmp("true", val)) + sectors[i].colormap_protected = true; } static void ParseTextmapSidedefParameter(UINT32 i, char *param, char *val) @@ -1533,10 +1602,29 @@ static void ParseTextmapLinedefParameter(UINT32 i, char *param, char *val) P_SetLinedefV1(i, atol(val)); else if (fastcmp(param, "v2")) P_SetLinedefV2(i, atol(val)); + else if (fastncmp(param, "arg", 3) && strlen(param) > 3) + { + size_t argnum = atol(param + 3); + if (argnum >= NUMLINEARGS) + return; + lines[i].args[argnum] = atol(val); + } + else if (fastncmp(param, "stringarg", 9) && strlen(param) > 9) + { + size_t argnum = param[9] - '0'; + if (argnum >= NUMLINESTRINGARGS) + return; + lines[i].stringargs[argnum] = Z_Malloc(strlen(val) + 1, PU_LEVEL, NULL); + M_Memcpy(lines[i].stringargs[argnum], val, strlen(val) + 1); + } else if (fastcmp(param, "sidefront")) lines[i].sidenum[0] = atol(val); else if (fastcmp(param, "sideback")) lines[i].sidenum[1] = atol(val); + else if (fastcmp(param, "alpha")) + lines[i].alpha = FLOAT_TO_FIXED(atof(val)); + else if (fastcmp(param, "executordelay")) + lines[i].executordelay = atol(val); // Flags else if (fastcmp(param, "blocking") && fastcmp("true", val)) @@ -1575,6 +1663,8 @@ static void ParseTextmapLinedefParameter(UINT32 i, char *param, char *val) static void ParseTextmapThingParameter(UINT32 i, char *param, char *val) { + if (fastcmp(param, "id")) + mapthings[i].tag = atol(val); if (fastcmp(param, "x")) mapthings[i].x = atol(val); else if (fastcmp(param, "y")) @@ -1583,18 +1673,39 @@ static void ParseTextmapThingParameter(UINT32 i, char *param, char *val) mapthings[i].z = atol(val); else if (fastcmp(param, "angle")) mapthings[i].angle = atol(val); + else if (fastcmp(param, "pitch")) + mapthings[i].pitch = atol(val); + else if (fastcmp(param, "roll")) + mapthings[i].roll = atol(val); else if (fastcmp(param, "type")) mapthings[i].type = atol(val); - + else if (fastcmp(param, "scale") || fastcmp(param, "scalex") || fastcmp(param, "scaley")) + mapthings[i].scale = FLOAT_TO_FIXED(atof(val)); // Flags else if (fastcmp(param, "extra") && fastcmp("true", val)) mapthings[i].options |= MTF_EXTRA; else if (fastcmp(param, "flip") && fastcmp("true", val)) mapthings[i].options |= MTF_OBJECTFLIP; - else if (fastcmp(param, "special") && fastcmp("true", val)) + else if (fastcmp(param, "objectspecial") && fastcmp("true", val)) mapthings[i].options |= MTF_OBJECTSPECIAL; else if (fastcmp(param, "ambush") && fastcmp("true", val)) mapthings[i].options |= MTF_AMBUSH; + + else if (fastncmp(param, "arg", 3) && strlen(param) > 3) + { + size_t argnum = atol(param + 3); + if (argnum >= NUMMAPTHINGARGS) + return; + mapthings[i].args[argnum] = atol(val); + } + else if (fastncmp(param, "stringarg", 9) && strlen(param) > 9) + { + size_t argnum = param[9] - '0'; + if (argnum >= NUMMAPTHINGSTRINGARGS) + return; + mapthings[i].stringargs[argnum] = Z_Malloc(strlen(val) + 1, PU_LEVEL, NULL); + M_Memcpy(mapthings[i].stringargs[argnum], val, strlen(val) + 1); + } } /** From a given position table, run a specified parser function through a {}-encapsuled text. @@ -1657,6 +1768,14 @@ static void TextmapFixFlatOffsets(sector_t *sec) } } +static INT32 P_ColorToRGBA(INT32 color, UINT8 alpha) +{ + UINT8 r = (color >> 16) & 0xFF; + UINT8 g = (color >> 8) & 0xFF; + UINT8 b = color & 0xFF; + return R_PutRgbaRGBA(r, g, b, alpha); +} + /** Loads the textmap data, after obtaining the elements count and allocating their respective space. */ static void P_LoadTextmap(void) @@ -1710,8 +1829,24 @@ static void P_LoadTextmap(void) sc->floorpic_angle = sc->ceilingpic_angle = 0; + sc->colormap_protected = false; + + textmap_colormap.used = false; + textmap_colormap.lightcolor = 0; + textmap_colormap.lightalpha = 25; + textmap_colormap.fadecolor = 0; + textmap_colormap.fadealpha = 25; + textmap_colormap.fadestart = 0; + textmap_colormap.fadeend = 31; + textmap_colormap.flags = 0; TextmapParse(sectorsPos[i], i, ParseTextmapSectorParameter); P_InitializeSector(sc); + if (textmap_colormap.used) + { + INT32 rgba = P_ColorToRGBA(textmap_colormap.lightcolor, textmap_colormap.lightalpha); + INT32 fadergba = P_ColorToRGBA(textmap_colormap.fadecolor, textmap_colormap.fadealpha); + sc->extra_colormap = sc->spawn_extra_colormap = R_CreateColormap(rgba, fadergba, textmap_colormap.fadestart, textmap_colormap.fadeend, textmap_colormap.flags); + } TextmapFixFlatOffsets(sc); } @@ -1722,6 +1857,10 @@ static void P_LoadTextmap(void) ld->flags = 0; ld->special = 0; ld->tag = 0; + memset(ld->args, 0, NUMLINEARGS*sizeof(*ld->args)); + memset(ld->stringargs, 0x00, NUMLINESTRINGARGS*sizeof(*ld->stringargs)); + ld->alpha = FRACUNIT; + ld->executordelay = 0; ld->sidenum[0] = 0xffff; ld->sidenum[1] = 0xffff; @@ -1760,11 +1899,15 @@ static void P_LoadTextmap(void) { // Defaults. mt->x = mt->y = 0; - mt->angle = 0; + mt->angle = mt->pitch = mt->roll = 0; mt->type = 0; mt->options = 0; mt->z = 0; mt->extrainfo = 0; + mt->scale = FRACUNIT; + mt->tag = 0; + memset(mt->args, 0, NUMMAPTHINGARGS*sizeof(*mt->args)); + memset(mt->stringargs, 0x00, NUMMAPTHINGSTRINGARGS*sizeof(*mt->stringargs)); mt->mobj = NULL; TextmapParse(mapthingsPos[i], i, ParseTextmapThingParameter); @@ -1780,9 +1923,9 @@ static void P_ProcessLinedefsAfterSidedefs(void) ld->frontsector = sides[ld->sidenum[0]].sector; //e6y: Can't be -1 here ld->backsector = ld->sidenum[1] != 0xffff ? sides[ld->sidenum[1]].sector : 0; - // Compile linedef 'text' from both sidedefs 'text' for appropriate specials. switch (ld->special) { + // Compile linedef 'text' from both sidedefs 'text' for appropriate specials. case 331: // Trigger linedef executor: Skin - Continuous case 332: // Trigger linedef executor: Skin - Each time case 333: // Trigger linedef executor: Skin - Once @@ -1798,6 +1941,41 @@ static void P_ProcessLinedefsAfterSidedefs(void) M_Memcpy(ld->text + strlen(ld->text) + 1, sides[ld->sidenum[1]].text, strlen(sides[ld->sidenum[1]].text) + 1); } break; + case 447: // Change colormap + case 455: // Fade colormap + if (udmf) + break; + if (ld->flags & ML_DONTPEGBOTTOM) // alternate alpha (by texture offsets) + { + extracolormap_t *exc = R_CopyColormap(sides[ld->sidenum[0]].colormap_data, false); + INT16 alpha = max(min(sides[ld->sidenum[0]].textureoffset >> FRACBITS, 25), -25); + INT16 fadealpha = max(min(sides[ld->sidenum[0]].rowoffset >> FRACBITS, 25), -25); + + // If alpha is negative, set "subtract alpha" flag and store absolute value + if (alpha < 0) + { + alpha *= -1; + ld->args[2] |= TMCF_SUBLIGHTA; + } + if (fadealpha < 0) + { + fadealpha *= -1; + ld->args[2] |= TMCF_SUBFADEA; + } + + exc->rgba = R_GetRgbaRGB(exc->rgba) + R_PutRgbaA(alpha); + exc->fadergba = R_GetRgbaRGB(exc->fadergba) + R_PutRgbaA(fadealpha); + + if (!(sides[ld->sidenum[0]].colormap_data = R_GetColormapFromList(exc))) + { + exc->colormap = R_CreateLightTable(exc); + R_AddColormapToList(exc); + sides[ld->sidenum[0]].colormap_data = exc; + } + else + Z_Free(exc); + } + break; } } } @@ -1805,11 +1983,11 @@ static void P_ProcessLinedefsAfterSidedefs(void) static boolean P_LoadMapData(const virtres_t *virt) { virtlump_t *virtvertexes = NULL, *virtsectors = NULL, *virtsidedefs = NULL, *virtlinedefs = NULL, *virtthings = NULL; - virtlump_t *textmap = vres_Find(virt, "TEXTMAP"); // Count map data. - if (textmap) // Count how many entries for each type we got in textmap. + if (udmf) // Count how many entries for each type we got in textmap. { + virtlump_t *textmap = vres_Find(virt, "TEXTMAP"); if (!TextmapCount(textmap->data, textmap->size)) return false; } @@ -1864,7 +2042,7 @@ static boolean P_LoadMapData(const virtres_t *virt) numlevelflats = 0; // Load map data. - if (textmap) + if (udmf) P_LoadTextmap(); else { @@ -1972,7 +2150,12 @@ static void P_InitializeSeg(seg_t *seg) { if (seg->linedef) { - seg->sidedef = &sides[seg->linedef->sidenum[seg->side]]; + UINT16 side = seg->linedef->sidenum[seg->side]; + + if (side == 0xffff) + I_Error("P_InitializeSeg: Seg %s refers to side %d of linedef %s, which doesn't exist!\n", sizeu1((size_t)(seg - segs)), seg->side, sizeu1((size_t)(seg->linedef - lines))); + + seg->sidedef = &sides[side]; seg->frontsector = seg->sidedef->sector; seg->backsector = (seg->linedef->flags & ML_TWOSIDED) ? sides[seg->linedef->sidenum[seg->side ^ 1]].sector : NULL; @@ -2041,7 +2224,7 @@ static nodetype_t P_GetNodetype(const virtres_t *virt, UINT8 **nodedata) nodetype_t nodetype = NT_UNSUPPORTED; char signature[4 + 1]; - if (vres_Find(virt, "TEXTMAP")) + if (udmf) { *nodedata = vres_Find(virt, "ZNODES")->data; supported[NT_XGLN] = supported[NT_XGL3] = true; @@ -2166,10 +2349,8 @@ static boolean P_LoadExtendedSubsectorsAndSegs(UINT8 **data, nodetype_t nodetype segs[k - 1 + ((m == 0) ? subsectors[i].numlines : 0)].v2 = segs[k].v1 = &vertexes[vertexnum]; READUINT32((*data)); // partner, can be ignored by software renderer - if (nodetype == NT_XGL3) - READUINT16((*data)); // Line number is 32-bit in XGL3, but we're limited to 16 bits. - linenum = READUINT16((*data)); + linenum = (nodetype == NT_XGL3) ? READUINT32((*data)) : READUINT16((*data)); if (linenum != 0xFFFF && linenum >= numlines) I_Error("P_LoadExtendedSubsectorsAndSegs: Seg %s in subsector %d has invalid linedef %d!\n", sizeu1(k), m, linenum); segs[k].glseg = (linenum == 0xFFFF); @@ -2737,6 +2918,259 @@ static void P_LinkMapData(void) } } +/** Hashes the sector tags across the sectors and linedefs. + * + * \sa P_FindSectorFromTag, P_ChangeSectorTag + * \author Lee Killough + */ +static inline void P_InitTagLists(void) +{ + register size_t i; + + for (i = numsectors - 1; i != (size_t)-1; i--) + { + size_t j = (unsigned)sectors[i].tag % numsectors; + sectors[i].nexttag = sectors[j].firsttag; + sectors[j].firsttag = (INT32)i; + } + + for (i = numlines - 1; i != (size_t)-1; i--) + { + size_t j = (unsigned)lines[i].tag % numlines; + lines[i].nexttag = lines[j].firsttag; + lines[j].firsttag = (INT32)i; + } +} + +//For maps in binary format, converts setup of specials to UDMF format. +static void P_ConvertBinaryMap(void) +{ + size_t i; + + for (i = 0; i < numlines; i++) + { + switch (lines[i].special) + { + case 20: //PolyObject first line + { + INT32 paramline = P_FindSpecialLineFromTag(22, lines[i].tag, -1); + + //PolyObject ID + lines[i].args[0] = lines[i].tag; + + //Default: Invisible planes + lines[i].args[3] |= TMPF_INVISIBLEPLANES; + + //Linedef executor tag + lines[i].args[4] = 32000 + lines[i].args[0]; + + if (paramline == -1) + break; // no extra settings to apply, let's leave it + + //Parent ID + lines[i].args[1] = lines[paramline].frontsector->special; + //Translucency + lines[i].args[2] = (lines[paramline].flags & ML_DONTPEGTOP) + ? (sides[lines[paramline].sidenum[0]].textureoffset >> FRACBITS) + : ((lines[paramline].frontsector->floorheight >> FRACBITS) / 100); + + //Flags + if (lines[paramline].flags & ML_EFFECT1) + lines[i].args[3] |= TMPF_NOINSIDES; + if (lines[paramline].flags & ML_EFFECT2) + lines[i].args[3] |= TMPF_INTANGIBLE; + if (lines[paramline].flags & ML_EFFECT3) + lines[i].args[3] |= TMPF_PUSHABLESTOP; + if (lines[paramline].flags & ML_EFFECT4) + lines[i].args[3] &= ~TMPF_INVISIBLEPLANES; + /*if (lines[paramline].flags & ML_EFFECT5) + lines[i].args[3] |= TMPF_DONTCLIPPLANES;*/ + if (lines[paramline].flags & ML_EFFECT6) + lines[i].args[3] |= TMPF_SPLAT; + if (lines[paramline].flags & ML_NOCLIMB) + lines[i].args[3] |= TMPF_EXECUTOR; + + break; + } + case 443: //Call Lua function + if (lines[i].text) + { + lines[i].stringargs[0] = Z_Malloc(strlen(lines[i].text) + 1, PU_LEVEL, NULL); + M_Memcpy(lines[i].stringargs[0], lines[i].text, strlen(lines[i].text) + 1); + } + else + CONS_Alert(CONS_WARNING, "Linedef %s is missing the hook name of the Lua function to call! (This should be given in the front texture fields)\n", sizeu1(i)); + break; + case 447: //Change colormap + lines[i].args[0] = lines[i].tag; + if (lines[i].flags & ML_EFFECT3) + lines[i].args[2] |= TMCF_RELATIVE; + if (lines[i].flags & ML_EFFECT1) + lines[i].args[2] |= TMCF_SUBLIGHTR|TMCF_SUBFADER; + if (lines[i].flags & ML_NOCLIMB) + lines[i].args[2] |= TMCF_SUBLIGHTG|TMCF_SUBFADEG; + if (lines[i].flags & ML_EFFECT2) + lines[i].args[2] |= TMCF_SUBLIGHTB|TMCF_SUBFADEB; + break; + case 455: //Fade colormap + { + INT32 speed = (INT32)((((lines[i].flags & ML_DONTPEGBOTTOM) || !sides[lines[i].sidenum[0]].rowoffset) && lines[i].sidenum[1] != 0xFFFF) ? + abs(sides[lines[i].sidenum[1]].rowoffset >> FRACBITS) + : abs(sides[lines[i].sidenum[0]].rowoffset >> FRACBITS)); + + lines[i].args[0] = lines[i].tag; + if (lines[i].flags & ML_EFFECT4) + lines[i].args[2] = speed; + else + lines[i].args[2] = (256 + speed - 1)/speed; + if (lines[i].flags & ML_EFFECT3) + lines[i].args[3] |= TMCF_RELATIVE; + if (lines[i].flags & ML_EFFECT1) + lines[i].args[3] |= TMCF_SUBLIGHTR|TMCF_SUBFADER; + if (lines[i].flags & ML_NOCLIMB) + lines[i].args[3] |= TMCF_SUBLIGHTG|TMCF_SUBFADEG; + if (lines[i].flags & ML_EFFECT2) + lines[i].args[3] |= TMCF_SUBLIGHTB|TMCF_SUBFADEB; + if (lines[i].flags & ML_BOUNCY) + lines[i].args[3] |= TMCF_FROMBLACK; + if (lines[i].flags & ML_EFFECT5) + lines[i].args[3] |= TMCF_OVERRIDE; + break; + } + case 456: //Stop fading colormap + lines[i].args[0] = lines[i].tag; + break; + case 606: //Colormap + lines[i].args[0] = lines[i].tag; + break; + case 700: //Slope front sector floor + case 701: //Slope front sector ceiling + case 702: //Slope front sector floor and ceiling + case 703: //Slope front sector floor and back sector ceiling + case 710: //Slope back sector floor + case 711: //Slope back sector ceiling + case 712: //Slope back sector floor and ceiling + case 713: //Slope back sector floor and front sector ceiling + { + boolean frontfloor = (lines[i].special == 700 || lines[i].special == 702 || lines[i].special == 703); + boolean backfloor = (lines[i].special == 710 || lines[i].special == 712 || lines[i].special == 713); + boolean frontceil = (lines[i].special == 701 || lines[i].special == 702 || lines[i].special == 713); + boolean backceil = (lines[i].special == 711 || lines[i].special == 712 || lines[i].special == 703); + + lines[i].args[0] = backfloor ? TMS_BACK : (frontfloor ? TMS_FRONT : TMS_NONE); + lines[i].args[1] = backceil ? TMS_BACK : (frontceil ? TMS_FRONT : TMS_NONE); + + if (lines[i].flags & ML_NETONLY) + lines[i].args[2] |= TMSL_NOPHYSICS; + if (lines[i].flags & ML_NONET) + lines[i].args[2] |= TMSL_DYNAMIC; + + lines[i].special = 700; + break; + } + case 704: //Slope front sector floor by 3 tagged vertices + case 705: //Slope front sector ceiling by 3 tagged vertices + case 714: //Slope back sector floor by 3 tagged vertices + case 715: //Slope back sector ceiling by 3 tagged vertices + { + if (lines[i].special == 704) + lines[i].args[0] = TMSP_FRONTFLOOR; + else if (lines[i].special == 705) + lines[i].args[0] = TMSP_FRONTCEILING; + else if (lines[i].special == 714) + lines[i].args[0] = TMSP_BACKFLOOR; + else if (lines[i].special == 715) + lines[i].args[0] = TMSP_BACKCEILING; + + lines[i].args[1] = lines[i].tag; + + if (lines[i].flags & ML_EFFECT6) + { + UINT8 side = lines[i].special >= 714; + + if (side == 1 && lines[i].sidenum[1] == 0xffff) + CONS_Debug(DBG_GAMELOGIC, "P_ConvertBinaryMap: Line special %d (line #%s) missing 2nd side!\n", lines[i].special, sizeu1(i)); + else + { + lines[i].args[2] = sides[lines[i].sidenum[side]].textureoffset >> FRACBITS; + lines[i].args[3] = sides[lines[i].sidenum[side]].rowoffset >> FRACBITS; + } + } + else + { + lines[i].args[2] = lines[i].args[1]; + lines[i].args[3] = lines[i].args[1]; + } + + if (lines[i].flags & ML_NETONLY) + lines[i].args[4] |= TMSL_NOPHYSICS; + if (lines[i].flags & ML_NONET) + lines[i].args[4] |= TMSL_DYNAMIC; + + lines[i].special = 704; + break; + } + case 720: //Copy front side floor slope + case 721: //Copy front side ceiling slope + case 722: //Copy front side floor and ceiling slope + if (lines[i].special != 721) + lines[i].args[0] = lines[i].tag; + if (lines[i].special != 720) + lines[i].args[1] = lines[i].tag; + lines[i].special = 720; + break; + case 900: //Translucent wall (10%) + case 901: //Translucent wall (20%) + case 902: //Translucent wall (30%) + case 903: //Translucent wall (40%) + case 904: //Translucent wall (50%) + case 905: //Translucent wall (60%) + case 906: //Translucent wall (70%) + case 907: //Translucent wall (80%) + case 908: //Translucent wall (90%) + lines[i].alpha = ((909 - lines[i].special) << FRACBITS)/10; + break; + default: + break; + } + + //Linedef executor delay + if (lines[i].special >= 400 && lines[i].special < 500) + { + //Dummy value to indicate that this executor is delayed. + //The real value is taken from the back sector at runtime. + if (lines[i].flags & ML_DONTPEGTOP) + lines[i].executordelay = 1; + } + } + + for (i = 0; i < nummapthings; i++) + { + switch (mapthings[i].type) + { + case 750: + case 760: + case 761: + mapthings[i].tag = mapthings[i].angle; + break; + case 762: + { + INT32 firstline = P_FindSpecialLineFromTag(20, mapthings[i].angle, -1); + if (firstline != -1) + lines[firstline].args[3] |= TMPF_CRUSH; + mapthings[i].tag = mapthings[i].angle; + mapthings[i].type = 761; + break; + } + case 780: + mapthings[i].tag = mapthings[i].extrainfo; + break; + default: + break; + } + } +} + /** Compute MD5 message digest for bytes read from memory source * * The resulting message digest number will be written into the 16 bytes @@ -2765,11 +3199,13 @@ static INT32 P_MakeBufferMD5(const char *buffer, size_t len, void *resblock) static void P_MakeMapMD5(virtres_t *virt, void *dest) { - virtlump_t *textmap = vres_Find(virt, "TEXTMAP"); unsigned char resmd5[16]; - if (textmap) + if (udmf) + { + virtlump_t *textmap = vres_Find(virt, "TEXTMAP"); P_MakeBufferMD5((char*)textmap->data, textmap->size, resmd5); + } else { unsigned char linemd5[16]; @@ -2800,6 +3236,8 @@ static void P_MakeMapMD5(virtres_t *virt, void *dest) static boolean P_LoadMapFromFile(void) { virtres_t *virt = vres_GetMap(lastloadedmaplumpnum); + virtlump_t *textmap = vres_Find(virt, "TEXTMAP"); + udmf = textmap != NULL; if (!P_LoadMapData(virt)) return false; @@ -2808,6 +3246,11 @@ static boolean P_LoadMapFromFile(void) P_LinkMapData(); + P_InitTagLists(); // Create xref tables for tags + + if (!udmf) + P_ConvertBinaryMap(); + // Copy relevant map data for NetArchive purposes. spawnsectors = Z_Calloc(numsectors * sizeof(*sectors), PU_LEVEL, NULL); spawnlines = Z_Calloc(numlines * sizeof(*lines), PU_LEVEL, NULL); @@ -3682,8 +4125,7 @@ boolean P_LoadLevel(boolean fromnetsave) if (!P_LoadMapFromFile()) return false; - // init gravity, tag lists, - // anything that P_SpawnSlopes/P_LoadThings needs to know + // init anything that P_SpawnSlopes/P_LoadThings needs to know P_InitSpecials(); P_SpawnSlopes(fromnetsave); diff --git a/src/p_slopes.c b/src/p_slopes.c index 6aeb1b025..e93b0f6c9 100644 --- a/src/p_slopes.c +++ b/src/p_slopes.c @@ -245,32 +245,30 @@ static void line_SpawnViaLine(const int linenum, const boolean spawnthinker) // because checking to see if a slope had changed will waste more memory than // if the slope was just updated when called line_t *line = lines + linenum; - INT16 special = line->special; pslope_t *fslope = NULL, *cslope = NULL; vector3_t origin, point; vector2_t direction; fixed_t nx, ny, dz, extent; - boolean frontfloor = (special == 700 || special == 702 || special == 703); - boolean backfloor = (special == 710 || special == 712 || special == 713); - boolean frontceil = (special == 701 || special == 702 || special == 713); - boolean backceil = (special == 711 || special == 712 || special == 703); - + boolean frontfloor = line->args[0] == TMS_FRONT; + boolean backfloor = line->args[0] == TMS_BACK; + boolean frontceil = line->args[1] == TMS_FRONT; + boolean backceil = line->args[1] == TMS_BACK; UINT8 flags = 0; // Slope flags - if (line->flags & ML_NETONLY) + if (line->args[2] & TMSL_NOPHYSICS) flags |= SL_NOPHYSICS; - if (line->flags & ML_NONET) + if (line->args[2] & TMSL_DYNAMIC) flags |= SL_DYNAMIC; if(!frontfloor && !backfloor && !frontceil && !backceil) { - CONS_Printf("P_SpawnSlope_Line called with non-slope line special.\n"); + CONS_Printf("line_SpawnViaLine: Slope special with nothing to do.\n"); return; } if(!line->frontsector || !line->backsector) { - CONS_Debug(DBG_SETUP, "P_SpawnSlope_Line used on a line without two sides. (line number %i)\n", linenum); + CONS_Debug(DBG_SETUP, "line_SpawnViaLine: Slope special used on a line without two sides. (line number %i)\n", linenum); return; } @@ -297,7 +295,7 @@ static void line_SpawnViaLine(const int linenum, const boolean spawnthinker) if(extent < 0) { - CONS_Printf("P_SpawnSlope_Line failed to get frontsector extent on line number %i\n", linenum); + CONS_Printf("line_SpawnViaLine failed to get frontsector extent on line number %i\n", linenum); return; } @@ -363,7 +361,7 @@ static void line_SpawnViaLine(const int linenum, const boolean spawnthinker) if(extent < 0) { - CONS_Printf("P_SpawnSlope_Line failed to get backsector extent on line number %i\n", linenum); + CONS_Printf("line_SpawnViaLine failed to get backsector extent on line number %i\n", linenum); return; } @@ -428,11 +426,11 @@ static pslope_t *MakeViaMapthings(INT16 tag1, INT16 tag2, INT16 tag3, UINT8 flag if (mt->type != 750) // Haha, I'm hijacking the old Chaos Spawn thingtype for something! continue; - if (!vertices[0] && mt->angle == tag1) + if (!vertices[0] && mt->tag == tag1) vertices[0] = mt; - else if (!vertices[1] && mt->angle == tag2) + else if (!vertices[1] && mt->tag == tag2) vertices[1] = mt; - else if (!vertices[2] && mt->angle == tag3) + else if (!vertices[2] && mt->tag == tag3) vertices[2] = mt; } @@ -462,44 +460,36 @@ static void line_SpawnViaMapthingVertexes(const int linenum, const boolean spawn line_t *line = lines + linenum; side_t *side; pslope_t **slopetoset; - UINT16 tag1, tag2, tag3; - - UINT8 flags = 0; - if (line->flags & ML_NETONLY) + UINT16 tag1 = line->args[1]; + UINT16 tag2 = line->args[2]; + UINT16 tag3 = line->args[3]; + UINT8 flags = 0; // Slope flags + if (line->args[4] & TMSL_NOPHYSICS) flags |= SL_NOPHYSICS; - if (line->flags & ML_NONET) + if (line->args[4] & TMSL_DYNAMIC) flags |= SL_DYNAMIC; - switch(line->special) + switch(line->args[0]) { - case 704: + case TMSP_FRONTFLOOR: slopetoset = &line->frontsector->f_slope; side = &sides[line->sidenum[0]]; break; - case 705: + case TMSP_FRONTCEILING: slopetoset = &line->frontsector->c_slope; side = &sides[line->sidenum[0]]; break; - case 714: + case TMSP_BACKFLOOR: slopetoset = &line->backsector->f_slope; side = &sides[line->sidenum[1]]; break; - case 715: + case TMSP_BACKCEILING: slopetoset = &line->backsector->c_slope; side = &sides[line->sidenum[1]]; default: return; } - if (line->flags & ML_EFFECT6) - { - tag1 = line->tag; - tag2 = side->textureoffset >> FRACBITS; - tag3 = side->rowoffset >> FRACBITS; - } - else - tag1 = tag2 = tag3 = line->tag; - *slopetoset = MakeViaMapthings(tag1, tag2, tag3, flags, spawnthinker); side->sector->hasslope = true; @@ -555,6 +545,47 @@ static void SpawnVertexSlopes(void) } } +static boolean P_SetSlopeFromTag(sector_t *sec, INT32 tag, boolean ceiling) +{ + INT32 i; + pslope_t **secslope = ceiling ? &sec->c_slope : &sec->f_slope; + + if (!tag || *secslope) + return false; + + for (i = -1; (i = P_FindSectorFromTag(tag, i)) >= 0;) + { + pslope_t *srcslope = ceiling ? sectors[i].c_slope : sectors[i].f_slope; + if (srcslope) + { + *secslope = srcslope; + return true; + } + } + return false; +} + +static boolean P_CopySlope(pslope_t **toslope, pslope_t *fromslope) +{ + if (*toslope || !fromslope) + return true; + + *toslope = fromslope; + return true; +} + +static void P_UpdateHasSlope(sector_t *sec) +{ + size_t i; + + sec->hasslope = true; + + // if this is an FOF control sector, make sure any target sectors also are marked as having slopes + if (sec->numattached) + for (i = 0; i < sec->numattached; i++) + sectors[sec->attached[i]].hasslope = true; +} + // // P_CopySectorSlope // @@ -563,25 +594,31 @@ static void SpawnVertexSlopes(void) void P_CopySectorSlope(line_t *line) { sector_t *fsec = line->frontsector; - int i, special = line->special; + sector_t *bsec = line->backsector; + boolean setfront = false; + boolean setback = false; - // Check for copy linedefs - for (i = -1; (i = P_FindSectorFromTag(line->tag, i)) >= 0;) + setfront |= P_SetSlopeFromTag(fsec, line->args[0], false); + setfront |= P_SetSlopeFromTag(fsec, line->args[1], true); + if (bsec) { - sector_t *srcsec = sectors + i; + setback |= P_SetSlopeFromTag(bsec, line->args[2], false); + setback |= P_SetSlopeFromTag(bsec, line->args[3], true); - if ((special - 719) & 1 && !fsec->f_slope && srcsec->f_slope) - fsec->f_slope = srcsec->f_slope; //P_CopySlope(srcsec->f_slope); - if ((special - 719) & 2 && !fsec->c_slope && srcsec->c_slope) - fsec->c_slope = srcsec->c_slope; //P_CopySlope(srcsec->c_slope); + if (line->args[4] & TMSC_FRONTTOBACKFLOOR) + setback |= P_CopySlope(&bsec->f_slope, fsec->f_slope); + if (line->args[4] & TMSC_BACKTOFRONTFLOOR) + setfront |= P_CopySlope(&fsec->f_slope, bsec->f_slope); + if (line->args[4] & TMSC_FRONTTOBACKCEILING) + setback |= P_CopySlope(&bsec->c_slope, fsec->c_slope); + if (line->args[4] & TMSC_BACKTOFRONTCEILING) + setfront |= P_CopySlope(&fsec->c_slope, bsec->c_slope); } - fsec->hasslope = true; - - // if this is an FOF control sector, make sure any target sectors also are marked as having slopes - if (fsec->numattached) - for (i = 0; i < (int)fsec->numattached; i++) - sectors[fsec->attached[i]].hasslope = true; + if (setfront) + P_UpdateHasSlope(fsec); + if (setback) + P_UpdateHasSlope(bsec); line->special = 0; // Linedef was use to set slopes, it finished its job, so now make it a normal linedef } @@ -614,20 +651,10 @@ void P_SpawnSlopes(const boolean fromsave) { switch (lines[i].special) { case 700: - case 701: - case 702: - case 703: - case 710: - case 711: - case 712: - case 713: line_SpawnViaLine(i, !fromsave); break; case 704: - case 705: - case 714: - case 715: line_SpawnViaMapthingVertexes(i, !fromsave); break; @@ -642,8 +669,6 @@ void P_SpawnSlopes(const boolean fromsave) { switch (lines[i].special) { case 720: - case 721: - case 722: P_CopySectorSlope(&lines[i]); default: break; diff --git a/src/p_slopes.h b/src/p_slopes.h index 06d900b66..46e8dc1e7 100644 --- a/src/p_slopes.h +++ b/src/p_slopes.h @@ -18,6 +18,35 @@ extern pslope_t *slopelist; extern UINT16 slopecount; +typedef enum +{ + TMSP_FRONTFLOOR, + TMSP_FRONTCEILING, + TMSP_BACKFLOOR, + TMSP_BACKCEILING, +} textmapslopeplane_t; + +typedef enum +{ + TMSC_FRONTTOBACKFLOOR = 1, + TMSC_BACKTOFRONTFLOOR = 1<<1, + TMSC_FRONTTOBACKCEILING = 1<<2, + TMSC_BACKTOFRONTCEILING = 1<<3, +} textmapslopecopy_t; + +typedef enum +{ + TMS_NONE, + TMS_FRONT, + TMS_BACK, +} textmapside_t; + +typedef enum +{ + TMSL_NOPHYSICS = 1, + TMSL_DYNAMIC = 2, +} textmapslopeflags_t; + void P_LinkSlopeThinkers (void); void P_CalculateSlopeNormal(pslope_t *slope); diff --git a/src/p_spec.c b/src/p_spec.c index b7fdedfd0..f30e25f7f 100644 --- a/src/p_spec.c +++ b/src/p_spec.c @@ -1496,30 +1496,6 @@ void P_RunNightsCapsuleTouchExecutors(mobj_t *actor, boolean entering, boolean e } } -/** Hashes the sector tags across the sectors and linedefs. - * - * \sa P_FindSectorFromTag, P_ChangeSectorTag - * \author Lee Killough - */ -static inline void P_InitTagLists(void) -{ - register size_t i; - - for (i = numsectors - 1; i != (size_t)-1; i--) - { - size_t j = (unsigned)sectors[i].tag % numsectors; - sectors[i].nexttag = sectors[j].firsttag; - sectors[j].firsttag = (INT32)i; - } - - for (i = numlines - 1; i != (size_t)-1; i--) - { - size_t j = (unsigned)lines[i].tag % numlines; - lines[i].nexttag = lines[j].firsttag; - lines[j].firsttag = (INT32)i; - } -} - /** Finds minimum light from an adjacent sector. * * \param sector Sector to start in. @@ -1563,16 +1539,24 @@ void T_ExecutorDelay(executor_t *e) static void P_AddExecutorDelay(line_t *line, mobj_t *mobj, sector_t *sector) { executor_t *e; + INT32 delay; - if (!line->backsector) - I_Error("P_AddExecutorDelay: Line has no backsector!\n"); + if (udmf) + delay = line->executordelay; + else + { + if (!line->backsector) + I_Error("P_AddExecutorDelay: Line has no backsector!\n"); + + delay = (line->backsector->ceilingheight >> FRACBITS) + (line->backsector->floorheight >> FRACBITS); + } e = Z_Calloc(sizeof (*e), PU_LEVSPEC, NULL); e->thinker.function.acp1 = (actionf_p1)T_ExecutorDelay; e->line = line; e->sector = sector; - e->timer = (line->backsector->ceilingheight>>FRACBITS)+(line->backsector->floorheight>>FRACBITS); + e->timer = delay; P_SetTarget(&e->caller, mobj); // Use P_SetTarget to make sure the mobj doesn't get freed while we're delaying. P_AddThinker(THINK_MAIN, &e->thinker); } @@ -1973,7 +1957,7 @@ boolean P_RunTriggerLinedef(line_t *triggerline, mobj_t *actor, sector_t *caller if (ctlsector->lines[i]->special >= 400 && ctlsector->lines[i]->special < 500) { - if (ctlsector->lines[i]->flags & ML_DONTPEGTOP) + if (ctlsector->lines[i]->executordelay) P_AddExecutorDelay(ctlsector->lines[i], actor, caller); else P_ProcessLineSpecial(ctlsector->lines[i], actor, caller); @@ -2061,7 +2045,7 @@ boolean P_RunTriggerLinedef(line_t *triggerline, mobj_t *actor, sector_t *caller if (ctlsector->lines[i]->special >= 400 && ctlsector->lines[i]->special < 500) { - if (ctlsector->lines[i]->flags & ML_DONTPEGTOP) + if (ctlsector->lines[i]->executordelay) P_AddExecutorDelay(ctlsector->lines[i], actor, caller); else P_ProcessLineSpecial(ctlsector->lines[i], actor, caller); @@ -3294,10 +3278,10 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) } case 443: // Calls a named Lua function - if (line->text) + if (line->stringargs[0]) LUAh_LinedefExecute(line, mo, callsec); else - CONS_Alert(CONS_WARNING, "Linedef %s is missing the hook name of the Lua function to call! (This should be given in the front texture fields)\n", sizeu1(line-lines)); + CONS_Alert(CONS_WARNING, "Linedef %s is missing the hook name of the Lua function to call! (This should be given in arg0str)\n", sizeu1(line-lines)); break; case 444: // Earthquake camera @@ -3420,46 +3404,53 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) // Except it is activated by linedef executor, not level load // This could even override existing colormaps I believe // -- Monster Iestyn 14/06/18 - for (secnum = -1; (secnum = P_FindSectorFromTag(line->tag, secnum)) >= 0 ;) + { + extracolormap_t *source; + if (!udmf) + source = sides[line->sidenum[0]].colormap_data; + else { + if (!line->args[1]) + source = line->frontsector->extra_colormap; + else + { + INT32 sourcesec = P_FindSectorFromTag(line->args[1], -1); + if (sourcesec == -1) + { + CONS_Debug(DBG_GAMELOGIC, "Line type 447 Executor: Can't find sector with source colormap (tag %d)!\n", line->args[1]); + return; + } + source = sectors[sourcesec].extra_colormap; + } + } + + for (secnum = -1; (secnum = P_FindSectorFromTag(line->args[0], secnum)) >= 0;) + { + if (sectors[secnum].colormap_protected) + continue; + P_ResetColormapFader(§ors[secnum]); - if (line->flags & ML_EFFECT3) // relative calc + if (line->args[2] & TMCF_RELATIVE) { - extracolormap_t *exc = R_AddColormaps( - (line->flags & ML_TFERLINE) && line->sidenum[1] != 0xFFFF ? - sides[line->sidenum[1]].colormap_data : sectors[secnum].extra_colormap, // use back colormap instead of target sector - sides[line->sidenum[0]].colormap_data, - line->flags & ML_EFFECT1, // subtract R - line->flags & ML_NOCLIMB, // subtract G - line->flags & ML_EFFECT2, // subtract B - false, // subtract A (no flag for this, just pass negative alpha) - line->flags & ML_EFFECT1, // subtract FadeR - line->flags & ML_NOCLIMB, // subtract FadeG - line->flags & ML_EFFECT2, // subtract FadeB - false, // subtract FadeA (no flag for this, just pass negative alpha) - false, // subtract FadeStart (we ran out of flags) - false, // subtract FadeEnd (we ran out of flags) - false, // ignore Flags (we ran out of flags) - line->flags & ML_DONTPEGBOTTOM, - (line->flags & ML_DONTPEGBOTTOM) ? (sides[line->sidenum[0]].textureoffset >> FRACBITS) : 0, - (line->flags & ML_DONTPEGBOTTOM) ? (sides[line->sidenum[0]].rowoffset >> FRACBITS) : 0, - false); + extracolormap_t *target = (!udmf && (line->flags & ML_TFERLINE) && line->sidenum[1] != 0xFFFF) ? + sides[line->sidenum[1]].colormap_data : sectors[secnum].extra_colormap; // use back colormap instead of target sector - if (!(sectors[secnum].extra_colormap = R_GetColormapFromList(exc))) - { - exc->colormap = R_CreateLightTable(exc); - R_AddColormapToList(exc); - sectors[secnum].extra_colormap = exc; - } - else - Z_Free(exc); - } - else if (line->flags & ML_DONTPEGBOTTOM) // alternate alpha (by texture offsets) - { - extracolormap_t *exc = R_CopyColormap(sides[line->sidenum[0]].colormap_data, false); - exc->rgba = R_GetRgbaRGB(exc->rgba) + R_PutRgbaA(max(min(sides[line->sidenum[0]].textureoffset >> FRACBITS, 25), 0)); - exc->fadergba = R_GetRgbaRGB(exc->fadergba) + R_PutRgbaA(max(min(sides[line->sidenum[0]].rowoffset >> FRACBITS, 25), 0)); + extracolormap_t *exc = R_AddColormaps( + target, + source, + line->args[2] & TMCF_SUBLIGHTR, + line->args[2] & TMCF_SUBLIGHTG, + line->args[2] & TMCF_SUBLIGHTB, + line->args[2] & TMCF_SUBLIGHTA, + line->args[2] & TMCF_SUBFADER, + line->args[2] & TMCF_SUBFADEG, + line->args[2] & TMCF_SUBFADEB, + line->args[2] & TMCF_SUBFADEA, + line->args[2] & TMCF_SUBFADESTART, + line->args[2] & TMCF_SUBFADEEND, + line->args[2] & TMCF_IGNOREFLAGS, + false); if (!(sectors[secnum].extra_colormap = R_GetColormapFromList(exc))) { @@ -3471,10 +3462,10 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) Z_Free(exc); } else - sectors[secnum].extra_colormap = sides[line->sidenum[0]].colormap_data; + sectors[secnum].extra_colormap = source; } break; - + } case 448: // Change skybox viewpoint/centerpoint if ((mo && mo->player && P_IsLocalPlayer(mo->player)) || (line->flags & ML_NOCLIMB)) { @@ -3748,15 +3739,35 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) } case 455: // Fade colormap - for (secnum = -1; (secnum = P_FindSectorFromTag(line->tag, secnum)) >= 0 ;) + { + extracolormap_t *dest; + if (!udmf) + dest = sides[line->sidenum[0]].colormap_data; + else + { + if (!line->args[1]) + dest = line->frontsector->extra_colormap; + else + { + INT32 destsec = P_FindSectorFromTag(line->args[1], -1); + if (destsec == -1) + { + CONS_Debug(DBG_GAMELOGIC, "Line type 455 Executor: Can't find sector with destination colormap (tag %d)!\n", line->args[1]); + return; + } + dest = sectors[destsec].extra_colormap; + } + } + + for (secnum = -1; (secnum = P_FindSectorFromTag(line->args[0], secnum)) >= 0;) { extracolormap_t *source_exc, *dest_exc, *exc; - INT32 speed = (INT32)((line->flags & ML_DONTPEGBOTTOM) || !sides[line->sidenum[0]].rowoffset) && line->sidenum[1] != 0xFFFF ? - abs(sides[line->sidenum[1]].rowoffset >> FRACBITS) - : abs(sides[line->sidenum[0]].rowoffset >> FRACBITS); - // Prevent continuous execs from interfering on an existing fade - if (!(line->flags & ML_EFFECT5) + if (sectors[secnum].colormap_protected) + continue; + + // Don't interrupt ongoing fade + if (!(line->args[3] & TMCF_OVERRIDE) && sectors[secnum].fadecolormapdata) //&& ((fadecolormap_t*)sectors[secnum].fadecolormapdata)->timer > (ticbased ? 2 : speed*2)) { @@ -3764,19 +3775,19 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) continue; } - if (line->flags & ML_TFERLINE) // use back colormap instead of target sector + if (!udmf && (line->flags & ML_TFERLINE)) // use back colormap instead of target sector sectors[secnum].extra_colormap = (line->sidenum[1] != 0xFFFF) ? - sides[line->sidenum[1]].colormap_data : NULL; + sides[line->sidenum[1]].colormap_data : NULL; exc = sectors[secnum].extra_colormap; - if (!(line->flags & ML_BOUNCY) // BOUNCY: Do not override fade from default rgba - && !R_CheckDefaultColormap(sides[line->sidenum[0]].colormap_data, true, false, false) + if (!(line->args[3] & TMCF_FROMBLACK) // Override fade from default rgba + && !R_CheckDefaultColormap(dest, true, false, false) && R_CheckDefaultColormap(exc, true, false, false)) { exc = R_CopyColormap(exc, false); - exc->rgba = R_GetRgbaRGB(sides[line->sidenum[0]].colormap_data->rgba) + R_PutRgbaA(R_GetRgbaA(exc->rgba)); - //exc->fadergba = R_GetRgbaRGB(sides[line->sidenum[0]].colormap_data->rgba) + R_PutRgbaA(R_GetRgbaA(exc->fadergba)); + exc->rgba = R_GetRgbaRGB(dest->rgba) + R_PutRgbaA(R_GetRgbaA(exc->rgba)); + //exc->fadergba = R_GetRgbaRGB(dest->rgba) + R_PutRgbaA(R_GetRgbaA(exc->fadergba)); if (!(source_exc = R_GetColormapFromList(exc))) { @@ -3792,35 +3803,26 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) else source_exc = exc ? exc : R_GetDefaultColormap(); - if (line->flags & ML_EFFECT3) // relative calc + if (line->args[3] & TMCF_RELATIVE) { exc = R_AddColormaps( source_exc, - sides[line->sidenum[0]].colormap_data, - line->flags & ML_EFFECT1, // subtract R - line->flags & ML_NOCLIMB, // subtract G - line->flags & ML_EFFECT2, // subtract B - false, // subtract A (no flag for this, just pass negative alpha) - line->flags & ML_EFFECT1, // subtract FadeR - line->flags & ML_NOCLIMB, // subtract FadeG - line->flags & ML_EFFECT2, // subtract FadeB - false, // subtract FadeA (no flag for this, just pass negative alpha) - false, // subtract FadeStart (we ran out of flags) - false, // subtract FadeEnd (we ran out of flags) - false, // ignore Flags (we ran out of flags) - line->flags & ML_DONTPEGBOTTOM, - (line->flags & ML_DONTPEGBOTTOM) ? (sides[line->sidenum[0]].textureoffset >> FRACBITS) : 0, - (line->flags & ML_DONTPEGBOTTOM) ? (sides[line->sidenum[0]].rowoffset >> FRACBITS) : 0, + dest, + line->args[3] & TMCF_SUBLIGHTR, + line->args[3] & TMCF_SUBLIGHTG, + line->args[3] & TMCF_SUBLIGHTB, + line->args[3] & TMCF_SUBLIGHTA, + line->args[3] & TMCF_SUBFADER, + line->args[3] & TMCF_SUBFADEG, + line->args[3] & TMCF_SUBFADEB, + line->args[3] & TMCF_SUBFADEA, + line->args[3] & TMCF_SUBFADESTART, + line->args[3] & TMCF_SUBFADEEND, + line->args[3] & TMCF_IGNOREFLAGS, false); } - else if (line->flags & ML_DONTPEGBOTTOM) // alternate alpha (by texture offsets) - { - exc = R_CopyColormap(sides[line->sidenum[0]].colormap_data, false); - exc->rgba = R_GetRgbaRGB(exc->rgba) + R_PutRgbaA(max(min(sides[line->sidenum[0]].textureoffset >> FRACBITS, 25), 0)); - exc->fadergba = R_GetRgbaRGB(exc->fadergba) + R_PutRgbaA(max(min(sides[line->sidenum[0]].rowoffset >> FRACBITS, 25), 0)); - } else - exc = R_CopyColormap(sides[line->sidenum[0]].colormap_data, false); + exc = R_CopyColormap(dest, false); if (!(dest_exc = R_GetColormapFromList(exc))) { @@ -3831,13 +3833,13 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) else Z_Free(exc); - Add_ColormapFader(§ors[secnum], source_exc, dest_exc, (line->flags & ML_EFFECT4), // tic-based timing - speed); + Add_ColormapFader(§ors[secnum], source_exc, dest_exc, true, // tic-based timing + line->args[2]); } break; - + } case 456: // Stop fade colormap - for (secnum = -1; (secnum = P_FindSectorFromTag(line->tag, secnum)) >= 0 ;) + for (secnum = -1; (secnum = P_FindSectorFromTag(line->args[0], secnum)) >= 0 ;) P_ResetColormapFader(§ors[secnum]); break; @@ -4027,6 +4029,23 @@ static void P_ProcessLineSpecial(line_t *line, mobj_t *mo, sector_t *callsec) } break; + case 465: // Set linedef executor delay + { + INT32 linenum; + + if (!udmf) + break; + + for (linenum = -1; (linenum = P_FindLineFromTag(line->args[0], linenum)) >= 0 ;) + { + if (line->args[2]) + lines[linenum].executordelay += line->args[1]; + else + lines[linenum].executordelay = line->args[1]; + } + } + break; + case 480: // Polyobj_DoorSlide case 481: // Polyobj_DoorSwing PolyDoor(line); @@ -5890,7 +5909,7 @@ static void P_AddRaiseThinker(sector_t *sec, INT16 tag, fixed_t speed, fixed_t c raise->ceilingtop = ceilingtop; raise->ceilingbottom = ceilingbottom; - raise->basespeed = speed; + raise->basespeed = speed; if (lower) raise->flags |= RF_REVERSE; @@ -6133,7 +6152,7 @@ static void P_RunLevelLoadExecutors(void) * by P_SpawnSlopes or P_LoadThings. This was split off from * P_SpawnSpecials, in case you couldn't tell. * - * \sa P_SpawnSpecials, P_InitTagLists + * \sa P_SpawnSpecials * \author Monster Iestyn */ void P_InitSpecials(void) @@ -6164,8 +6183,6 @@ void P_InitSpecials(void) // Set globalweather globalweather = mapheaderinfo[gamemap-1]->weather; - - P_InitTagLists(); // Create xref tables for tags } static void P_ApplyFlatAlignment(line_t *master, sector_t *sector, angle_t flatangle, fixed_t xoffs, fixed_t yoffs) @@ -7145,8 +7162,32 @@ void P_SpawnSpecials(boolean fromnetsave) break; case 606: // HACK! Copy colormaps. Just plain colormaps. - for (s = -1; (s = P_FindSectorFromTag(lines[i].tag, s)) >= 0 ;) - sectors[s].extra_colormap = sectors[s].spawn_extra_colormap = sides[lines[i].sidenum[0]].colormap_data; + for (s = -1; (s = P_FindSectorFromTag(lines[i].args[0], s)) >= 0;) + { + extracolormap_t *exc; + + if (sectors[s].colormap_protected) + continue; + + if (!udmf) + exc = sides[lines[i].sidenum[0]].colormap_data; + else + { + if (!lines[i].args[1]) + exc = lines[i].frontsector->extra_colormap; + else + { + INT32 sourcesec = P_FindSectorFromTag(lines[i].args[1], -1); + if (sourcesec == -1) + { + CONS_Debug(DBG_GAMELOGIC, "Line type 606: Can't find sector with source colormap (tag %d)!\n", lines[i].args[1]); + return; + } + exc = sectors[sourcesec].extra_colormap; + } + } + sectors[s].extra_colormap = sectors[s].spawn_extra_colormap = exc; + } break; default: @@ -8109,7 +8150,7 @@ static void P_AddFakeFloorFader(ffloor_t *rover, size_t sectornum, size_t ffloor d->destlightlevel = -1; // Set a separate thinker for colormap fading - if (docolormap && !(rover->flags & FF_NOSHADE) && sectors[rover->secnum].spawn_extra_colormap) + if (docolormap && !(rover->flags & FF_NOSHADE) && sectors[rover->secnum].spawn_extra_colormap && !sectors[rover->secnum].colormap_protected) { extracolormap_t *dest_exc, *source_exc = sectors[rover->secnum].extra_colormap ? sectors[rover->secnum].extra_colormap : R_GetDefaultColormap(); diff --git a/src/p_user.c b/src/p_user.c index 679f4064b..44793b0cc 100644 --- a/src/p_user.c +++ b/src/p_user.c @@ -5536,7 +5536,7 @@ static void P_DoJumpStuff(player_t *player, ticcmd_t *cmd) if ((!(gametyperules & GTR_TEAMFLAGS) || !player->gotflag) && !player->exiting) { - if (player->secondjump == 1 && player->charability != CA_DOUBLEJUMP) + if (player->secondjump == 1 && player->charability != CA_DOUBLEJUMP && player->charability != CA_THOK) { fixed_t potentialmomz; if (player->charability == CA_SLOWFALL) @@ -7975,20 +7975,13 @@ void P_MovePlayer(player_t *player) // Locate the capsule for this mare. else if (maptol & TOL_NIGHTS) { - if ((player->powers[pw_carry] == CR_NIGHTSMODE) - && (player->exiting - || !(player->mo->state >= &states[S_PLAY_NIGHTS_TRANS1] - && player->mo->state < &states[S_PLAY_NIGHTS_TRANS6]))) // Note the < instead of <= + if (P_PlayerFullbright(player)) { - skin_t *skin = ((skin_t *)(player->mo->skin)); - if (( skin->flags & (SF_SUPER|SF_NONIGHTSSUPER) ) == SF_SUPER) - { - player->mo->color = skin->supercolor - + ((player->nightstime == player->startedtime) - ? 4 - : abs((((signed)leveltime >> 1) % 9) - 4)); // This is where super flashing is handled. - G_GhostAddColor(GHC_SUPER); - } + player->mo->color = ((skin_t *)player->mo->skin)->supercolor + + ((player->nightstime == player->startedtime) + ? 4 + : abs((((signed)leveltime >> 1) % 9) - 4)); // This is where super flashing is handled. + G_GhostAddColor(GHC_SUPER); } if (!player->capsule && !player->bonustime) @@ -12895,3 +12888,12 @@ void P_ForceLocalAngle(player_t *player, angle_t angle) else if (player == &players[secondarydisplayplayer]) localangle2 = angle; } + +boolean P_PlayerFullbright(player_t *player) +{ + return (player->powers[pw_super] + || ((player->powers[pw_carry] == CR_NIGHTSMODE && (((skin_t *)player->mo->skin)->flags & (SF_SUPER|SF_NONIGHTSSUPER)) == SF_SUPER) // Super colours? Super bright! + && (player->exiting + || !(player->mo->state >= &states[S_PLAY_NIGHTS_TRANS1] + && player->mo->state < &states[S_PLAY_NIGHTS_TRANS6])))); // Note the < instead of <= +} diff --git a/src/r_data.c b/src/r_data.c index d10919d81..befb73c20 100644 --- a/src/r_data.c +++ b/src/r_data.c @@ -2080,7 +2080,7 @@ extracolormap_t *R_ColormapForName(char *name) #endif // -// R_CreateColormap +// R_CreateColormapFromLinedef // // This is a more GL friendly way of doing colormaps: Specify colormap // data in a special linedef's texture areas and use that to generate @@ -2219,10 +2219,8 @@ lighttable_t *R_CreateLightTable(extracolormap_t *extra_colormap) return lighttable; } -extracolormap_t *R_CreateColormap(char *p1, char *p2, char *p3) +extracolormap_t *R_CreateColormapFromLinedef(char *p1, char *p2, char *p3) { - extracolormap_t *extra_colormap, *exc; - // default values UINT8 cr = 0, cg = 0, cb = 0, ca = 0, cfr = 0, cfg = 0, cfb = 0, cfa = 25; UINT32 fadestart = 0, fadeend = 31; @@ -2345,6 +2343,13 @@ extracolormap_t *R_CreateColormap(char *p1, char *p2, char *p3) rgba = R_PutRgbaRGBA(cr, cg, cb, ca); fadergba = R_PutRgbaRGBA(cfr, cfg, cfb, cfa); + return R_CreateColormap(rgba, fadergba, fadestart, fadeend, flags); +} + +extracolormap_t *R_CreateColormap(INT32 rgba, INT32 fadergba, UINT8 fadestart, UINT8 fadeend, UINT8 flags) +{ + extracolormap_t *extra_colormap; + // Did we just make a default colormap? #ifdef EXTRACOLORMAPLUMPS if (R_CheckDefaultColormapByValues(true, true, true, rgba, fadergba, fadestart, fadeend, flags, LUMPERROR)) @@ -2356,17 +2361,16 @@ extracolormap_t *R_CreateColormap(char *p1, char *p2, char *p3) // Look for existing colormaps #ifdef EXTRACOLORMAPLUMPS - exc = R_GetColormapFromListByValues(rgba, fadergba, fadestart, fadeend, flags, LUMPERROR); + extra_colormap = R_GetColormapFromListByValues(rgba, fadergba, fadestart, fadeend, flags, LUMPERROR); #else - exc = R_GetColormapFromListByValues(rgba, fadergba, fadestart, fadeend, flags); + extra_colormap = R_GetColormapFromListByValues(rgba, fadergba, fadestart, fadeend, flags); #endif - if (exc) - return exc; + if (extra_colormap) + return extra_colormap; - CONS_Debug(DBG_RENDER, "Creating Colormap: rgba(%d,%d,%d,%d) fadergba(%d,%d,%d,%d)\n", - cr, cg, cb, ca, cfr, cfg, cfb, cfa); + CONS_Debug(DBG_RENDER, "Creating Colormap: rgba(%x) fadergba(%x)\n", rgba, fadergba); - extra_colormap = Z_Calloc(sizeof (*extra_colormap), PU_LEVEL, NULL); + extra_colormap = Z_Calloc(sizeof(*extra_colormap), PU_LEVEL, NULL); extra_colormap->fadestart = (UINT16)fadestart; extra_colormap->fadeend = (UINT16)fadeend; @@ -2398,7 +2402,6 @@ extracolormap_t *R_AddColormaps(extracolormap_t *exc_augend, extracolormap_t *ex boolean subR, boolean subG, boolean subB, boolean subA, boolean subFadeR, boolean subFadeG, boolean subFadeB, boolean subFadeA, boolean subFadeStart, boolean subFadeEnd, boolean ignoreFlags, - boolean useAltAlpha, INT16 altAlpha, INT16 altFadeAlpha, boolean lighttable) { INT16 red, green, blue, alpha; @@ -2434,7 +2437,7 @@ extracolormap_t *R_AddColormaps(extracolormap_t *exc_augend, extracolormap_t *ex * R_GetRgbaB(exc_addend->rgba) , 255), 0); - alpha = useAltAlpha ? altAlpha : R_GetRgbaA(exc_addend->rgba); + alpha = R_GetRgbaA(exc_addend->rgba); alpha = max(min(R_GetRgbaA(exc_augend->rgba) + (subA ? -1 : 1) * alpha, 25), 0); exc_augend->rgba = R_PutRgbaRGBA(red, green, blue, alpha); @@ -2461,8 +2464,8 @@ extracolormap_t *R_AddColormaps(extracolormap_t *exc_augend, extracolormap_t *ex * R_GetRgbaB(exc_addend->fadergba) , 255), 0); - alpha = useAltAlpha ? altFadeAlpha : R_GetRgbaA(exc_addend->fadergba); - if (alpha == 25 && !useAltAlpha && !R_GetRgbaRGB(exc_addend->fadergba)) + alpha = R_GetRgbaA(exc_addend->fadergba); + if (alpha == 25 && !R_GetRgbaRGB(exc_addend->fadergba)) alpha = 0; // HACK: fadergba A defaults at 25, so don't add anything in this case alpha = max(min(R_GetRgbaA(exc_augend->fadergba) + (subFadeA ? -1 : 1) * alpha, 25), 0); diff --git a/src/r_data.h b/src/r_data.h index 8b8d08c52..fda342083 100644 --- a/src/r_data.h +++ b/src/r_data.h @@ -149,13 +149,31 @@ boolean R_CheckDefaultColormap(extracolormap_t *extra_colormap, boolean checkrgb boolean R_CheckEqualColormaps(extracolormap_t *exc_a, extracolormap_t *exc_b, boolean checkrgba, boolean checkfadergba, boolean checkparams); extracolormap_t *R_GetColormapFromList(extracolormap_t *extra_colormap); +typedef enum +{ + TMCF_RELATIVE = 1, + TMCF_SUBLIGHTR = 1<<1, + TMCF_SUBLIGHTG = 1<<2, + TMCF_SUBLIGHTB = 1<<3, + TMCF_SUBLIGHTA = 1<<4, + TMCF_SUBFADER = 1<<5, + TMCF_SUBFADEG = 1<<6, + TMCF_SUBFADEB = 1<<7, + TMCF_SUBFADEA = 1<<8, + TMCF_SUBFADESTART = 1<<9, + TMCF_SUBFADEEND = 1<<10, + TMCF_IGNOREFLAGS = 1<<11, + TMCF_FROMBLACK = 1<<12, + TMCF_OVERRIDE = 1<<13, +} textmapcolormapflags_t; + lighttable_t *R_CreateLightTable(extracolormap_t *extra_colormap); -extracolormap_t *R_CreateColormap(char *p1, char *p2, char *p3); +extracolormap_t * R_CreateColormapFromLinedef(char *p1, char *p2, char *p3); +extracolormap_t* R_CreateColormap(INT32 rgba, INT32 fadergba, UINT8 fadestart, UINT8 fadeend, UINT8 flags); extracolormap_t *R_AddColormaps(extracolormap_t *exc_augend, extracolormap_t *exc_addend, boolean subR, boolean subG, boolean subB, boolean subA, boolean subFadeR, boolean subFadeG, boolean subFadeB, boolean subFadeA, boolean subFadeStart, boolean subFadeEnd, boolean ignoreFlags, - boolean useAltAlpha, INT16 altAlpha, INT16 altFadeAlpha, boolean lighttable); #ifdef EXTRACOLORMAPLUMPS extracolormap_t *R_ColormapForName(char *name); diff --git a/src/r_defs.h b/src/r_defs.h index fd868ee97..132106bc8 100644 --- a/src/r_defs.h +++ b/src/r_defs.h @@ -333,6 +333,7 @@ typedef struct sector_s // per-sector colormaps! extracolormap_t *extra_colormap; + boolean colormap_protected; // This points to the master's floorheight, so it can be changed in realtime! fixed_t *gravity; // per-sector gravity @@ -374,6 +375,9 @@ typedef enum #define HORIZONSPECIAL 41 +#define NUMLINEARGS 6 +#define NUMLINESTRINGARGS 2 + typedef struct line_s { // Vertices, from v1 to v2. @@ -386,9 +390,13 @@ typedef struct line_s INT16 flags; INT16 special; INT16 tag; + INT32 args[NUMLINEARGS]; + char *stringargs[NUMLINESTRINGARGS]; // Visual appearance: sidedefs. UINT16 sidenum[2]; // sidenum[1] will be 0xffff if one-sided + fixed_t alpha; // translucency + INT32 executordelay; fixed_t bbox[4]; // bounding box for the extent of the linedef diff --git a/src/r_draw.c b/src/r_draw.c index 5351ef37f..2b798c3bf 100644 --- a/src/r_draw.c +++ b/src/r_draw.c @@ -134,6 +134,7 @@ UINT32 nflatxshift, nflatyshift, nflatshiftup, nflatmask; #define NUM_PALETTE_ENTRIES 256 static UINT8** translationtablecache[MAXSKINS + 7] = {NULL}; +UINT8 skincolor_modified[MAXSKINCOLORS]; CV_PossibleValue_t Color_cons_t[MAXSKINCOLORS+1]; @@ -362,6 +363,7 @@ UINT8* R_GetTranslationColormap(INT32 skinnum, skincolornum_t color, UINT8 flags { UINT8* ret; INT32 skintableindex; + INT32 i; // Adjust if we want the default colormap switch (skinnum) @@ -385,6 +387,15 @@ UINT8* R_GetTranslationColormap(INT32 skinnum, skincolornum_t color, UINT8 flags // Get colormap ret = translationtablecache[skintableindex][color]; + + // Rebuild the cache if necessary + if (skincolor_modified[color]) + { + for (i = 0; i < (INT32)(sizeof(translationtablecache) / sizeof(translationtablecache[0])); i++) + if (translationtablecache[i] && translationtablecache[i][color]) + R_GenerateTranslationColormap(translationtablecache[i][color], i>=MAXSKINS ? MAXSKINS-i-1 : i, color); + skincolor_modified[color] = false; + } } else ret = NULL; @@ -427,12 +438,12 @@ UINT16 R_GetColorByName(const char *name) for (color = 1; color < numskincolors; color++) if (!stricmp(skincolors[color].name, name)) return color; - return SKINCOLOR_GREEN; + return SKINCOLOR_NONE; } UINT16 R_GetSuperColorByName(const char *name) { - UINT16 i, color = SKINCOLOR_SUPERGOLD1; + UINT16 i, color = SKINCOLOR_NONE; char *realname = Z_Malloc(MAXCOLORNAME+1, PU_STATIC, NULL); snprintf(realname, MAXCOLORNAME+1, "Super %s 1", name); for (i = 1; i < numskincolors; i++) diff --git a/src/r_draw.h b/src/r_draw.h index 329c4974a..1ca22f18a 100644 --- a/src/r_draw.h +++ b/src/r_draw.h @@ -117,6 +117,9 @@ void R_FlushTranslationColormapCache(void); UINT16 R_GetColorByName(const char *name); UINT16 R_GetSuperColorByName(const char *name); +// Color ramp modification should force a recache +extern UINT8 skincolor_modified[]; + // Custom player skin translation void R_InitViewBuffer(INT32 width, INT32 height); void R_InitViewBorder(void); diff --git a/src/r_main.c b/src/r_main.c index ead1403be..4f79dd8db 100644 --- a/src/r_main.c +++ b/src/r_main.c @@ -318,6 +318,24 @@ angle_t R_PointToAngle(fixed_t x, fixed_t y) 0; } +// This version uses 64-bit variables to avoid overflows with large values. +// Currently used only by OpenGL rendering. +angle_t R_PointToAngle64(INT64 x, INT64 y) +{ + return (y -= viewy, (x -= viewx) || y) ? + x >= 0 ? + y >= 0 ? + (x > y) ? tantoangle[SlopeDivEx(y,x)] : // octant 0 + ANGLE_90-tantoangle[SlopeDivEx(x,y)] : // octant 1 + x > (y = -y) ? 0-tantoangle[SlopeDivEx(y,x)] : // octant 8 + ANGLE_270+tantoangle[SlopeDivEx(x,y)] : // octant 7 + y >= 0 ? (x = -x) > y ? ANGLE_180-tantoangle[SlopeDivEx(y,x)] : // octant 3 + ANGLE_90 + tantoangle[SlopeDivEx(x,y)] : // octant 2 + (x = -x) > (y = -y) ? ANGLE_180+tantoangle[SlopeDivEx(y,x)] : // octant 4 + ANGLE_270-tantoangle[SlopeDivEx(x,y)] : // octant 5 + 0; +} + angle_t R_PointToAngle2(fixed_t pviewx, fixed_t pviewy, fixed_t x, fixed_t y) { return (y -= pviewy, (x -= pviewx) || y) ? diff --git a/src/r_main.h b/src/r_main.h index 99a25d86e..729ec6973 100644 --- a/src/r_main.h +++ b/src/r_main.h @@ -63,6 +63,7 @@ extern lighttable_t *zlight[LIGHTLEVELS][MAXLIGHTZ]; INT32 R_PointOnSide(fixed_t x, fixed_t y, node_t *node); INT32 R_PointOnSegSide(fixed_t x, fixed_t y, seg_t *line); angle_t R_PointToAngle(fixed_t x, fixed_t y); +angle_t R_PointToAngle64(INT64 x, INT64 y); angle_t R_PointToAngle2(fixed_t px2, fixed_t py2, fixed_t px1, fixed_t py1); angle_t R_PointToAngleEx(INT32 x2, INT32 y2, INT32 x1, INT32 y1); fixed_t R_PointToDist(fixed_t x, fixed_t y); diff --git a/src/r_segs.c b/src/r_segs.c index 741a25254..d9fc75838 100644 --- a/src/r_segs.c +++ b/src/r_segs.c @@ -274,6 +274,11 @@ static void R_Render2sidedMultiPatchColumn(column_t *column) } } +transnum_t R_GetLinedefTransTable(fixed_t alpha) +{ + return (20*(FRACUNIT - alpha - 1) + FRACUNIT) >> (FRACBITS+1); +} + void R_RenderMaskedSegRange(drawseg_t *ds, INT32 x1, INT32 x2) { size_t pindex; @@ -300,31 +305,24 @@ void R_RenderMaskedSegRange(drawseg_t *ds, INT32 x1, INT32 x2) texnum = R_GetTextureNum(curline->sidedef->midtexture); windowbottom = windowtop = sprbotscreen = INT32_MAX; - // hack translucent linedef types (900-909 for transtables 1-9) ldef = curline->linedef; - switch (ldef->special) + if (!ldef->alpha) + return; + + if (ldef->alpha > 0 && ldef->alpha < FRACUNIT) { - case 900: - case 901: - case 902: - case 903: - case 904: - case 905: - case 906: - case 907: - case 908: - dc_transmap = transtables + ((ldef->special-900)<ceilingheight; - windowbottom = frontsector->floorheight; - break; - default: - colfunc = colfuncs[BASEDRAWFUNC]; - break; + dc_transmap = transtables + ((R_GetLinedefTransTable(ldef->alpha) - 1) << FF_TRANSSHIFT); + colfunc = colfuncs[COLDRAWFUNC_FUZZY]; + } + else if (ldef->special == 909) + { + colfunc = colfuncs[COLDRAWFUNC_FOG]; + windowtop = frontsector->ceilingheight; + windowbottom = frontsector->floorheight; + } + else + colfunc = colfuncs[BASEDRAWFUNC]; if (curline->polyseg && curline->polyseg->translucency > 0) { diff --git a/src/r_segs.h b/src/r_segs.h index a61f1f921..ace5711d4 100644 --- a/src/r_segs.h +++ b/src/r_segs.h @@ -18,6 +18,7 @@ #pragma interface #endif +transnum_t R_GetLinedefTransTable(fixed_t alpha); void R_RenderMaskedSegRange(drawseg_t *ds, INT32 x1, INT32 x2); void R_RenderThickSideRange(drawseg_t *ds, INT32 x1, INT32 x2, ffloor_t *pffloor); void R_StoreWallRange(INT32 start, INT32 stop); diff --git a/src/r_skins.c b/src/r_skins.c index 57ce382c4..a1484a2b3 100644 --- a/src/r_skins.c +++ b/src/r_skins.c @@ -464,12 +464,19 @@ static boolean R_ProcessPatchableFields(skin_t *skin, char *stoken, char *value) GETINT(contangle) #undef GETINT -#define GETSKINCOLOR(field) else if (!stricmp(stoken, #field)) skin->field = R_GetColorByName(value); +#define GETSKINCOLOR(field) else if (!stricmp(stoken, #field)) \ +{ \ + UINT16 color = R_GetColorByName(value); \ + skin->field = (color ? color : SKINCOLOR_GREEN); \ +} GETSKINCOLOR(prefcolor) GETSKINCOLOR(prefoppositecolor) #undef GETSKINCOLOR else if (!stricmp(stoken, "supercolor")) - skin->supercolor = R_GetSuperColorByName(value); + { + UINT16 color = R_GetSuperColorByName(value); + skin->supercolor = (color ? color : SKINCOLOR_SUPERGOLD1); + } #define GETFLOAT(field) else if (!stricmp(stoken, #field)) skin->field = FLOAT_TO_FIXED(atof(value)); GETFLOAT(jumpfactor) diff --git a/src/r_state.h b/src/r_state.h index 7c860a6f2..25aa69702 100644 --- a/src/r_state.h +++ b/src/r_state.h @@ -52,6 +52,8 @@ extern size_t numspritelumps, max_spritelumps; // // Lookup tables for map data. // +extern boolean udmf; + extern size_t numsprites; extern spritedef_t *sprites; diff --git a/src/r_things.c b/src/r_things.c index d2647b811..c0795acd5 100644 --- a/src/r_things.c +++ b/src/r_things.c @@ -2773,7 +2773,7 @@ boolean R_ThingVisible (mobj_t *thing) return (!( thing->sprite == SPR_NULL || ( thing->flags2 & (MF2_DONTDRAW) ) || - thing == r_viewmobj + (r_viewmobj && (thing == r_viewmobj || (r_viewmobj->player && r_viewmobj->player->followmobj == thing))) )); } diff --git a/src/s_sound.c b/src/s_sound.c index 5ed9fd83a..072a69f6c 100644 --- a/src/s_sound.c +++ b/src/s_sound.c @@ -60,6 +60,7 @@ static void Command_RestartAudio_f(void); static void GameMIDIMusic_OnChange(void); static void GameSounds_OnChange(void); static void GameDigiMusic_OnChange(void); +static void MusicPref_OnChange(void); #ifdef HAVE_OPENMPT static void ModFilter_OnChange(void); @@ -129,6 +130,14 @@ consvar_t cv_gamedigimusic = {"digimusic", "On", CV_SAVE|CV_CALL|CV_NOINIT, CV_O consvar_t cv_gamemidimusic = {"midimusic", "On", CV_SAVE|CV_CALL|CV_NOINIT, CV_OnOff, GameMIDIMusic_OnChange, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_gamesounds = {"sounds", "On", CV_SAVE|CV_CALL|CV_NOINIT, CV_OnOff, GameSounds_OnChange, 0, NULL, NULL, 0, 0, NULL}; +// Music preference +static CV_PossibleValue_t cons_musicpref_t[] = { + {0, "Digital"}, + {1, "MIDI"}, + {0, NULL} +}; +consvar_t cv_musicpref = {"musicpref", "Digital", CV_SAVE|CV_CALL|CV_NOINIT, cons_musicpref_t, MusicPref_OnChange, 0, NULL, NULL, 0, 0, NULL}; + // Window focus sound sytem toggles consvar_t cv_playmusicifunfocused = {"playmusicifunfocused", "No", CV_SAVE, CV_YesNo, NULL, 0, NULL, NULL, 0, 0, NULL}; consvar_t cv_playsoundsifunfocused = {"playsoundsifunfocused", "No", CV_SAVE, CV_YesNo, NULL, 0, NULL, NULL, 0, 0, NULL}; @@ -301,6 +310,7 @@ void S_RegisterSoundStuff(void) CV_RegisterVar(&cv_gamesounds); CV_RegisterVar(&cv_gamedigimusic); CV_RegisterVar(&cv_gamemidimusic); + CV_RegisterVar(&cv_musicpref); #ifdef HAVE_OPENMPT CV_RegisterVar(&cv_modfilter); #endif @@ -1847,19 +1857,6 @@ const char *S_MusicName(void) return music_name; } -boolean S_MusicInfo(char *mname, UINT16 *mflags, boolean *looping) -{ - if (!I_SongPlaying()) - return false; - - strncpy(mname, music_name, 7); - mname[6] = 0; - *mflags = music_flags; - *looping = music_looping; - - return (boolean)mname[0]; -} - boolean S_MusicExists(const char *mname, boolean checkMIDI, boolean checkDigi) { return ( @@ -2100,6 +2097,8 @@ boolean S_RecallMusic(UINT16 status, boolean fromfirst) boolean mapmuschanged = false; musicstack_t *result; musicstack_t *entry = Z_Calloc(sizeof (*result), PU_MUSIC, NULL); + boolean currentmidi = (I_SongType() == MU_MID || I_SongType() == MU_MID_EX); + boolean midipref = cv_musicpref.value; if (status) result = S_GetMusicStackEntry(status, fromfirst, -1); @@ -2154,7 +2153,8 @@ boolean S_RecallMusic(UINT16 status, boolean fromfirst) return false; } - if (strncmp(entry->musname, S_MusicName(), 7)) // don't restart music if we're already playing it + if (strncmp(entry->musname, S_MusicName(), 7) || // don't restart music if we're already playing it + (midipref != currentmidi && S_PrefAvailable(midipref, entry->musname))) // but do if the user's preference has changed { if (music_stack_fadeout) S_ChangeMusicEx(entry->musname, entry->musflags, entry->looping, 0, music_stack_fadeout, 0); @@ -2201,10 +2201,12 @@ boolean S_RecallMusic(UINT16 status, boolean fromfirst) static lumpnum_t S_GetMusicLumpNum(const char *mname) { - if (!S_DigMusicDisabled() && S_DigExists(mname)) - return W_GetNumForName(va("o_%s", mname)); - else if (!S_MIDIMusicDisabled() && S_MIDIExists(mname)) - return W_GetNumForName(va("d_%s", mname)); + boolean midipref = cv_musicpref.value; + + if (S_PrefAvailable(midipref, mname)) + return W_GetNumForName(va(midipref ? "d_%s":"o_%s", mname)); + else if (S_PrefAvailable(!midipref, mname)) + return W_GetNumForName(va(midipref ? "o_%s":"d_%s", mname)); else return LUMPERROR; } @@ -2330,6 +2332,8 @@ static void S_ChangeMusicToQueue(void) void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32 position, UINT32 prefadems, UINT32 fadeinms) { char newmusic[7]; + boolean currentmidi = (I_SongType() == MU_MID || I_SongType() == MU_MID_EX); + boolean midipref = cv_musicpref.value; if (S_MusicDisabled()) return; @@ -2359,7 +2363,8 @@ void S_ChangeMusicEx(const char *mmusic, UINT16 mflags, boolean looping, UINT32 I_FadeSong(0, prefadems, S_ChangeMusicToQueue); return; } - else if (strnicmp(music_name, newmusic, 6) || (mflags & MUSIC_FORCERESET)) + else if (strnicmp(music_name, newmusic, 6) || (mflags & MUSIC_FORCERESET) || + (midipref != currentmidi && S_PrefAvailable(midipref, newmusic))) { CONS_Debug(DBG_DETAILED, "Now playing song %s\n", newmusic); @@ -2665,32 +2670,24 @@ void GameDigiMusic_OnChange(void) digital_disabled = false; I_StartupSound(); // will return early if initialised I_InitMusic(); - S_StopMusic(); + if (Playing()) P_RestoreMusic(&players[consoleplayer]); - else + else if ((!cv_musicpref.value || midi_disabled) && S_DigExists("_clear")) S_ChangeMusicInternal("_clear", false); } else { digital_disabled = true; - if (S_MusicType() != MU_MID) + if (S_MusicType() != MU_MID && S_MusicType() != MU_MID_EX) { - if (midi_disabled) - S_StopMusic(); - else + S_StopMusic(); + if (!midi_disabled) { - char mmusic[7]; - UINT16 mflags; - boolean looping; - - if (S_MusicInfo(mmusic, &mflags, &looping) && S_MIDIExists(mmusic)) - { - S_StopMusic(); - S_ChangeMusic(mmusic, mflags, looping); - } + if (Playing()) + P_RestoreMusic(&players[consoleplayer]); else - S_StopMusic(); + S_ChangeMusicInternal("_clear", false); } } } @@ -2708,9 +2705,10 @@ void GameMIDIMusic_OnChange(void) midi_disabled = false; I_StartupSound(); // will return early if initialised I_InitMusic(); + if (Playing()) P_RestoreMusic(&players[consoleplayer]); - else + else if ((cv_musicpref.value || digital_disabled) && S_MIDIExists("_clear")) S_ChangeMusicInternal("_clear", false); } else @@ -2718,26 +2716,30 @@ void GameMIDIMusic_OnChange(void) midi_disabled = true; if (S_MusicType() == MU_MID || S_MusicType() == MU_MID_EX) { - if (digital_disabled) - S_StopMusic(); - else + S_StopMusic(); + if (!digital_disabled) { - char mmusic[7]; - UINT16 mflags; - boolean looping; - - if (S_MusicInfo(mmusic, &mflags, &looping) && S_DigExists(mmusic)) - { - S_StopMusic(); - S_ChangeMusic(mmusic, mflags, looping); - } + if (Playing()) + P_RestoreMusic(&players[consoleplayer]); else - S_StopMusic(); + S_ChangeMusicInternal("_clear", false); } } } } +void MusicPref_OnChange(void) +{ + if (M_CheckParm("-nomusic") || M_CheckParm("-noaudio") || + M_CheckParm("-nomidimusic") || M_CheckParm("-nodigmusic")) + return; + + if (Playing()) + P_RestoreMusic(&players[consoleplayer]); + else if (S_PrefAvailable(cv_musicpref.value, "_clear")) + S_ChangeMusicInternal("_clear", false); +} + #ifdef HAVE_OPENMPT void ModFilter_OnChange(void) { diff --git a/src/s_sound.h b/src/s_sound.h index 3334fcb69..35d1c3dc5 100644 --- a/src/s_sound.h +++ b/src/s_sound.h @@ -46,6 +46,7 @@ extern consvar_t cv_1upsound; extern consvar_t cv_gamedigimusic; extern consvar_t cv_gamemidimusic; extern consvar_t cv_gamesounds; +extern consvar_t cv_musicpref; extern consvar_t cv_playmusicifunfocused; extern consvar_t cv_playsoundsifunfocused; @@ -178,11 +179,16 @@ boolean S_MusicPaused(void); boolean S_MusicNotInFocus(void); musictype_t S_MusicType(void); const char *S_MusicName(void); -boolean S_MusicInfo(char *mname, UINT16 *mflags, boolean *looping); boolean S_MusicExists(const char *mname, boolean checkMIDI, boolean checkDigi); #define S_DigExists(a) S_MusicExists(a, false, true) #define S_MIDIExists(a) S_MusicExists(a, true, false) +// Returns whether the preferred format a (true = MIDI, false = Digital) +// exists and is enabled for musicname b +#define S_PrefAvailable(a, b) (a ? \ + (!S_MIDIMusicDisabled() && S_MIDIExists(b)) : \ + (!S_DigMusicDisabled() && S_DigExists(b))) + // // Music Effects // diff --git a/src/sdl/CMakeLists.txt b/src/sdl/CMakeLists.txt index 70aa68c88..687e8b388 100644 --- a/src/sdl/CMakeLists.txt +++ b/src/sdl/CMakeLists.txt @@ -1,6 +1,10 @@ # Declare SDL2 interface sources -set(SRB2_CONFIG_SDL2_USEMIXER ON CACHE BOOL "Use SDL2_mixer or regular sdl sound") +if(NOT ${SRB2_CONFIG_HAVE_MIXERX}) + set(SRB2_CONFIG_SDL2_USEMIXER ON CACHE BOOL "Use SDL2_mixer or regular sdl sound") +else() + set(SRB2_CONFIG_SDL2_USEMIXER OFF) +endif() if(${SRB2_CONFIG_SDL2_USEMIXER}) if(${SRB2_CONFIG_USE_INTERNAL_LIBRARIES}) @@ -22,6 +26,8 @@ if(${SRB2_CONFIG_SDL2_USEMIXER}) message(WARNING "You specified that SDL2_mixer is available, but it was not found. Falling back to sdl sound.") set(SRB2_SDL2_SOUNDIMPL sdl_sound.c) endif() +elseif(${MIXERX_FOUND}) + set(SRB2_SDL2_SOUNDIMPL mixer_sound.c) else() set(SRB2_SDL2_SOUNDIMPL sdl_sound.c) endif() @@ -156,6 +162,7 @@ if(${SDL2_FOUND}) SDL2_mixer ${GME_LIBRARIES} ${OPENMPT_LIBRARIES} + ${MIXERX_LIBRARIES} ${PNG_LIBRARIES} ${ZLIB_LIBRARIES} ${OPENGL_LIBRARIES} @@ -168,6 +175,7 @@ if(${SDL2_FOUND}) ${SDL2_MIXER_LIBRARIES} ${GME_LIBRARIES} ${OPENMPT_LIBRARIES} + ${MIXERX_LIBRARIES} ${PNG_LIBRARIES} ${ZLIB_LIBRARIES} ${OPENGL_LIBRARIES} @@ -249,28 +257,33 @@ if(${SDL2_FOUND}) ${SDL2_MIXER_INCLUDE_DIRS} ${GME_INCLUDE_DIRS} ${OPENMPT_INCLUDE_DIRS} + ${MIXERX_INCLUDE_DIRS} ${PNG_INCLUDE_DIRS} ${ZLIB_INCLUDE_DIRS} ${OPENGL_INCLUDE_DIRS} ${CURL_INCLUDE_DIRS} ) - if(${SRB2_HAVE_MIXER}) + if((${SRB2_HAVE_MIXER}) OR (${SRB2_HAVE_MIXERX})) target_compile_definitions(SRB2SDL2 PRIVATE -DHAVE_MIXER -DSOUND=SOUND_MIXER) endif() target_compile_definitions(SRB2SDL2 PRIVATE - -DHAVE_SDL + -DDDIRECTFULLSCREEN -DHAVE_SDL ) - ## strip debug symbols into separate file when using gcc - if(CMAKE_COMPILER_IS_GNUCC) - if(${CMAKE_BUILD_TYPE} MATCHES Debug) + ## strip debug symbols into separate file when using gcc. + ## to be consistent with Makefile, don't generate for OS X. + if((CMAKE_COMPILER_IS_GNUCC) AND NOT (${CMAKE_SYSTEM} MATCHES Darwin)) + if((${CMAKE_BUILD_TYPE} MATCHES Debug) OR (${CMAKE_BUILD_TYPE} MATCHES RelWithDebInfo)) + if(${CMAKE_BUILD_TYPE} MATCHES Debug) + set(OBJCOPY_ONLY_KEEP_DEBUG "--only-keep-debug") + endif() message(STATUS "Will make separate debug symbols in *.debug") add_custom_command(TARGET SRB2SDL2 POST_BUILD - COMMAND ${OBJCOPY} --only-keep-debug $ $.debug + COMMAND ${OBJCOPY} ${OBJCOPY_ONLY_KEEP_DEBUG} $ $.debug COMMAND ${OBJCOPY} --strip-debug $ - COMMAND ${OBJCOPY} --add-gnu-debuglink=$.debug $ + COMMAND ${OBJCOPY} --add-gnu-debuglink=$.debug $ ) endif() endif() @@ -284,6 +297,15 @@ if(${SDL2_FOUND}) install(TARGETS SRB2SDL2 SRB2SDL2 RUNTIME DESTINATION . ) + if ((${CMAKE_BUILD_TYPE} MATCHES Debug) OR (${CMAKE_BUILD_TYPE} MATCHES RelWithDebInfo)) + set(SRB2_DEBUG_INSTALL OFF CACHE BOOL "Insert *.debug file into the install directory or package.") + if (${SRB2_DEBUG_INSTALL}) + install(FILES $.debug + DESTINATION . + OPTIONAL + ) + endif() + endif() endif() if(${CMAKE_SYSTEM} MATCHES Windows) @@ -297,6 +319,7 @@ if(${SDL2_FOUND}) HINTS ${CMAKE_SOURCE_DIR}/libs/SDL2/x86_64-w64-mingw32/bin HINTS ${CMAKE_SOURCE_DIR}/libs/SDL2_mixer/x86_64-w64-mingw32/bin HINTS ${CMAKE_SOURCE_DIR}/libs/libopenmpt/bin/x86_64/mingw + HINTS ${CMAKE_SOURCE_DIR}/libs/SDLMixerX/x86_64-w64-mingw32/bin ) else() find_library(SRB2_SDL2_DLL_${dllname} "${defaultname}" @@ -304,6 +327,7 @@ if(${SDL2_FOUND}) HINTS ${CMAKE_SOURCE_DIR}/libs/SDL2/i686-w64-mingw32/bin HINTS ${CMAKE_SOURCE_DIR}/libs/SDL2_mixer/i686-w64-mingw32/bin HINTS ${CMAKE_SOURCE_DIR}/libs/libopenmpt/bin/x86/mingw + HINTS ${CMAKE_SOURCE_DIR}/libs/SDLMixerX/i686-w64-mingw32/bin ) endif() else() @@ -313,6 +337,7 @@ if(${SDL2_FOUND}) HINTS ${CMAKE_SOURCE_DIR}/libs/SDL2/lib/x64 HINTS ${CMAKE_SOURCE_DIR}/libs/SDL2_mixer/lib/x64 HINTS ${CMAKE_SOURCE_DIR}/libs/libopenmpt/bin/x86_64/mingw + HINTS ${CMAKE_SOURCE_DIR}/libs/SDLMixerX/x86_64-w64-mingw32/bin ) else() find_library(SRB2_SDL2_DLL_${dllname} "${defaultname}" @@ -320,6 +345,7 @@ if(${SDL2_FOUND}) HINTS ${CMAKE_SOURCE_DIR}/libs/SDL2/lib/x86 HINTS ${CMAKE_SOURCE_DIR}/libs/SDL2_mixer/lib/x86 HINTS ${CMAKE_SOURCE_DIR}/libs/libopenmpt/bin/x86/mingw + HINTS ${CMAKE_SOURCE_DIR}/libs/SDLMixerX/i686-w64-mingw32/bin ) endif() endif() @@ -343,6 +369,12 @@ if(${SDL2_FOUND}) if(${SRB2_CONFIG_HAVE_OPENMPT}) getwinlib(libopenmpt "libopenmpt.dll") endif() + if(${SRB2_CONFIG_HAVE_MIXERX}) + getwinlib(SDL2_mixer_ext "SDL2_mixer_ext.dll") + getwinlib(libfluidsynth-2 "libfluidsynth-2.dll") + getwinlib(libgcc_s_sjlj-1 "libgcc_s_sjlj-1.dll") + getwinlib(libstdc++-6 "libstdc++-6.dll") + endif() install(PROGRAMS ${win_extra_dll_list} diff --git a/src/w_wad.c b/src/w_wad.c index e6dedba22..e4a19f30e 100644 --- a/src/w_wad.c +++ b/src/w_wad.c @@ -1862,7 +1862,7 @@ void W_VerifyFileMD5(UINT16 wadfilenum, const char *matchmd5) #else I_Error #endif - (M_GetText("File is corrupt or has been modified: %s (found md5: %s, wanted: %s)\n"), wadfiles[wadfilenum]->filename, actualmd5text, matchmd5); + (M_GetText("File is old, is corrupt or has been modified: %s (found md5: %s, wanted: %s)\n"), wadfiles[wadfilenum]->filename, actualmd5text, matchmd5); } #endif } diff --git a/src/y_inter.c b/src/y_inter.c index 58e0c4a88..d857d60dc 100644 --- a/src/y_inter.c +++ b/src/y_inter.c @@ -141,7 +141,6 @@ static y_data data; // graphics static patch_t *bgpatch = NULL; // INTERSCR -static patch_t *widebgpatch = NULL; // INTERSCW static patch_t *bgtile = NULL; // SPECTILE/SRB2BACK static patch_t *interpic = NULL; // custom picture defined in map header static boolean usetile; @@ -330,7 +329,7 @@ void Y_IntermissionDrawer(void) safetorender = false; } - if (!usebuffer || !safetorender) + if (!safetorender) V_DrawFill(0, 0, BASEVIDWIDTH, BASEVIDHEIGHT, 31); if (!safetorender) @@ -359,12 +358,11 @@ void Y_IntermissionDrawer(void) else if (rendermode != render_soft && usebuffer) HWR_DrawIntermissionBG(); #endif - else + else if (bgpatch) { - if (widebgpatch && rendermode == render_soft && vid.width / vid.dupx == 400) - V_DrawScaledPatch(0, 0, V_SNAPTOLEFT, widebgpatch); - else if (bgpatch) - V_DrawScaledPatch(0, 0, 0, bgpatch); + fixed_t hs = vid.width * FRACUNIT / BASEVIDWIDTH; + fixed_t vs = vid.height * FRACUNIT / BASEVIDHEIGHT; + V_DrawStretchyFixedPatch(0, 0, hs, vs, V_NOSCALEPATCH, bgpatch, NULL); } } else if (bgtile) @@ -1266,7 +1264,6 @@ void Y_StartIntermission(void) data.coop.actnum = mapheaderinfo[gamemap-1]->actnum; // get background patches - widebgpatch = W_CachePatchName("INTERSCW", PU_PATCH); bgpatch = W_CachePatchName("INTERSCR", PU_PATCH); // grab an interscreen if appropriate @@ -2084,7 +2081,6 @@ static void Y_UnloadData(void) // unload the background patches UNLOAD(bgpatch); - UNLOAD(widebgpatch); UNLOAD(bgtile); UNLOAD(interpic); @@ -2127,7 +2123,6 @@ static void Y_CleanupData(void) { // unload the background patches CLEANUP(bgpatch); - CLEANUP(widebgpatch); CLEANUP(bgtile); CLEANUP(interpic); diff --git a/tools/masterserver/.gitignore b/tools/masterserver/.gitignore index 9f45745a3..8ae879eec 100644 --- a/tools/masterserver/.gitignore +++ b/tools/masterserver/.gitignore @@ -1,4 +1,4 @@ /client /server -/server.log -/*.o +/*.log +/*.o \ No newline at end of file diff --git a/tools/masterserver/ipcs.h b/tools/masterserver/ipcs.h index b9dc52fdf..4e144f4a5 100644 --- a/tools/masterserver/ipcs.h +++ b/tools/masterserver/ipcs.h @@ -140,8 +140,8 @@ typedef struct char port[8]; char name[32]; INT32 room; - char key[32]; // Secret key for linking dedicated servers to accounts char version[8]; // format is: x.yy.z (like 1.30.2 or 1.31) + char key[32]; // Secret key for linking dedicated servers to accounts } ATTRPACK msg_server_t; typedef struct diff --git a/tools/masterserver/masterserver.sh b/tools/masterserver/masterserver.sh index 9b1adb128..fe4ba0071 100755 --- a/tools/masterserver/masterserver.sh +++ b/tools/masterserver/masterserver.sh @@ -5,9 +5,10 @@ # Get LSB functions . /lib/lsb/init-functions -. /etc/default/rcS +#. /etc/default/rcS -SRB2MS=/usr/local/bin/masterserver +#SRB2MS=/usr/local/bin/masterserver +SRB2MS=./server SRB2MS_PORT=28900 # Check that the package is still installed @@ -15,11 +16,9 @@ SRB2MS_PORT=28900 case "$1" in start) - log_begin_msg "Starting SRB2MS..." + log_begin_msg "Starting SRB2MS...\n" umask 002 - if start-stop-daemon --start \ - --exec $SRB2MS \ - -- $SRB2MS_PORT; then + if exec $SRB2MS $SRB2MS_PORT & then log_end_msg 0 else log_end_msg $? @@ -27,11 +26,11 @@ case "$1" in ;; stop) - log_begin_msg "Stopping SRB2MS..." - if start-stop-daemon --stop --exec $SRB2MS; then - log_end_msg 0 + log_begin_msg "Stopping SRB2MS...\n" + if killall $SRB2MS -q & then + log_end_msg 0 else - log_end_msg $? + log_end_msg $? fi ;; @@ -40,7 +39,7 @@ case "$1" in ;; *) - e cho "Usage: /etc/init.d/masterserver {start|stop|restart|force-reload}" + echo "Usage: $0 {start|stop|restart|force-reload}" exit 1 ;; esac diff --git a/tools/masterserver/server.cpp b/tools/masterserver/server.cpp index b7ed0d6b4..d00205301 100644 --- a/tools/masterserver/server.cpp +++ b/tools/masterserver/server.cpp @@ -86,7 +86,7 @@ typedef struct //============================================================================= -#define HOSTNAME "loopback" +#define HOSTNAME "localhost" #define USER "srb2_ms" #define PASSWORD "gLRDRb7WgLRDRb7W" #define DATABASE "srb2_ms" @@ -291,17 +291,17 @@ void MySQL_AddServer(const char *ip, const char *port, const char *name, const c char checkquery[500]; char updatequery[5000]; char queryp1[5000] = "INSERT INTO `ms_servers` (`name`,`ip`,`port`,`version`,`timestamp`,`room`,`key`) VALUES ('%s','%s','%s','%s','%ld','%d','%s')"; - char checkqueryp1[500] = "SELECT room_override FROM `ms_servers` WHERE `ip` = '%s'"; + char checkqueryp1[500] = "SELECT room_override FROM `ms_servers` WHERE `ip` = '%s' AND `port` = '%s'"; char updatequeryp1[5000]; if(firstadd) { logPrintf(logfile, "First add.\n"); - strcpy(updatequeryp1, "UPDATE `ms_servers` SET `name` = '%s', `port` = '%s', `version` = '%s', timestamp = '%ld', upnow = '1', `room` = '%d', `delisted` = '0', `key` = '%s' WHERE `ip` = '%s'"); + strcpy(updatequeryp1, "UPDATE `ms_servers` SET `name` = '%s', `port` = '%s', `version` = '%s', timestamp = '%ld', upnow = '1', `room` = '%d', `delisted` = '0', `key` = '%s' WHERE `ip` = '%s' AND `port` = '%s'"); } else { logPrintf(logfile, "Update ping.\n"); - strcpy(updatequeryp1, "UPDATE `ms_servers` SET `name` = '%s', `port` = '%s', `version` = '%s', timestamp = '%ld', upnow = '1', `room` = '%d', `key` = '%s' WHERE `ip` = '%s' AND `delisted` = '0'"); + strcpy(updatequeryp1, "UPDATE `ms_servers` SET `name` = '%s', `port` = '%s', `version` = '%s', timestamp = '%ld', upnow = '1', `room` = '%d', `key` = '%s' WHERE `ip` = '%s' AND `port` = '%s' AND `delisted` = '0'"); } MySQL_Conn(false); mysql_real_escape_string(conn, escapedName, name, (unsigned long)strlen(name)); @@ -314,10 +314,10 @@ void MySQL_AddServer(const char *ip, const char *port, const char *name, const c logPrintf(errorfile, "IP %s tried to use the private room %d! THIS SHOULD NOT HAPPEN\n", ip, room); return; } - sprintf(checkquery, checkqueryp1, ip); + sprintf(checkquery, checkqueryp1, ip, port); time_t timestamp; timestamp = time (NULL); - logPrintf(logfile, "Checking for existing servers in table with the same IP...\n"); + logPrintf(logfile, "Checking for existing servers in table with the same IP and port...\n"); logPrintf(mysqlfile, "Executing MySQL Query: %s\n", checkquery); if(mysql_query(conn, checkquery)) { logPrintf(errorfile, "MYSQL ERROR: %s\n", mysql_error(conn)); @@ -341,9 +341,9 @@ void MySQL_AddServer(const char *ip, const char *port, const char *name, const c if(atoi(row[0]) != 0) room = atoi(row[0]); mysql_free_result(res); - logPrintf(logfile, "Server's IP already exists, so let's just update it instead...\n"); + logPrintf(logfile, "Server's IP and port already exists, so let's just update it instead...\n"); logPrintf(logfile, "Updating Server Data for %s\n", ip); - sprintf(updatequery, updatequeryp1, escapedName, escapedPort, escapedVersion, timestamp, room, escapedKey, ip); + sprintf(updatequery, updatequeryp1, escapedName, escapedPort, escapedVersion, timestamp, room, escapedKey, ip, port); logPrintf(mysqlfile, "Executing MySQL Query: %s\n", updatequery); if(mysql_query(conn, updatequery)) { logPrintf(errorfile, "MYSQL ERROR: %s\n", mysql_error(conn)); @@ -619,10 +619,10 @@ void MySQL_ListServServers(UINT32 id, UINT32 type, const char *ip) { void MySQL_RemoveServer(char *ip, char *port, char *name, char *version) { char escapedName[255]; char updatequery[5000]; - char updatequeryp1[5000] = "UPDATE `ms_servers` SET upnow = '0' WHERE `ip` = '%s' AND `permanent` = '0'"; + char updatequeryp1[5000] = "UPDATE `ms_servers` SET upnow = '0' WHERE `ip` = '%s' AND `port` = '%s' AND `permanent` = '0'"; MySQL_Conn(false); mysql_real_escape_string(conn, escapedName, name, (unsigned long)strlen(name)); - sprintf(updatequery, updatequeryp1, ip); + sprintf(updatequery, updatequeryp1, ip, port); logPrintf(mysqlfile, "Executing MySQL Query: %s\n", updatequery); if(mysql_query(conn, updatequery)) { logPrintf(errorfile, "MYSQL ERROR: %s\n", mysql_error(conn)); @@ -841,6 +841,10 @@ static void addServer(int id, char *buffer, bool firstadd) info->port[sizeof (info->port)-1] = '\0'; info->name[sizeof (info->name)-1] = '\0'; info->version[sizeof (info->version)-1] = '\0'; + + logPrintf(logfile, "addServer(): Version = \"%s\"\n", info->version); + logPrintf(logfile, "addServer(): Key = \"%s\"\n", info->key); + // retrieve the true ip of the server strcpy(info->ip, server_socket.getClientIP(id)); //strcpy(info->port, server_socket.getClientPort(id)); @@ -995,7 +999,7 @@ int main(int argc, char *argv[]) if (server_socket.listen(argv[1]) < 0) { - fprintf(stderr, "Error while initializing the server\n"); + fprintf(stderr, "Error while initializing the server; port being used! Try killing the other Master Server.\n"); exit(2); } diff --git a/tools/masterserver/structure.sql b/tools/masterserver/structure.sql index 3cc2cb15b..013c22383 100644 --- a/tools/masterserver/structure.sql +++ b/tools/masterserver/structure.sql @@ -13,8 +13,8 @@ SET time_zone = "+00:00"; -- Database: `srb2ms` -- -CREATE DATABASE IF NOT EXISTS `srb2ms` DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci; -USE `srb2ms`; +CREATE DATABASE IF NOT EXISTS `srb2_ms` DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci; +USE `srb2_ms`; -- -------------------------------------------------------- @@ -25,8 +25,8 @@ USE `srb2ms`; CREATE TABLE `ms_bans` ( `bid` int(11) DEFAULT NULL, - `ipstart` int(11) DEFAULT NULL, - `ipend` int(11) DEFAULT NULL, + `ipstart` int(10) unsigned DEFAULT NULL, + `ipend` int(10) unsigned DEFAULT NULL, `full_endtime` int(11) DEFAULT NULL, `permanent` tinyint(1) DEFAULT NULL, `hostonly` tinyint(1) DEFAULT NULL, @@ -63,19 +63,19 @@ INSERT INTO `ms_rooms` (`room_id`, `title`, `motd`, `visible`, `order`, `private -- CREATE TABLE `ms_servers` ( - `sid` int(11) NOT NULL, + `sid` int(11) primary key AUTO_INCREMENT, `name` text COLLATE utf8mb4_unicode_ci NOT NULL, `ip` text COLLATE utf8mb4_unicode_ci NOT NULL, - `port` int(11) NOT NULL, + `port` int(11) NOT NULL DEFAULT 5029, `version` text COLLATE utf8mb4_unicode_ci NOT NULL, - `timestamp` int(11) NOT NULL, - `room` int(11) NOT NULL, + `timestamp` int(11) NOT NULL DEFAULT 0, + `room` int(11) NOT NULL DEFAULT 0, `key` text COLLATE utf8mb4_unicode_ci NOT NULL, - `room_override` int(11) NOT NULL, - `upnow` tinyint(1) NOT NULL, - `permanent` tinyint(1) NOT NULL, - `delisted` tinyint(1) NOT NULL, - `sticky` int(11) NOT NULL + `room_override` int(11) NOT NULL DEFAULT 0, + `upnow` tinyint(1) NOT NULL DEFAULT 1, + `permanent` tinyint(1) NOT NULL DEFAULT 0, + `delisted` tinyint(1) NOT NULL DEFAULT 0, + `sticky` int(11) NOT NULL DEFAULT 0 ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; -- -------------------------------------------------------- @@ -85,16 +85,20 @@ CREATE TABLE `ms_servers` ( -- CREATE TABLE `ms_versions` ( - `mod_id` int(11) NOT NULL, - `mod_version` int(11) NOT NULL + `mod_id` int(10) unsigned primary key AUTO_INCREMENT, + `mod_version` int(10) unsigned NOT NULL DEFAULT 1, + `mod_vstring` varchar(45) NOT NULL DEFAULT 'v1.0', + `mod_codebase` int(10) unsigned NOT NULL DEFAULT 205, + `mod_name` varchar(255) NOT NULL DEFAULT 'Default MOD Name', + `mod_url` text NOT NULL ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; -- -- Dumping data for table `ms_versions` -- -INSERT INTO `ms_versions` (`mod_id`, `mod_version`) VALUES -(12, 25); +INSERT INTO `ms_versions` (`mod_id`, `mod_version`, `mod_vstring`, `mod_codebase`, `mod_name`, `mod_url`) VALUES +(18, 42, 'v2.2.2', 205, 'SRB2 2.2', 'SRB2.org'); -- -------------------------------------------------------- @@ -114,4 +118,4 @@ COMMIT; /*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */; /*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */; -/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */; +/*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */; \ No newline at end of file