- backend code matching with GZDoom

This commit is contained in:
Christoph Oelckers 2020-04-12 00:04:02 +02:00
parent 0ca4bbd0c4
commit 8e87674d4c
59 changed files with 3545 additions and 955 deletions

View file

@ -394,9 +394,9 @@ endif()
# Update gitinfo.h
add_custom_target( revision_check ALL
COMMAND updaterevision source/gitinfo.h
COMMAND "${CMAKE_COMMAND}" -P "${CMAKE_SOURCE_DIR}/tools/updaterevision/UpdateRevision.cmake" src/gitinfo.h
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
DEPENDS updaterevision )
)
# required libraries
@ -562,8 +562,8 @@ else()
endif()
add_custom_command( OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h
COMMAND re2c --no-generation-date -s -o ${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h ${CMAKE_CURRENT_SOURCE_DIR}/core/utility/sc_man_scanner.re
DEPENDS re2c ${CMAKE_CURRENT_SOURCE_DIR}/core/utility/sc_man_scanner.re )
COMMAND re2c --no-generation-date -s -o ${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h ${CMAKE_CURRENT_SOURCE_DIR}/common/engine/sc_man_scanner.re
DEPENDS re2c ${CMAKE_CURRENT_SOURCE_DIR}/common/engine/sc_man_scanner.re )
include_directories( ${CMAKE_CURRENT_BINARY_DIR} )
@ -603,7 +603,9 @@ file( GLOB HEADER_FILES
core/rendering/hwrenderer/utility/*.h
common/utility/*.h
common/engine/*.h
common/filesystem/*.h
common/textures/*.h
common/thirdparty/*.h
common/thirdparty/rapidjson/*.h
common/thirdparty/math./*h
@ -624,7 +626,7 @@ file( GLOB HEADER_FILES
set( NOT_COMPILED_SOURCE_FILES
${OTHER_SYSTEM_SOURCES}
sc_man_scanner.h
core/utility/sc_man_scanner.re
common/engine/sc_man_scanner.re
platform/win32/zutil.natvis
)
@ -721,6 +723,7 @@ set (PCH_SOURCES
core/console/c_con.cpp
common/thirdparty/sfmt/SFMT.cpp
common/textures/bitmap.cpp
common/utility/engineerrors.cpp
common/utility/i_module.cpp
common/utility/m_alloc.cpp
@ -735,6 +738,7 @@ set (PCH_SOURCES
common/utility/m_argv.cpp
common/utility/s_playlist.cpp
common/utility/zstrformat.cpp
common/utility/name.cpp
common/thirdparty/md5.cpp
common/thirdparty/superfasthash.cpp
common/filesystem/filesystem.cpp
@ -749,14 +753,13 @@ set (PCH_SOURCES
common/filesystem/file_whres.cpp
common/filesystem/file_directory.cpp
common/filesystem/resourcefile.cpp
common/engine/sc_man.cpp
#common/engine/palettecontainer.cpp // not yet operational.
core/utility/name.cpp
core/utility/m_png.cpp
core/utility/sc_man.cpp
core/utility/stringtable.cpp
core/utility/stats.cpp
core/textures/bitmap.cpp
core/textures/buildtiles.cpp
core/textures/texture.cpp
core/textures/image.cpp
@ -862,7 +865,7 @@ add_executable( ${PROJECT_NAME} WIN32 MACOSX_BUNDLE
#set_source_files_properties( ${FASTMATH_SOURCES} PROPERTIES COMPILE_FLAGS ${DEM_FASTMATH_FLAG} )
set_source_files_properties( xlat/parse_xlat.cpp PROPERTIES OBJECT_DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/xlat_parser.c" )
set_source_files_properties( utility/sc_man.cpp PROPERTIES OBJECT_DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h" )
set_source_files_properties( common/engine/sc_man.cpp PROPERTIES OBJECT_DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h" )
set_source_files_properties( ${NOT_COMPILED_SOURCE_FILES} PROPERTIES HEADER_FILE_ONLY TRUE )
@ -910,9 +913,10 @@ include_directories(
core/rendering
platform
common/thirdparty
common/textures
common/filesystem
common/utility
common/engine
${CMAKE_BINARY_DIR}/libraries/gdtoa
${SYSTEM_SOURCES_DIR}
@ -1021,8 +1025,10 @@ source_group("Platform" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/platfor
source_group("Platform\\Win32" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/platform/win32/.+")
source_group("Platform\\POSIX" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/platform/posix/.+")
source_group("Common" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/.+")
source_group("Common\\File System" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/filesystem/.+")
source_group("Common\\Utility" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/utility/.+")
source_group("Common\\Engine" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/engine/.+")
source_group("Common\\File System" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/filesystem/.+")
source_group("Common\\Textures" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/textures/.+")
source_group("Common\\Third Party" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/thirdparty/.+")
source_group("Common\\Third Party\\Math" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/thirdparty/math/.+")
source_group("Common\\Third Party\\RapidJSON" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/common/thirdparty/rapidjson/.+")

View file

@ -512,7 +512,7 @@ int VectorScan(spritetype *pSprite, int nOffset, int nZOffset, int dx, int dy, i
if (width2 >= 0 && width2 < tilesiz[nPicnum].x)
{
auto pData = tileLoadTile(nPicnum);
if (pData[width2*tilesiz[nPicnum].y+height2] != (char)255)
if (pData[width2*tilesiz[nPicnum].y+height2] != TRANSPARENT_INDEX)
return 3;
}
}
@ -599,7 +599,7 @@ int VectorScan(spritetype *pSprite, int nOffset, int nZOffset, int dx, int dy, i
else
nPixel = nHOffset*nSizY + nOffset;
if (pData[nPixel] == (char)255)
if (pData[nPixel] == TRANSPARENT_INDEX)
{
int bakCstat = pWall->cstat;
pWall->cstat &= ~64;

View file

@ -48,7 +48,7 @@ BEGIN_BLD_NS
void LevelWarp(int nEpisode, int nLevel);
static int osdcmd_map(osdcmdptr_t parm)
static int osdcmd_map(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
return OSDCMD_SHOWHELP;
@ -96,7 +96,7 @@ static int osdcmd_map(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_demo(osdcmdptr_t parm)
static int osdcmd_demo(CCmdFuncPtr parm)
{
if (numplayers > 1)
{
@ -121,7 +121,7 @@ static int osdcmd_demo(osdcmdptr_t parm)
}
static int osdcmd_give(osdcmdptr_t parm)
static int osdcmd_give(CCmdFuncPtr parm)
{
if (numplayers != 1 || !gGameStarted || gMe->pXSprite->health == 0)
{
@ -180,7 +180,7 @@ static int osdcmd_give(osdcmdptr_t parm)
return OSDCMD_SHOWHELP;
}
static int osdcmd_god(osdcmdptr_t UNUSED(parm))
static int osdcmd_god(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
if (numplayers == 1 && gGameStarted)
@ -194,7 +194,7 @@ static int osdcmd_god(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
static int osdcmd_noclip(osdcmdptr_t UNUSED(parm))
static int osdcmd_noclip(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -220,7 +220,7 @@ void onvideomodechange(int32_t newmode)
UpdateDacs(gLastPal, false);
}
static int osdcmd_activatecheat(osdcmdptr_t parm)
static int osdcmd_activatecheat(CCmdFuncPtr parm)
{
FString CheatEntry;
if (parm->numparms != 1)
@ -238,7 +238,7 @@ static int osdcmd_activatecheat(osdcmdptr_t parm)
}
}
static int osdcmd_levelwarp(osdcmdptr_t parm)
static int osdcmd_levelwarp(CCmdFuncPtr parm)
{
if (parm->numparms != 2)
return OSDCMD_SHOWHELP;
@ -255,16 +255,16 @@ static int osdcmd_levelwarp(osdcmdptr_t parm)
int32_t registerosdcommands(void)
{
OSD_RegisterFunction("map","map <mapname>: loads the given map", osdcmd_map);
OSD_RegisterFunction("demo","demo <demofile or demonum>: starts the given demo", osdcmd_demo);
C_RegisterFunction("map","map <mapname>: loads the given map", osdcmd_map);
C_RegisterFunction("demo","demo <demofile or demonum>: starts the given demo", osdcmd_demo);
OSD_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
OSD_RegisterFunction("god","god: toggles god mode", osdcmd_god);
OSD_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
C_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
C_RegisterFunction("god","god: toggles god mode", osdcmd_god);
C_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
OSD_RegisterFunction("activatecheat","activatecheat <string>: activates a classic cheat code", osdcmd_activatecheat);
C_RegisterFunction("activatecheat","activatecheat <string>: activates a classic cheat code", osdcmd_activatecheat);
OSD_RegisterFunction("levelwarp","levelwarp <e> <m>: warp to episode 'e' and map 'm'", osdcmd_levelwarp);
C_RegisterFunction("levelwarp","levelwarp <e> <m>: warp to episode 'e' and map 'm'", osdcmd_levelwarp);
return 0;
}

View file

@ -65,7 +65,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "v_2ddrawer.h"
#include "v_video.h"
CVARD(Bool, hud_powerupduration, true, CVAR_ARCHIVE|CVAR_FRONTEND_BLOOD, "enable/disable displaying the remaining seconds for power-ups")
CVARD(Bool, hud_powerupduration, true, CVAR_ARCHIVE/*|CVAR_FRONTEND_BLOOD*/, "enable/disable displaying the remaining seconds for power-ups")
BEGIN_BLD_NS
@ -1823,7 +1823,7 @@ void viewInit(void)
}
#endif
uint8_t *data = tileAllocTile(4077, kLensSize, kLensSize, 0, 0);
memset(data, 255, kLensSize*kLensSize);
memset(data, TRANSPARENT_INDEX, kLensSize*kLensSize);
gGameMessageMgr.SetState(hud_messages);
gGameMessageMgr.SetCoordinates(1, 1);
char nFont;

View file

@ -11,6 +11,8 @@
#ifndef build_h_
#define build_h_
#define TRANSPARENT_INDEX 255
static_assert('\xff' == 255, "Char must be unsigned!");
#if !defined __cplusplus || (__cplusplus < 201103L && !defined _MSC_VER)

View file

@ -9,22 +9,13 @@
#include "compat.h"
#include "printf.h"
struct osdfuncparm_t
{
int32_t numparms;
const char* name;
const char** parms;
const char* raw;
};
using osdcmdptr_t = osdfuncparm_t const * const;
#include "c_dispatch.h"
const char *OSD_StripColors(char *outBuf, const char *inBuf);
#define OSDCMD_OK 0
#define OSDCMD_SHOWHELP 1
#define OSDCMD_OK CCMD_OK
#define OSDCMD_SHOWHELP CCMD_SHOWHELP
// void OSD_Draw();
@ -36,11 +27,5 @@ inline void OSD_DispatchQueued(void)
C_RunDelayedCommands();
}
// registers a function
// name = name of the function
// help = a short help string
// func = the entry point to the function
int OSD_RegisterFunction(const char *pszName, const char *pszDesc, int (*func)(osdcmdptr_t));
#endif // osd_h_

View file

@ -11,6 +11,7 @@
#include "clip.h"
#include "engine_priv.h"
static int16_t clipnum;
static linetype clipit[MAXCLIPNUM];
static int32_t clipsectnum, origclipsectnum, clipspritenum;
@ -2539,7 +2540,7 @@ restart_grand:
int32_t ytex = mulscale16(vcoefup16, tilesiz[tilenum].y);
auto texel = (tilePtr(tilenum) + tilesiz[tilenum].y*xtex + ytex);
if (*texel == 255)
if (*texel == TRANSPARENT_INDEX)
continue;
}
}

View file

@ -143,7 +143,6 @@ xx(ArtiPoisonBag3)
// Strife quests
xx(QuestItem)
xx(Sigil)
xx(ScriptedMarine)
xx(GiveSigilPiece)
xx(SetWeapon)
xx(SetSprite)
@ -151,43 +150,9 @@ xx(SetSprite)
// Armor
xx(BasicArmor)
// The Wings of Wrath
xx(ArtiFly)
// Doom ammo types
xx(Clip)
xx(Shell)
xx(RocketAmmo)
xx(Cell)
// Hexen Mana
xx(Mana1)
xx(Mana2)
// Hexen's fourth weapons
xx(FWeapQuietus)
xx(CWeapWraithverge)
xx(MWeapBloodscourge)
// Misc Hexen classes
xx(LightningZap)
// Ammo and weapon names for the Strife status bar
xx(ClipOfBullets)
xx(PoisonBolts)
xx(ElectricBolts)
xx(HEGrenadeRounds)
xx(PhosphorusGrenadeRounds)
xx(MiniMissiles)
xx(EnergyPod)
xx(StrifeCrossbow)
xx(AssaultGun)
xx(FlameThrower)
xx(MiniMissileLauncher)
xx(StrifeGrenadeLauncher)
xx(Mauler)
xx(BackpackItem)
xx(PuzzleItem)
xx(PuzzleItemNumber)
xx(HealthPickup)
@ -215,28 +180,13 @@ xx(StateProvider)
xx(CallTryPickup)
xx(QuestItem25)
xx(QuestItem28)
xx(QuestItem29)
xx(PowerDoubleFiringSpeed)
xx(PowerInfiniteAmmo)
xx(PowerBuddha)
xx(AcolyteBlue)
xx(SpectralLightningV1)
xx(SpectralLightningV2)
xx(TeleportDest)
xx(TeleportDest2)
// Strife's spectres
xx(AlienSpectre1)
xx(AlienSpectre2)
xx(AlienSpectre3)
xx(AlienSpectre4)
xx(AlienSpectre5)
xx(Oracle)
xx(Chicken)
xx(Pig)
// Standard animator names.
xx(Spawn)
xx(See)
@ -717,6 +667,7 @@ xx(Next)
xx(Prev)
xx(Children)
xx(Owner)
xx(FlameThrower)
xx(HealthFloor)
xx(HealthCeiling)

View file

@ -0,0 +1,656 @@
/*
** r_translate.cpp
** Translation table handling
**
**---------------------------------------------------------------------------
** Copyright 1998-2006 Randy Heit
** All rights reserved.
**
** Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions
** are met:
**
** 1. Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** 2. Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in the
** documentation and/or other materials provided with the distribution.
** 3. The name of the author may not be used to endorse or promote products
** derived from this software without specific prior written permission.
**
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
**---------------------------------------------------------------------------
**
*/
#include "palutil.h"
#include "sc_man.h"
#include "m_crc32.h"
#include "printf.h"
#include "colormatcher.h"
#include "templates.h"
#include "palettecontainer.h"
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
void PaletteContainer::Init(int numslots) // This cannot be a constructor!!!
{
Clear();
// Make sure that index 0 is always the identity translation.
FRemapTable remap;
remap.MakeIdentity();
remap.Inactive = true;
AddRemap(&remap);
TranslationTables.Resize(numslots);
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
void PaletteContainer::Clear()
{
remapArena.FreeAllBlocks();
uniqueRemaps.Reset();
TranslationTables.Reset();
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
FRemapTable* PaletteContainer::AddRemap(FRemapTable* remap)
{
if (!remap) return uniqueRemaps[0];
remap->crc32 = CalcCRC32((uint8_t*)remap->Palette, sizeof(remap->Palette));
for (auto uremap : uniqueRemaps)
{
if (uremap->crc32 == remap->crc32 && uremap->NumEntries == remap->NumEntries && *uremap == *remap)
return uremap;
}
auto newremap = (FRemapTable*)remapArena.Alloc(sizeof(FRemapTable));
*newremap = *remap;
auto index = uniqueRemaps.Push(newremap);
newremap->Index = index;
return newremap;
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
void PaletteContainer::UpdateTranslation(int trans, FRemapTable* remap)
{
auto newremap = AddRemap(remap);
TranslationTables[GetTranslationType(trans)].SetVal(GetTranslationIndex(trans), newremap);
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
int PaletteContainer::AddTranslation(int slot, FRemapTable* remap, int count)
{
uint32_t id;
for (int i = 0; i < count; i++)
{
auto newremap = AddRemap(&remap[i]);
id = TranslationTables[slot].Push(newremap);
}
return TRANSLATION(slot, id);
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
void PaletteContainer::CopyTranslation(int dest, int src)
{
TranslationTables[GetTranslationType(dest)][GetTranslationType(src)] = TranslationToTable(src);
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
FRemapTable *PaletteContainer::TranslationToTable(int translation)
{
unsigned int type = GetTranslationType(translation);
unsigned int index = GetTranslationIndex(translation);
if (type <= 0 || type >= TranslationTables.Size() || index >= NumTranslations(type))
{
return NULL;
}
return GetTranslation(type, index);
}
//----------------------------------------------------------------------------
//
// Stores a copy of this translation but avoids duplicates
//
//----------------------------------------------------------------------------
int PaletteContainer::StoreTranslation(int slot, FRemapTable *remap)
{
unsigned int i;
auto size = NumTranslations(slot);
for (i = 0; i < size; i++)
{
if (*remap == *palMgr.TranslationToTable(TRANSLATION(slot, i)))
{
// A duplicate of this translation already exists
return TRANSLATION(slot, i);
}
}
if (size >= 65535) // Translation IDs only have 16 bits for the index.
{
I_Error("Too many DECORATE translations");
}
return AddTranslation(slot, remap);
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
static bool IndexOutOfRange(const int color)
{
const bool outOfRange = color < 0 || color > 255;
if (outOfRange)
{
Printf(TEXTCOLOR_ORANGE "Palette index %i is out of range [0..255]\n", color);
}
return outOfRange;
}
static bool IndexOutOfRange(const int start, const int end)
{
const bool outOfRange = IndexOutOfRange(start);
return IndexOutOfRange(end) || outOfRange;
}
static bool IndexOutOfRange(const int start1, const int end1, const int start2, const int end2)
{
const bool outOfRange = IndexOutOfRange(start1, end1);
return IndexOutOfRange(start2, end2) || outOfRange;
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
void FRemapTable::MakeIdentity()
{
int i;
for (i = 0; i < NumEntries; ++i)
{
Remap[i] = i;
}
for (i = 0; i < NumEntries; ++i)
{
Palette[i] = GPalette.BaseColors[i];
}
for (i = 1; i < NumEntries; ++i)
{
Palette[i].a = 255;
}
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
bool FRemapTable::IsIdentity() const
{
for (int j = 0; j < 256; ++j)
{
if (Remap[j] != j)
{
return false;
}
}
return true;
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
bool FRemapTable::AddIndexRange(int start, int end, int pal1, int pal2)
{
if (IndexOutOfRange(start, end, pal1, pal2))
{
return false;
}
double palcol, palstep;
if (start > end)
{
std::swap (start, end);
std::swap (pal1, pal2);
}
else if (start == end)
{
start = GPalette.Remap[start];
pal1 = GPalette.Remap[pal1];
Remap[start] = pal1;
Palette[start] = GPalette.BaseColors[pal1];
Palette[start].a = start == 0 ? 0 : 255;
return true;
}
palcol = pal1;
palstep = (pal2 - palcol) / (end - start);
for (int i = start; i <= end; palcol += palstep, ++i)
{
int j = GPalette.Remap[i], k = GPalette.Remap[int(round(palcol))];
Remap[j] = k;
Palette[j] = GPalette.BaseColors[k];
Palette[j].a = j == 0 ? 0 : 255;
}
return true;
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
bool FRemapTable::AddColorRange(int start, int end, int _r1,int _g1, int _b1, int _r2, int _g2, int _b2)
{
if (IndexOutOfRange(start, end))
{
return false;
}
double r1 = _r1;
double g1 = _g1;
double b1 = _b1;
double r2 = _r2;
double g2 = _g2;
double b2 = _b2;
double r, g, b;
double rs, gs, bs;
if (start > end)
{
std::swap (start, end);
r = r2;
g = g2;
b = b2;
rs = r1 - r2;
gs = g1 - g2;
bs = b1 - b2;
}
else
{
r = r1;
g = g1;
b = b1;
rs = r2 - r1;
gs = g2 - g1;
bs = b2 - b1;
}
if (start == end)
{
start = GPalette.Remap[start];
Palette[start] = PalEntry(start == 0 ? 0 : 255, int(r), int(g), int(b));
Remap[start] = ColorMatcher.Pick(Palette[start]);
}
else
{
rs /= (end - start);
gs /= (end - start);
bs /= (end - start);
for (int i = start; i <= end; ++i)
{
int j = GPalette.Remap[i];
Palette[j] = PalEntry(j == 0 ? 0 : 255, int(r), int(g), int(b));
Remap[j] = ColorMatcher.Pick(Palette[j]);
r += rs;
g += gs;
b += bs;
}
}
return true;
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
bool FRemapTable::AddDesaturation(int start, int end, double r1, double g1, double b1, double r2, double g2, double b2)
{
if (IndexOutOfRange(start, end))
{
return false;
}
r1 = clamp(r1, 0.0, 2.0);
g1 = clamp(g1, 0.0, 2.0);
b1 = clamp(b1, 0.0, 2.0);
r2 = clamp(r2, 0.0, 2.0);
g2 = clamp(g2, 0.0, 2.0);
b2 = clamp(b2, 0.0, 2.0);
if (start > end)
{
std::swap(start, end);
std::swap(r1, r2);
std::swap(g1, g2);
std::swap(b1, b2);
}
r2 -= r1;
g2 -= g1;
b2 -= b1;
r1 *= 255;
g1 *= 255;
b1 *= 255;
for(int c = start; c <= end; c++)
{
double intensity = (GPalette.BaseColors[c].r * 77 +
GPalette.BaseColors[c].g * 143 +
GPalette.BaseColors[c].b * 37) / 256.0;
PalEntry pe = PalEntry( MIN(255, int(r1 + intensity*r2)),
MIN(255, int(g1 + intensity*g2)),
MIN(255, int(b1 + intensity*b2)));
int cc = GPalette.Remap[c];
Remap[cc] = ColorMatcher.Pick(pe);
Palette[cc] = pe;
Palette[cc].a = cc == 0 ? 0:255;
}
return true;
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
bool FRemapTable::AddColourisation(int start, int end, int r, int g, int b)
{
if (IndexOutOfRange(start, end))
{
return false;
}
for (int i = start; i < end; ++i)
{
double br = GPalette.BaseColors[i].r;
double bg = GPalette.BaseColors[i].g;
double bb = GPalette.BaseColors[i].b;
double grey = (br * 0.299 + bg * 0.587 + bb * 0.114) / 255.0f;
if (grey > 1.0) grey = 1.0;
br = r * grey;
bg = g * grey;
bb = b * grey;
int j = GPalette.Remap[i];
Palette[j] = PalEntry(j == 0 ? 0 : 255, int(br), int(bg), int(bb));
Remap[j] = ColorMatcher.Pick(Palette[j]);
}
return true;
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
bool FRemapTable::AddTint(int start, int end, int r, int g, int b, int amount)
{
if (IndexOutOfRange(start, end))
{
return false;
}
for (int i = start; i < end; ++i)
{
float br = GPalette.BaseColors[i].r;
float bg = GPalette.BaseColors[i].g;
float bb = GPalette.BaseColors[i].b;
float a = amount * 0.01f;
float ia = 1.0f - a;
br = br * ia + r * a;
bg = bg * ia + g * a;
bb = bb * ia + b * a;
int j = GPalette.Remap[i];
Palette[j] = PalEntry(j == 0 ? 0 : 255, int(br), int(bg), int(bb));
Remap[j] = ColorMatcher.Pick(Palette[j]);
}
return true;
}
//----------------------------------------------------------------------------
//
//
//
//----------------------------------------------------------------------------
bool FRemapTable::AddToTranslation(const char *range)
{
int start,end;
bool desaturated = false;
FScanner sc;
sc.OpenMem("translation", range, int(strlen(range)));
sc.SetCMode(true);
sc.MustGetToken(TK_IntConst);
start = sc.Number;
sc.MustGetToken(':');
sc.MustGetToken(TK_IntConst);
end = sc.Number;
sc.MustGetToken('=');
if (start < 0 || start > 255 || end < 0 || end > 255)
{
sc.ScriptError("Palette index out of range");
return false;
}
sc.MustGetAnyToken();
if (sc.TokenType == '[')
{
// translation using RGB values
int r1,g1,b1,r2,g2,b2;
sc.MustGetToken(TK_IntConst);
r1 = sc.Number;
sc.MustGetToken(',');
sc.MustGetToken(TK_IntConst);
g1 = sc.Number;
sc.MustGetToken(',');
sc.MustGetToken(TK_IntConst);
b1 = sc.Number;
sc.MustGetToken(']');
sc.MustGetToken(':');
sc.MustGetToken('[');
sc.MustGetToken(TK_IntConst);
r2 = sc.Number;
sc.MustGetToken(',');
sc.MustGetToken(TK_IntConst);
g2 = sc.Number;
sc.MustGetToken(',');
sc.MustGetToken(TK_IntConst);
b2 = sc.Number;
sc.MustGetToken(']');
return AddColorRange(start, end, r1, g1, b1, r2, g2, b2);
}
else if (sc.TokenType == '%')
{
// translation using RGB values
double r1,g1,b1,r2,g2,b2;
sc.MustGetToken('[');
sc.MustGetAnyToken();
if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst);
r1 = sc.Float;
sc.MustGetToken(',');
sc.MustGetAnyToken();
if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst);
g1 = sc.Float;
sc.MustGetToken(',');
sc.MustGetAnyToken();
if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst);
b1 = sc.Float;
sc.MustGetToken(']');
sc.MustGetToken(':');
sc.MustGetToken('[');
sc.MustGetAnyToken();
if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst);
r2 = sc.Float;
sc.MustGetToken(',');
sc.MustGetAnyToken();
if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst);
g2 = sc.Float;
sc.MustGetToken(',');
sc.MustGetAnyToken();
if (sc.TokenType != TK_IntConst) sc.TokenMustBe(TK_FloatConst);
b2 = sc.Float;
sc.MustGetToken(']');
return AddDesaturation(start, end, r1, g1, b1, r2, g2, b2);
}
else if (sc.TokenType == '#')
{
// Colourise translation
int r, g, b;
sc.MustGetToken('[');
sc.MustGetToken(TK_IntConst);
r = sc.Number;
sc.MustGetToken(',');
sc.MustGetToken(TK_IntConst);
g = sc.Number;
sc.MustGetToken(',');
sc.MustGetToken(TK_IntConst);
b = sc.Number;
sc.MustGetToken(']');
return AddColourisation(start, end, r, g, b);
}
else if (sc.TokenType == '@')
{
// Tint translation
int a, r, g, b;
sc.MustGetToken(TK_IntConst);
a = sc.Number;
sc.MustGetToken('[');
sc.MustGetToken(TK_IntConst);
r = sc.Number;
sc.MustGetToken(',');
sc.MustGetToken(TK_IntConst);
g = sc.Number;
sc.MustGetToken(',');
sc.MustGetToken(TK_IntConst);
b = sc.Number;
sc.MustGetToken(']');
return AddTint(start, end, r, g, b, a);
}
else
{
int pal1, pal2;
sc.TokenMustBe(TK_IntConst);
pal1 = sc.Number;
sc.MustGetToken(':');
sc.MustGetToken(TK_IntConst);
pal2 = sc.Number;
return AddIndexRange(start, end, pal1, pal2);
}
}
//----------------------------------------------------------------------------
//
// Adds raw colors to a given translation
//
//----------------------------------------------------------------------------
bool FRemapTable::AddColors(int start, int count, const uint8_t*colors)
{
int end = start + count;
if (IndexOutOfRange(start, end))
{
return false;
}
for (int i = start; i < end; ++i)
{
auto br = colors[0];
auto bg = colors[1];
auto bb = colors[2];
colors += 3;
int j = GPalette.Remap[i];
Palette[j] = PalEntry(j == 0 ? 0 : 255, br, bg, bb);
Remap[j] = ColorMatcher.Pick(Palette[j]);
}
return true;
}

View file

@ -0,0 +1,106 @@
#pragma once
#include <stdint.h>
#include "memarena.h"
#include "palentry.h"
struct FRemapTable
{
FRemapTable(int count = 256) { NumEntries = count; }
FRemapTable(const FRemapTable& o) = default;
bool operator==(const FRemapTable& o);
void MakeIdentity();
bool IsIdentity() const;
bool AddIndexRange(int start, int end, int pal1, int pal2);
bool AddColorRange(int start, int end, int r1, int g1, int b1, int r2, int g2, int b2);
bool AddDesaturation(int start, int end, double r1, double g1, double b1, double r2, double g2, double b2);
bool AddColourisation(int start, int end, int r, int g, int b);
bool AddTint(int start, int end, int r, int g, int b, int amount);
bool AddToTranslation(const char* range);
bool AddColors(int start, int count, const uint8_t*);
uint8_t Remap[256]; // For the software renderer
PalEntry Palette[256]; // The ideal palette this maps to
int crc32;
int Index;
int NumEntries; // # of elements in this table (usually 256)
bool Inactive = false; // This table is inactive and should be treated as if it was passed as NULL
private:
};
// A class that initializes unusued pointers to NULL. This is used so that when
// the TAutoGrowArray below is expanded, the new elements will be NULLed.
class FRemapTablePtr
{
public:
FRemapTablePtr() throw() : Ptr(0) {}
FRemapTablePtr(FRemapTable* p) throw() : Ptr(p) {}
FRemapTablePtr(const FRemapTablePtr& p) throw() : Ptr(p.Ptr) {}
operator FRemapTable* () const throw() { return Ptr; }
FRemapTablePtr& operator= (FRemapTable* p) throw() { Ptr = p; return *this; }
FRemapTablePtr& operator= (FRemapTablePtr& p) throw() { Ptr = p.Ptr; return *this; }
FRemapTable& operator*() const throw() { return *Ptr; }
FRemapTable* operator->() const throw() { return Ptr; }
private:
FRemapTable* Ptr = nullptr;
};
#define TRANSLATION_SHIFT 16
#define TRANSLATION_MASK ((1<<TRANSLATION_SHIFT)-1)
#define TRANSLATIONTYPE_MASK (255<<TRANSLATION_SHIFT)
inline uint32_t TRANSLATION(uint8_t a, uint32_t b)
{
return (a << TRANSLATION_SHIFT) | b;
}
inline int GetTranslationType(uint32_t trans)
{
return (trans & TRANSLATIONTYPE_MASK) >> TRANSLATION_SHIFT;
}
inline int GetTranslationIndex(uint32_t trans)
{
return (trans & TRANSLATION_MASK);
}
class PaletteContainer
{
FMemArena remapArena;
TArray<FRemapTable*> uniqueRemaps;
TArray<TAutoGrowArray<FRemapTablePtr, FRemapTable*>> TranslationTables;
public:
void Init(int numslots); // This cannot be a constructor!!!
void Clear();
FRemapTable* AddRemap(FRemapTable* remap);
void UpdateTranslation(int trans, FRemapTable* remap);
int AddTranslation(int slot, FRemapTable* remap, int count = 1);
void CopyTranslation(int dest, int src);
int StoreTranslation(int slot, FRemapTable* remap);
FRemapTable* TranslationToTable(int translation);
void PushIdentityTable(int slot)
{
AddTranslation(slot, nullptr);
}
FRemapTable* GetTranslation(int slot, int index)
{
return TranslationTables[slot].GetVal(index);
}
void ClearTranslationSlot(int slot)
{
TranslationTables[slot].Clear();
}
unsigned NumTranslations(int slot) const
{
return TranslationTables[slot].Size();
}
};
extern PaletteContainer palMgr;

View file

@ -39,6 +39,12 @@ extern "C" int myvsnprintf(char* buffer, size_t count, const char* format, va_li
#define TEXTCOLOR_SAPPHIRE "\034Y"
#define TEXTCOLOR_TEAL "\034Z"
#define TEXTCOLOR_NORMAL "\034-"
#define TEXTCOLOR_BOLD "\034+"
#define TEXTCOLOR_CHAT "\034*"
#define TEXTCOLOR_TEAMCHAT "\034!"
// game print flags
enum
{

View file

@ -33,12 +33,11 @@
// HEADER FILES ------------------------------------------------------------
#include <string.h>
#include <stdlib.h>
#include "engineerrors.h"
#include "sc_man.h"
#include "cmdlib.h"
#include "templates.h"
@ -68,6 +67,31 @@
// CODE --------------------------------------------------------------------
void VersionInfo::operator=(const char *string)
{
char *endp;
major = (int16_t)clamp<unsigned long long>(strtoull(string, &endp, 10), 0, USHRT_MAX);
if (*endp == '.')
{
minor = (int16_t)clamp<unsigned long long>(strtoull(endp + 1, &endp, 10), 0, USHRT_MAX);
if (*endp == '.')
{
revision = (int16_t)clamp<unsigned long long>(strtoull(endp + 1, &endp, 10), 0, USHRT_MAX);
if (*endp != 0) major = USHRT_MAX;
}
else if (*endp == 0)
{
revision = 0;
}
else major = USHRT_MAX;
}
else if (*endp == 0)
{
minor = revision = 0;
}
else major = USHRT_MAX;
}
//==========================================================================
//
// FScanner Constructor
@ -102,6 +126,18 @@ FScanner::FScanner(const FScanner &other)
*this = other;
}
//==========================================================================
//
// FScanner OpenLumpNum Constructor
//
//==========================================================================
FScanner::FScanner(int lumpnum)
{
ScriptOpen = false;
OpenLumpNum(lumpnum);
}
//==========================================================================
//
// FScanner :: operator =
@ -155,7 +191,6 @@ FScanner &FScanner::operator=(const FScanner &other)
TokenType = other.TokenType;
Number = other.Number;
Float = other.Float;
//Name = other.Name;
Line = other.Line;
End = other.End;
Crossed = other.Crossed;
@ -171,37 +206,12 @@ FScanner &FScanner::operator=(const FScanner &other)
void FScanner::Open (const char *name)
{
auto fr = fileSystem.OpenFileReader(name);
if (!fr.isOpen())
int lump = fileSystem.CheckNumForFullName(name, true);
if (lump == -1)
{
I_Error("Could not find script lump '%s'\n", name);
}
Close();
auto data = fr.ReadPadded(1);
ScriptBuffer = data;
ScriptName = name;
//LumpNum = lump;
PrepareScript();
}
//==========================================================================
//
// FScanner :: Open
//
//==========================================================================
FScanner::FScanner(int lump)
{
if ((unsigned)lump >= fileSystem.GetNumEntries())
{
I_Error("Invalid file index %d\n", lump);
}
Close();
auto data = fileSystem.GetFileData(lump, 1);
ScriptBuffer = data;
ScriptName = fileSystem.GetFileFullName(lump);
LumpNum = lump;
PrepareScript();
OpenLumpNum(lump);
}
//==========================================================================
@ -212,16 +222,21 @@ FScanner::FScanner(int lump)
//
//==========================================================================
void FScanner::OpenFile (const char *name)
bool FScanner::OpenFile (const char *name)
{
Close ();
FileReader fr;
if (!fr.OpenFile(name)) return;
auto data = fr.ReadPadded(1);
ScriptBuffer = data;
if (!fr.OpenFile(name)) return false;
auto filesize = fr.GetLength();
auto filebuff = fr.Read();
if (filebuff.Size() == 0 && filesize > 0) return false;
ScriptBuffer = FString((const char *)filebuff.Data(), filesize);
ScriptName = name; // This is used for error messages so the full file name is preferable
LumpNum = -1;
PrepareScript ();
return true;
}
//==========================================================================
@ -255,6 +270,26 @@ void FScanner::OpenString (const char *name, FString buffer)
PrepareScript ();
}
//==========================================================================
//
// FScanner :: OpenLumpNum
//
// Loads a script from the lump directory
//
//==========================================================================
void FScanner :: OpenLumpNum (int lump)
{
Close ();
{
FileData mem = fileSystem.ReadFile(lump);
ScriptBuffer = mem.GetString();
}
ScriptName = fileSystem.GetFileFullPath(lump);
LumpNum = lump;
PrepareScript ();
}
//==========================================================================
//
// FScanner :: PrepareScript
@ -1084,7 +1119,7 @@ void FScanner::CheckOpen()
{
if (ScriptOpen == false)
{
I_Error ("SC_ call before SC_Open().");
I_FatalError ("SC_ call before SC_Open().");
}
}
@ -1095,13 +1130,14 @@ void FScanner::CheckOpen()
//==========================================================================
int FScriptPosition::ErrorCounter;
int FScriptPosition::WarnCounter;
int FScriptPosition::Developer;
bool FScriptPosition::StrictErrors; // makes all OPTERROR messages real errors.
bool FScriptPosition::errorout; // call I_Error instead of printing the error itself.
FScriptPosition::FScriptPosition(FString fname, int line)
{
FileName = fname.GetChars();
FileName = fname;
ScriptLine = line;
}
@ -1128,15 +1164,13 @@ void FScriptPosition::Message (int severity, const char *message, ...) const
{
FString composed;
#if 0
if (severity == MSG_DEBUGLOG && developer < DMSG_NOTIFY) return;
if (severity == MSG_DEBUGERROR && developer < DMSG_ERROR) return;
if (severity == MSG_DEBUGWARN && developer < DMSG_WARNING) return;
if (severity == MSG_DEBUGMSG && developer < DMSG_NOTIFY) return;
#endif
if (severity == MSG_DEBUGLOG && Developer < DMSG_NOTIFY) return;
if (severity == MSG_DEBUGERROR && Developer < DMSG_ERROR) return;
if (severity == MSG_DEBUGWARN && Developer < DMSG_WARNING) return;
if (severity == MSG_DEBUGMSG && Developer < DMSG_NOTIFY) return;
if (severity == MSG_OPTERROR)
{
severity = StrictErrors ? MSG_ERROR : MSG_WARNING;
severity = StrictErrors? MSG_ERROR : MSG_WARNING;
}
// This is mainly for catching the error with an exception handler.
if (severity == MSG_ERROR && errorout) severity = MSG_FATAL;

View file

@ -5,6 +5,38 @@
#include "name.h"
#include "basics.h"
struct VersionInfo
{
uint16_t major;
uint16_t minor;
uint32_t revision;
bool operator <=(const VersionInfo& o) const
{
return o.major > this->major || (o.major == this->major && o.minor > this->minor) || (o.major == this->major && o.minor == this->minor && o.revision >= this->revision);
}
bool operator >=(const VersionInfo& o) const
{
return o.major < this->major || (o.major == this->major && o.minor < this->minor) || (o.major == this->major && o.minor == this->minor && o.revision <= this->revision);
}
bool operator > (const VersionInfo& o) const
{
return o.major < this->major || (o.major == this->major && o.minor < this->minor) || (o.major == this->major && o.minor == this->minor && o.revision < this->revision);
}
bool operator < (const VersionInfo& o) const
{
return o.major > this->major || (o.major == this->major && o.minor > this->minor) || (o.major == this->major && o.minor == this->minor && o.revision > this->revision);
}
void operator=(const char* string);
};
// Cannot be a constructor because Lemon would puke on it.
inline VersionInfo MakeVersion(unsigned int ma, unsigned int mi, unsigned int re = 0)
{
return{ (uint16_t)ma, (uint16_t)mi, (uint32_t)re };
}
class FScanner
{
public:
@ -23,10 +55,19 @@ public:
FScanner &operator=(const FScanner &other);
void Open(const char *lumpname);
void OpenFile(const char *filename);
bool OpenFile(const char *filename);
void OpenMem(const char *name, const char *buffer, int size);
void OpenMem(const char *name, const TArray<uint8_t> &buffer)
{
OpenMem(name, (const char*)buffer.Data(), buffer.Size());
}
void OpenString(const char *name, FString buffer);
void OpenLumpNum(int lump);
void Close();
void SetParseVersion(VersionInfo ver)
{
ParseVersion = ver;
}
void SetCMode(bool cmode);
void SetEscape(bool esc);
@ -111,6 +152,7 @@ protected:
uint8_t StateMode;
bool StateOptions;
bool Escape;
VersionInfo ParseVersion = { 0, 0, 0 }; // no ZScript extensions by default
bool ScanValue(bool allowfloat);
@ -156,6 +198,7 @@ struct FScriptPosition
static int WarnCounter;
static int ErrorCounter;
static bool StrictErrors;
static int Developer;
static bool errorout;
FName FileName;
int ScriptLine;

View file

@ -120,7 +120,109 @@ std2:
("#region"|"#endregion") (any\"\n")* "\n"
{ goto newline; } /* Region blocks [mxd] */
/* C Keywords */
'break' { RET(TK_Break); }
'case' { RET(TK_Case); }
'const' { RET(TK_Const); }
'continue' { RET(TK_Continue); }
'default' { RET(TK_Default); }
'do' { RET(TK_Do); }
'else' { RET(TK_Else); }
'for' { RET(TK_For); }
'goto' { RET(TK_Goto); }
'if' { RET(TK_If); }
'return' { RET(TK_Return); }
'switch' { RET(TK_Switch); }
'until' { RET(TK_Until); }
'volatile' { RET(TK_Volatile); }
'while' { RET(TK_While); }
/* Type names */
'bool' { RET(TK_Bool); }
'float' { RET(TK_Float); }
'double' { RET(TK_Double); }
'char' { RET(TK_Char); }
'byte' { RET(TK_Byte); }
'sbyte' { RET(TK_SByte); }
'short' { RET(TK_Short); }
'ushort' { RET(TK_UShort); }
'int8' { RET(TK_Int8); }
'uint8' { RET(TK_UInt8); }
'int16' { RET(TK_Int16); }
'uint16' { RET(TK_UInt16); }
'int' { RET(TK_Int); }
'uint' { RET(TK_UInt); }
'long' { RET(TK_Long); }
'ulong' { RET(TK_ULong); }
'void' { RET(TK_Void); }
'struct' { RET(TK_Struct); }
'class' { RET(TK_Class); }
'mixin' { RET(TK_Mixin); }
'enum' { RET(TK_Enum); }
'name' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Name : TK_Identifier); }
'string' { RET(TK_String); }
'sound' { RET(TK_Sound); }
'state' { RET(TK_State); }
'color' { RET(TK_Color); }
'vector2' { RET(TK_Vector2); }
'vector3' { RET(TK_Vector3); }
'map' { RET(TK_Map); }
'array' { RET(TK_Array); }
'in' { RET(TK_In); }
'sizeof' { RET(TK_SizeOf); }
'alignof' { RET(TK_AlignOf); }
/* Other keywords from UnrealScript */
'abstract' { RET(TK_Abstract); }
'foreach' { RET(TK_ForEach); }
'true' { RET(TK_True); }
'false' { RET(TK_False); }
'none' { RET(TK_None); }
'auto' { RET(TK_Auto); }
'property' { RET(TK_Property); }
'flagdef' { RET(ParseVersion >= MakeVersion(3, 7, 0)? TK_FlagDef : TK_Identifier); }
'native' { RET(TK_Native); }
'var' { RET(TK_Var); }
'out' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Out : TK_Identifier); }
'static' { RET(TK_Static); }
'transient' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Transient : TK_Identifier); }
'final' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Final : TK_Identifier); }
'extend' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Extend : TK_Identifier); }
'protected' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Protected : TK_Identifier); }
'private' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Private : TK_Identifier); }
'dot' { RET(TK_Dot); }
'cross' { RET(TK_Cross); }
'virtual' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Virtual : TK_Identifier); }
'override' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Override : TK_Identifier); }
'vararg' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_VarArg : TK_Identifier); }
'ui' { RET(ParseVersion >= MakeVersion(2, 4, 0)? TK_UI : TK_Identifier); }
'play' { RET(ParseVersion >= MakeVersion(2, 4, 0)? TK_Play : TK_Identifier); }
'clearscope' { RET(ParseVersion >= MakeVersion(2, 4, 0)? TK_ClearScope : TK_Identifier); }
'virtualscope' { RET(ParseVersion >= MakeVersion(2, 4, 0)? TK_VirtualScope : TK_Identifier); }
'super' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Super : TK_Identifier); }
'stop' { RET(TK_Stop); }
'null' { RET(TK_Null); }
'is' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Is : TK_Identifier); }
'replaces' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Replaces : TK_Identifier); }
'states' { RET(TK_States); }
'meta' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Meta : TK_Identifier); }
'deprecated' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Deprecated : TK_Identifier); }
'version' { RET(ParseVersion >= MakeVersion(2, 4, 0)? TK_Version : TK_Identifier); }
'action' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Action : TK_Identifier); }
'readonly' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_ReadOnly : TK_Identifier); }
'internal' { RET(ParseVersion >= MakeVersion(3, 4, 0)? TK_Internal : TK_Identifier); }
'let' { RET(ParseVersion >= MakeVersion(1, 0, 0)? TK_Let : TK_Identifier); }
/* Actor state options */
'bright' { RET(StateOptions ? TK_Bright : TK_Identifier); }
'fast' { RET(StateOptions ? TK_Fast : TK_Identifier); }
'slow' { RET(StateOptions ? TK_Slow : TK_Identifier); }
'nodelay' { RET(StateOptions ? TK_NoDelay : TK_Identifier); }
'canraise' { RET(StateOptions ? TK_CanRaise : TK_Identifier); }
'offset' { RET(StateOptions ? TK_Offset : TK_Identifier); }
'light' { RET(StateOptions ? TK_Light : TK_Identifier); }
/* other DECORATE top level keywords */
'#include' { RET(TK_Include); }
@ -167,8 +269,8 @@ std2:
"**" { RET(TK_MulMul); }
"::" { RET(TK_ColonColon); }
"->" { RET(TK_Arrow); }
";" { RET(';'); }
"{" { RET('{'); }
";" { StateOptions = false; RET(';'); }
"{" { StateOptions = false; RET('{'); }
"}" { RET('}'); }
"," { RET(','); }
":" { RET(':'); }

View file

@ -0,0 +1,499 @@
/*
** bitmap.cpp
**
**---------------------------------------------------------------------------
** Copyright 2008 Christoph Oelckers
** All rights reserved.
**
** Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions
** are met:
**
** 1. Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** 2. Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in the
** documentation and/or other materials provided with the distribution.
** 3. The name of the author may not be used to endorse or promote products
** derived from this software without specific prior written permission.
**
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
**---------------------------------------------------------------------------
**
**
*/
#include "bitmap.h"
//#include "colormaps.h" // todo: Move the special colormaps out of the game specicic code
uint8_t IcePalette[16][3] =
{
{ 10, 8, 18 },
{ 15, 15, 26 },
{ 20, 16, 36 },
{ 30, 26, 46 },
{ 40, 36, 57 },
{ 50, 46, 67 },
{ 59, 57, 78 },
{ 69, 67, 88 },
{ 79, 77, 99 },
{ 89, 87,109 },
{ 99, 97,120 },
{ 109,107,130 },
{ 118,118,141 },
{ 128,128,151 },
{ 138,138,162 },
{ 148,148,172 }
};
//===========================================================================
//
// multi-format pixel copy with colormap application
// requires the previously defined conversion classes to work
//
//===========================================================================
template<class TSrc, class TDest, class TBlend>
void iCopyColors(uint8_t *pout, const uint8_t *pin, int count, int step, FCopyInfo *inf,
uint8_t tr, uint8_t tg, uint8_t tb)
{
int i;
int fac;
uint8_t r,g,b;
int gray;
int a;
switch(inf? inf->blend : BLEND_NONE)
{
case BLEND_NONE:
for(i=0;i<count;i++)
{
a = TSrc::A(pin, tr, tg, tb);
if (TBlend::ProcessAlpha0() || a)
{
TBlend::OpC(pout[TDest::RED], TSrc::R(pin), a, inf);
TBlend::OpC(pout[TDest::GREEN], TSrc::G(pin), a, inf);
TBlend::OpC(pout[TDest::BLUE], TSrc::B(pin), a, inf);
TBlend::OpA(pout[TDest::ALPHA], a, inf);
}
pout+=4;
pin+=step;
}
break;
case BLEND_ICEMAP:
// Create the ice translation table, based on Hexen's.
// Since this is done in True Color the purplish tint is fully preserved - even in Doom!
for(i=0;i<count;i++)
{
a = TSrc::A(pin, tr, tg, tb);
if (TBlend::ProcessAlpha0() || a)
{
int gray = TSrc::Gray(pin)>>4;
TBlend::OpC(pout[TDest::RED], IcePalette[gray][0], a, inf);
TBlend::OpC(pout[TDest::GREEN], IcePalette[gray][1], a, inf);
TBlend::OpC(pout[TDest::BLUE], IcePalette[gray][2], a, inf);
TBlend::OpA(pout[TDest::ALPHA], a, inf);
}
pout+=4;
pin+=step;
}
break;
default:
if (inf->blend >= BLEND_SPECIALCOLORMAP1)
{
#if 0
FSpecialColormap *cm = &SpecialColormaps[inf->blend - BLEND_SPECIALCOLORMAP1];
for(i=0;i<count;i++)
{
a = TSrc::A(pin, tr, tg, tb);
if (TBlend::ProcessAlpha0() || a)
{
gray = clamp<int>(TSrc::Gray(pin),0,255);
PalEntry pe = cm->GrayscaleToColor[gray];
TBlend::OpC(pout[TDest::RED], pe.r , a, inf);
TBlend::OpC(pout[TDest::GREEN], pe.g, a, inf);
TBlend::OpC(pout[TDest::BLUE], pe.b, a, inf);
TBlend::OpA(pout[TDest::ALPHA], a, inf);
}
pout+=4;
pin+=step;
}
#endif
}
else if (inf->blend >= BLEND_DESATURATE1 && inf->blend<=BLEND_DESATURATE31)
{
// Desaturated light settings.
fac=inf->blend-BLEND_DESATURATE1+1;
for(i=0;i<count;i++)
{
a = TSrc::A(pin, tr, tg, tb);
if (TBlend::ProcessAlpha0() || a)
{
gray = TSrc::Gray(pin);
r = (TSrc::R(pin)*(31-fac) + gray*fac)/31;
g = (TSrc::G(pin)*(31-fac) + gray*fac)/31;
b = (TSrc::B(pin)*(31-fac) + gray*fac)/31;
TBlend::OpC(pout[TDest::RED], r, a, inf);
TBlend::OpC(pout[TDest::GREEN], g, a, inf);
TBlend::OpC(pout[TDest::BLUE], b, a, inf);
TBlend::OpA(pout[TDest::ALPHA], a, inf);
}
pout+=4;
pin+=step;
}
}
break;
case BLEND_MODULATE:
for(i=0;i<count;i++)
{
a = TSrc::A(pin, tr, tg, tb);
if (TBlend::ProcessAlpha0() || a)
{
r = (TSrc::R(pin)*inf->blendcolor[0])>>BLENDBITS;
g = (TSrc::G(pin)*inf->blendcolor[1])>>BLENDBITS;
b = (TSrc::B(pin)*inf->blendcolor[2])>>BLENDBITS;
TBlend::OpC(pout[TDest::RED], r, a, inf);
TBlend::OpC(pout[TDest::GREEN], g, a, inf);
TBlend::OpC(pout[TDest::BLUE], b, a, inf);
TBlend::OpA(pout[TDest::ALPHA], a, inf);
}
pout+=4;
pin+=step;
}
break;
case BLEND_OVERLAY:
for(i=0;i<count;i++)
{
// color blend
a = TSrc::A(pin, tr, tg, tb);
if (TBlend::ProcessAlpha0() || a)
{
r = (TSrc::R(pin)*inf->blendcolor[3] + inf->blendcolor[0]) >> BLENDBITS;
g = (TSrc::G(pin)*inf->blendcolor[3] + inf->blendcolor[1]) >> BLENDBITS;
b = (TSrc::B(pin)*inf->blendcolor[3] + inf->blendcolor[2]) >> BLENDBITS;
TBlend::OpC(pout[TDest::RED], r, a, inf);
TBlend::OpC(pout[TDest::GREEN], g, a, inf);
TBlend::OpC(pout[TDest::BLUE], b, a, inf);
TBlend::OpA(pout[TDest::ALPHA], a, inf);
}
pout+=4;
pin+=step;
}
break;
}
}
typedef void (*CopyFunc)(uint8_t *pout, const uint8_t *pin, int count, int step, FCopyInfo *inf, uint8_t r, uint8_t g, uint8_t b);
#define COPY_FUNCS(op) \
{ \
iCopyColors<cRGB, cBGRA, op>, \
iCopyColors<cRGBT, cBGRA, op>, \
iCopyColors<cRGBA, cBGRA, op>, \
iCopyColors<cIA, cBGRA, op>, \
iCopyColors<cCMYK, cBGRA, op>, \
iCopyColors<cYCbCr, cBGRA, op>, \
iCopyColors<cBGR, cBGRA, op>, \
iCopyColors<cBGRA, cBGRA, op>, \
iCopyColors<cI16, cBGRA, op>, \
iCopyColors<cRGB555, cBGRA, op>, \
iCopyColors<cPalEntry, cBGRA, op> \
}
static const CopyFunc copyfuncs[][11]={
COPY_FUNCS(bCopy),
COPY_FUNCS(bBlend),
COPY_FUNCS(bAdd),
COPY_FUNCS(bSubtract),
COPY_FUNCS(bReverseSubtract),
COPY_FUNCS(bModulate),
COPY_FUNCS(bCopyAlpha),
COPY_FUNCS(bCopyNewAlpha),
COPY_FUNCS(bOverlay),
COPY_FUNCS(bOverwrite)
};
#undef COPY_FUNCS
//===========================================================================
//
// Clips the copy area for CopyPixelData functions
//
//===========================================================================
bool ClipCopyPixelRect(const FClipRect *cr, int &originx, int &originy,
const uint8_t *&patch, int &srcwidth, int &srcheight,
int &pstep_x, int &pstep_y, int rotate)
{
int pixxoffset;
int pixyoffset;
int step_x;
int step_y;
assert(cr != NULL);
// First adjust the settings for the intended rotation
switch (rotate)
{
default:
case 0: // normal
pixxoffset = 0;
pixyoffset = 0;
step_x = pstep_x;
step_y = pstep_y;
break;
case 1: // rotate 90° right
pixxoffset = 0;
pixyoffset = srcheight - 1;
step_x = -pstep_y;
step_y = pstep_x;
break;
case 2: // rotate 180°
pixxoffset = srcwidth - 1;
pixyoffset = srcheight - 1;
step_x = -pstep_x;
step_y = -pstep_y;
break;
case 3: // rotate 90° left
pixxoffset = srcwidth - 1;
pixyoffset = 0;
step_x = pstep_y;
step_y = -pstep_x;
break;
case 4: // flip horizontally
pixxoffset = srcwidth - 1;
pixyoffset = 0;
step_x = -pstep_x;
step_y = pstep_y;
break;
case 5: // flip horizontally and rotate 90° right
pixxoffset = srcwidth - 1;
pixyoffset = srcheight - 1;
step_x = -pstep_y;
step_y = -pstep_x;
break;
case 6: // flip vertically
pixxoffset = 0;
pixyoffset = srcheight - 1;
step_x = pstep_x;
step_y = -pstep_y;
break;
case 7: // flip horizontally and rotate 90° left
pixxoffset = 0;
pixyoffset = 0;
step_x = pstep_y;
step_y = pstep_x;
break;
}
if (rotate&1)
{
int v = srcwidth;
srcwidth = srcheight;
srcheight = v;
}
patch += pixxoffset * pstep_x + pixyoffset * pstep_y;
pstep_x = step_x;
pstep_y = step_y;
// clip source rectangle to destination
if (originx < cr->x)
{
int skip = cr->x - originx;
srcwidth -= skip;
patch +=skip * step_x;
originx = cr->x;
if (srcwidth<=0) return false;
}
if (originx + srcwidth > cr->x + cr->width)
{
srcwidth = cr->x + cr->width - originx;
if (srcwidth<=0) return false;
}
if (originy < cr->y)
{
int skip = cr->y - originy;
srcheight -= skip;
patch += skip*step_y;
originy = cr->y;
if (srcheight <= 0) return false;
}
if (originy + srcheight > cr->y + cr->height)
{
srcheight = cr->y + cr->height - originy;
if (srcheight <= 0) return false;
}
return true;
}
//===========================================================================
//
//
//
//===========================================================================
bool FClipRect::Intersect(int ix, int iy, int iw, int ih)
{
if (ix > x)
{
width -= (ix-x);
x = ix;
}
else
{
iw -= (x-ix);
}
if (iy > y)
{
height -= (iy-y);
y = iy;
}
else
{
ih -= (y-iy);
}
if (iw < width) width = iw;
if (ih < height) height = ih;
return width > 0 && height > 0;
}
//===========================================================================
//
// True Color texture copy function
//
//===========================================================================
void FBitmap::CopyPixelDataRGB(int originx, int originy, const uint8_t *patch, int srcwidth,
int srcheight, int step_x, int step_y, int rotate, int ct, FCopyInfo *inf,
int r, int g, int b)
{
if (ClipCopyPixelRect(&ClipRect, originx, originy, patch, srcwidth, srcheight, step_x, step_y, rotate))
{
uint8_t *buffer = data + 4 * originx + Pitch * originy;
int op = inf==NULL? OP_COPY : inf->op;
for (int y=0;y<srcheight;y++)
{
copyfuncs[op][ct](&buffer[y*Pitch], &patch[y*step_y], srcwidth, step_x, inf, r, g, b);
}
}
}
template<class TDest, class TBlend>
void iCopyPaletted(uint8_t *buffer, const uint8_t * patch, int srcwidth, int srcheight, int Pitch,
int step_x, int step_y, int rotate, const PalEntry * palette, FCopyInfo *inf)
{
int x,y,pos;
for (y=0;y<srcheight;y++)
{
pos = y*Pitch;
for (x=0;x<srcwidth;x++,pos+=4)
{
int v=(unsigned char)patch[y*step_y+x*step_x];
int a = palette[v].a;
if (TBlend::ProcessAlpha0() || a)
{
TBlend::OpC(buffer[pos + TDest::RED], palette[v].r, a, inf);
TBlend::OpC(buffer[pos + TDest::GREEN], palette[v].g, a, inf);
TBlend::OpC(buffer[pos + TDest::BLUE], palette[v].b, a, inf);
TBlend::OpA(buffer[pos + TDest::ALPHA], a, inf);
}
}
}
}
typedef void (*CopyPalettedFunc)(uint8_t *buffer, const uint8_t * patch, int srcwidth, int srcheight, int Pitch,
int step_x, int step_y, int rotate, const PalEntry * palette, FCopyInfo *inf);
static const CopyPalettedFunc copypalettedfuncs[]=
{
iCopyPaletted<cBGRA, bCopy>,
iCopyPaletted<cBGRA, bBlend>,
iCopyPaletted<cBGRA, bAdd>,
iCopyPaletted<cBGRA, bSubtract>,
iCopyPaletted<cBGRA, bReverseSubtract>,
iCopyPaletted<cBGRA, bModulate>,
iCopyPaletted<cBGRA, bCopyAlpha>,
iCopyPaletted<cBGRA, bCopyNewAlpha>,
iCopyPaletted<cBGRA, bOverlay>,
iCopyPaletted<cBGRA, bOverwrite>
};
//===========================================================================
//
// Paletted to True Color texture copy function
//
//===========================================================================
void FBitmap::CopyPixelData(int originx, int originy, const uint8_t * patch, int srcwidth, int srcheight,
int step_x, int step_y, int rotate, const PalEntry * palette, FCopyInfo *inf)
{
if (ClipCopyPixelRect(&ClipRect, originx, originy, patch, srcwidth, srcheight, step_x, step_y, rotate))
{
uint8_t *buffer = data + 4*originx + Pitch*originy;
PalEntry penew[256];
memset(penew, 0, sizeof(penew));
if (inf)
{
if (inf->blend)
{
iCopyColors<cPalEntry, cBGRA, bCopy>((uint8_t*)penew, (const uint8_t*)palette, 256, 4, inf, 0, 0, 0);
palette = penew;
}
else if (inf->palette)
{
palette = inf->palette;
}
}
copypalettedfuncs[inf==NULL? OP_COPY : inf->op](buffer, patch, srcwidth, srcheight, Pitch,
step_x, step_y, rotate, palette, inf);
}
}
//===========================================================================
//
// Clear buffer
//
//===========================================================================
void FBitmap::Zero()
{
uint8_t *buffer = data;
for (int y = ClipRect.y; y < ClipRect.height; ++y)
{
memset(buffer + ClipRect.x, 0, ClipRect.width*4);
buffer += Pitch;
}
}

View file

@ -2,7 +2,7 @@
** bitmap.h
**
**---------------------------------------------------------------------------
** Copyright 2008-2019 Christoph Oelckers
** Copyright 2008 Christoph Oelckers
** All rights reserved.
**
** Redistribution and use in source and binary forms, with or without
@ -36,11 +36,9 @@
#ifndef __BITMAP_H__
#define __BITMAP_H__
#include <algorithm>
#include "palentry.h"
#include <string.h>
#include <stdlib.h>
#include "basics.h"
#include "templates.h"
#include "palentry.h"
struct FCopyInfo;
@ -83,6 +81,7 @@ protected:
int Height;
int Pitch;
bool FreeBuffer;
FClipRect ClipRect;
public:
@ -92,6 +91,7 @@ public:
Width = Height = 0;
Pitch = 0;
FreeBuffer = false;
ClipRect.x = ClipRect.y = ClipRect.width = ClipRect.height = 0;
}
FBitmap(uint8_t *buffer, int pitch, int width, int height)
@ -102,6 +102,9 @@ public:
Width = width;
Height = height;
FreeBuffer = false;
ClipRect.x = ClipRect.y = 0;
ClipRect.width = width;
ClipRect.height = height;
}
FBitmap(const FBitmap &other) = delete; // disallow because in nearly all cases this creates an unwanted copy.
@ -113,6 +116,7 @@ public:
Width = other.Width;
Height = other.Height;
FreeBuffer = other.FreeBuffer;
ClipRect = other.ClipRect;
other.data = nullptr;
other.FreeBuffer = false;
}
@ -127,6 +131,7 @@ public:
Width = other.Width;
Height = other.Height;
FreeBuffer = other.FreeBuffer;
ClipRect = other.ClipRect;
other.data = nullptr;
other.FreeBuffer = false;
return *this;
@ -139,6 +144,7 @@ public:
Width = other.Width;
Height = other.Height;
FreeBuffer = deep;
ClipRect = other.ClipRect;
if (deep)
{
data = new uint8_t[Pitch * Height];
@ -171,6 +177,9 @@ public:
data = new uint8_t[4*w*h];
memset(data, 0, 4*w*h);
FreeBuffer = true;
ClipRect.x = ClipRect.y = 0;
ClipRect.width = w;
ClipRect.height = h;
return data != NULL;
}
@ -199,21 +208,52 @@ public:
return data;
}
void SetClipRect(FClipRect &clip)
{
ClipRect = clip;
}
void IntersectClipRect(FClipRect &clip)
{
ClipRect.Intersect(clip.x, clip.y, clip.width, clip.height);
}
void IntersectClipRect(int cx, int cy, int cw, int ch)
{
ClipRect.Intersect(cx, cy, cw, ch);
}
const FClipRect &GetClipRect() const
{
return ClipRect;
}
void Zero();
void CopyPixelDataRGB(int originx, int originy, const uint8_t *patch, int srcwidth,
int srcheight, int step_x, int step_y, int rotate, int ct,
int srcheight, int step_x, int step_y, int rotate, int ct, FCopyInfo *inf = NULL,
/* for PNG tRNS */ int r=0, int g=0, int b=0);
void CopyPixelData(int originx, int originy, const uint8_t * patch, int srcwidth, int srcheight,
int step_x, int step_y, int rotate, const PalEntry * palette);
int step_x, int step_y, int rotate, const PalEntry * palette, FCopyInfo *inf = NULL);
void Blit(int originx, int originy, const FBitmap &src)
void Blit(int originx, int originy, const FBitmap &src, int width, int height, int rotate = 0, FCopyInfo *inf = NULL)
{
CopyPixelDataRGB(originx, originy, src.GetPixels(), src.GetWidth(), src.GetHeight(), 4, src.GetWidth()*4, 0, CF_BGRA);
CopyPixelDataRGB(originx, originy, src.GetPixels(), width, height, 4, src.GetWidth()*4, rotate, CF_BGRA, inf);
}
void Blit(int originx, int originy, const FBitmap &src, FCopyInfo *inf = NULL)
{
CopyPixelDataRGB(originx, originy, src.GetPixels(), src.GetWidth(), src.GetHeight(), 4, src.GetWidth()*4, 0, CF_BGRA, inf);
}
};
bool ClipCopyPixelRect(const FClipRect *cr, int &originx, int &originy,
const uint8_t *&patch, int &srcwidth, int &srcheight,
int &step_x, int &step_y, int rotate);
//===========================================================================
//
// True color conversion classes for the different pixel formats
@ -349,10 +389,108 @@ struct cPalEntry
static __forceinline int Gray(const unsigned char * p) { return (R(p)*77 + G(p)*143 + B(p)*36)>>8; }
};
enum EBlend
{
BLEND_NONE = 0,
BLEND_ICEMAP = 1,
BLEND_DESATURATE1 = 2,
BLEND_DESATURATE31 = 32,
BLEND_SPECIALCOLORMAP1 = 33,
BLEND_MODULATE = -1,
BLEND_OVERLAY = -2,
};
enum ECopyOp
{
OP_COPY,
OP_BLEND,
OP_ADD,
OP_SUBTRACT,
OP_REVERSESUBTRACT,
OP_MODULATE,
OP_COPYALPHA,
OP_COPYNEWALPHA,
OP_OVERLAY,
OP_OVERWRITE
};
struct FCopyInfo
{
ECopyOp op;
EBlend blend;
blend_t blendcolor[4];
blend_t alpha;
blend_t invalpha;
PalEntry *palette;
};
struct bOverwrite
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = s; }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = s; }
static __forceinline bool ProcessAlpha0() { return true; }
};
struct bCopy
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a) { d = s; }
static __forceinline void OpA(uint8_t &d, uint8_t s) { d = s; }
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = s; }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = s; }
static __forceinline bool ProcessAlpha0() { return false; }
};
struct bCopyNewAlpha
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = s; }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = (s*i->alpha) >> BLENDBITS; }
static __forceinline bool ProcessAlpha0() { return false; }
};
struct bCopyAlpha
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = (s*a + d*(255-a))/255; }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = s; }
static __forceinline bool ProcessAlpha0() { return false; }
};
struct bOverlay
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = (s*a + d*(255-a))/255; }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = MAX(s,d); }
static __forceinline bool ProcessAlpha0() { return false; }
};
struct bBlend
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = (d*i->invalpha + s*i->alpha) >> BLENDBITS; }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = s; }
static __forceinline bool ProcessAlpha0() { return false; }
};
struct bAdd
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = MIN<int>((d*BLENDUNIT + s*i->alpha) >> BLENDBITS, 255); }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = s; }
static __forceinline bool ProcessAlpha0() { return false; }
};
struct bSubtract
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = MAX<int>((d*BLENDUNIT - s*i->alpha) >> BLENDBITS, 0); }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = s; }
static __forceinline bool ProcessAlpha0() { return false; }
};
struct bReverseSubtract
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = MAX<int>((-d*BLENDUNIT + s*i->alpha) >> BLENDBITS, 0); }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = s; }
static __forceinline bool ProcessAlpha0() { return false; }
};
struct bModulate
{
static __forceinline void OpC(uint8_t &d, uint8_t s, uint8_t a, FCopyInfo *i) { d = (s*d)/255; }
static __forceinline void OpA(uint8_t &d, uint8_t s, FCopyInfo *i) { d = s; }
static __forceinline bool ProcessAlpha0() { return false; }
};

View file

@ -53,7 +53,6 @@ void I_DebugPrint(const char *cp)
#endif
#include "engineerrors.h"
#include "printf.h"
//==========================================================================
//
@ -70,7 +69,7 @@ void I_Error(const char *error, ...)
char errortext[MAX_ERRORTEXT];
va_start(argptr, error);
myvsnprintf(errortext, MAX_ERRORTEXT, error, argptr);
vsnprintf(errortext, MAX_ERRORTEXT, error, argptr);
va_end(argptr);
I_DebugPrint(errortext);
@ -97,7 +96,7 @@ void I_FatalError(const char *error, ...)
char errortext[MAX_ERRORTEXT];
va_list argptr;
va_start(argptr, error);
myvsnprintf(errortext, MAX_ERRORTEXT, error, argptr);
vsnprintf(errortext, MAX_ERRORTEXT, error, argptr);
va_end(argptr);
I_DebugPrint(errortext);

View file

@ -44,7 +44,7 @@
#include <malloc.h>
#endif
#include "printf.h"
#include "engineerrors.h"
#include "m_alloc.h"
#ifndef _MSC_VER

View file

@ -39,7 +39,6 @@
#include "basics.h"
#include "memarena.h"
#include "printf.h"
#include "cmdlib.h"
#include "m_alloc.h"

View file

@ -32,9 +32,13 @@
**
*/
#include <algorithm>
#include "palutil.h"
#include "palentry.h"
#include "sc_man.h"
#include "files.h"
#include "filesystem.h"
#include "printf.h"
/****************************/
/* Palette management stuff */
@ -313,3 +317,380 @@ void HSVtoRGB (float *r, float *g, float *b, float h, float s, float v)
}
}
struct RemappingWork
{
uint32_t Color;
uint8_t Foreign; // 0 = local palette, 1 = foreign palette
uint8_t PalEntry; // Entry # in the palette
uint8_t Pad[2];
};
static int sortforremap(const void* a, const void* b)
{
return (*(const uint32_t*)a & 0xFFFFFF) - (*(const uint32_t*)b & 0xFFFFFF);
}
static int sortforremap2(const void* a, const void* b)
{
const RemappingWork* ap = (const RemappingWork*)a;
const RemappingWork* bp = (const RemappingWork*)b;
if (ap->Color == bp->Color)
{
return bp->Foreign - ap->Foreign;
}
else
{
return ap->Color - bp->Color;
}
}
void MakeRemap(uint32_t* BaseColors, const uint32_t* colors, uint8_t* remap, const uint8_t* useful, int numcolors)
{
RemappingWork workspace[255 + 256];
int i, j, k;
// Fill in workspace with the colors from the passed palette and this palette.
// By sorting this array, we can quickly find exact matches so that we can
// minimize the time spent calling BestColor for near matches.
for (i = 1; i < 256; ++i)
{
workspace[i - 1].Color = uint32_t(BaseColors[i]) & 0xFFFFFF;
workspace[i - 1].Foreign = 0;
workspace[i - 1].PalEntry = i;
}
for (i = k = 0, j = 255; i < numcolors; ++i)
{
if (useful == NULL || useful[i] != 0)
{
workspace[j].Color = colors[i] & 0xFFFFFF;
workspace[j].Foreign = 1;
workspace[j].PalEntry = i;
++j;
++k;
}
else
{
remap[i] = 0;
}
}
qsort(workspace, j, sizeof(RemappingWork), sortforremap2);
// Find exact matches
--j;
for (i = 0; i < j; ++i)
{
if (workspace[i].Foreign)
{
if (!workspace[i + 1].Foreign && workspace[i].Color == workspace[i + 1].Color)
{
remap[workspace[i].PalEntry] = workspace[i + 1].PalEntry;
workspace[i].Foreign = 2;
++i;
--k;
}
}
}
// Find near matches
if (k > 0)
{
for (i = 0; i <= j; ++i)
{
if (workspace[i].Foreign == 1)
{
remap[workspace[i].PalEntry] = BestColor((uint32_t*)BaseColors,
RPART(workspace[i].Color), GPART(workspace[i].Color), BPART(workspace[i].Color),
1, 255);
}
}
}
}
// In ZDoom's new texture system, color 0 is used as the transparent color.
// But color 0 is also a valid color for Doom engine graphics. What to do?
// Simple. The default palette for every game has at least one duplicate
// color, so find a duplicate pair of palette entries, make one of them a
// duplicate of color 0, and remap every graphic so that it uses that entry
// instead of entry 0.
void MakeGoodRemap(uint32_t* BaseColors, uint8_t* Remap)
{
for (int i = 0; i < 256; i++) Remap[i] = i;
PalEntry color0 = BaseColors[0];
int i;
// First try for an exact match of color 0. Only Hexen does not have one.
for (i = 1; i < 256; ++i)
{
if (BaseColors[i] == color0)
{
Remap[0] = i;
break;
}
}
// If there is no duplicate of color 0, find the first set of duplicate
// colors and make one of them a duplicate of color 0. In Hexen's PLAYPAL
// colors 209 and 229 are the only duplicates, but we cannot assume
// anything because the player might be using a custom PLAYPAL where those
// entries are not duplicates.
if (Remap[0] == 0)
{
PalEntry sortcopy[256];
for (i = 0; i < 256; ++i)
{
sortcopy[i] = BaseColors[i] | (i << 24);
}
qsort(sortcopy, 256, 4, sortforremap);
for (i = 255; i > 0; --i)
{
if ((sortcopy[i] & 0xFFFFFF) == (sortcopy[i - 1] & 0xFFFFFF))
{
int new0 = sortcopy[i].a;
int dup = sortcopy[i - 1].a;
if (new0 > dup)
{
// Make the lower-numbered entry a copy of color 0. (Just because.)
std::swap(new0, dup);
}
Remap[0] = new0;
Remap[new0] = dup;
BaseColors[new0] = color0;
break;
}
}
}
// If there were no duplicates, InitPalette() will remap color 0 to the
// closest matching color. Hopefully nobody will use a palette where all
// 256 entries are different. :-)
}
//==========================================================================
//
// V_GetColorFromString
//
// Passed a string of the form "#RGB", "#RRGGBB", "R G B", or "RR GG BB",
// returns a number representing that color. If palette is non-NULL, the
// index of the best match in the palette is returned, otherwise the
// RRGGBB value is returned directly.
//
//==========================================================================
int V_GetColorFromString(const uint32_t* palette, const char* cstr, FScriptPosition* sc)
{
int c[3], i, p;
char val[3];
val[2] = '\0';
// Check for HTML-style #RRGGBB or #RGB color string
if (cstr[0] == '#')
{
size_t len = strlen(cstr);
if (len == 7)
{
// Extract each eight-bit component into c[].
for (i = 0; i < 3; ++i)
{
val[0] = cstr[1 + i * 2];
val[1] = cstr[2 + i * 2];
c[i] = ParseHex(val, sc);
}
}
else if (len == 4)
{
// Extract each four-bit component into c[], expanding to eight bits.
for (i = 0; i < 3; ++i)
{
val[1] = val[0] = cstr[1 + i];
c[i] = ParseHex(val, sc);
}
}
else
{
// Bad HTML-style; pretend it's black.
c[2] = c[1] = c[0] = 0;
}
}
else
{
if (strlen(cstr) == 6)
{
char* p;
int color = strtol(cstr, &p, 16);
if (*p == 0)
{
// RRGGBB string
c[0] = (color & 0xff0000) >> 16;
c[1] = (color & 0xff00) >> 8;
c[2] = (color & 0xff);
}
else goto normal;
}
else
{
normal:
// Treat it as a space-delimited hexadecimal string
for (i = 0; i < 3; ++i)
{
// Skip leading whitespace
while (*cstr <= ' ' && *cstr != '\0')
{
cstr++;
}
// Extract a component and convert it to eight-bit
for (p = 0; *cstr > ' '; ++p, ++cstr)
{
if (p < 2)
{
val[p] = *cstr;
}
}
if (p == 0)
{
c[i] = 0;
}
else
{
if (p == 1)
{
val[1] = val[0];
}
c[i] = ParseHex(val, sc);
}
}
}
}
if (palette)
return BestColor(palette, c[0], c[1], c[2]);
else
return MAKERGB(c[0], c[1], c[2]);
}
//==========================================================================
//
// V_GetColorStringByName
//
// Searches for the given color name in x11r6rgb.txt and returns an
// HTML-ish "#RRGGBB" string for it if found or the empty string if not.
//
//==========================================================================
FString V_GetColorStringByName(const char* name, FScriptPosition* sc)
{
FileData rgbNames;
char* rgbEnd;
char* rgb, * endp;
int rgblump;
int c[3], step;
size_t namelen;
if (fileSystem.GetNumEntries() == 0) return FString();
rgblump = fileSystem.CheckNumForName("X11R6RGB");
if (rgblump == -1)
{
if (!sc) Printf("X11R6RGB lump not found\n");
else sc->Message(MSG_WARNING, "X11R6RGB lump not found");
return FString();
}
rgbNames = fileSystem.ReadFile(rgblump);
rgb = (char*)rgbNames.GetMem();
rgbEnd = rgb + fileSystem.FileLength(rgblump);
step = 0;
namelen = strlen(name);
while (rgb < rgbEnd)
{
// Skip white space
if (*rgb <= ' ')
{
do
{
rgb++;
} while (rgb < rgbEnd && *rgb <= ' ');
}
else if (step == 0 && *rgb == '!')
{ // skip comment lines
do
{
rgb++;
} while (rgb < rgbEnd && *rgb != '\n');
}
else if (step < 3)
{ // collect RGB values
c[step++] = strtoul(rgb, &endp, 10);
if (endp == rgb)
{
break;
}
rgb = endp;
}
else
{ // Check color name
endp = rgb;
// Find the end of the line
while (endp < rgbEnd && *endp != '\n')
endp++;
// Back up over any whitespace
while (endp > rgb && *endp <= ' ')
endp--;
if (endp == rgb)
{
break;
}
size_t checklen = ++endp - rgb;
if (checklen == namelen && strnicmp(rgb, name, checklen) == 0)
{
FString descr;
descr.Format("#%02x%02x%02x", c[0], c[1], c[2]);
return descr;
}
rgb = endp;
step = 0;
}
}
if (rgb < rgbEnd)
{
if (!sc) Printf("X11R6RGB lump is corrupt\n");
else sc->Message(MSG_WARNING, "X11R6RGB lump is corrupt");
}
return FString();
}
//==========================================================================
//
// V_GetColor
//
// Works like V_GetColorFromString(), but also understands X11 color names.
//
//==========================================================================
int V_GetColor(const uint32_t* palette, const char* str, FScriptPosition* sc)
{
FString string = V_GetColorStringByName(str, sc);
int res;
if (!string.IsEmpty())
{
res = V_GetColorFromString(palette, string, sc);
}
else
{
res = V_GetColorFromString(palette, str, sc);
}
return res;
}
int V_GetColor(const uint32_t* palette, FScanner& sc)
{
FScriptPosition scc = sc;
return V_GetColor(palette, sc.String, &scc);
}

View file

@ -3,10 +3,29 @@
#include <stdint.h>
#include "palentry.h"
struct FScriptPosition;
class FScanner;
int BestColor(const uint32_t* pal, int r, int g, int b, int first = 1, int num = 255);
int PTM_BestColor(const uint32_t* pal_in, int r, int g, int b, bool reverselookup, float powtable, int first = 1, int num = 255);
void DoBlending(const PalEntry* from, PalEntry* to, int count, int r, int g, int b, int a);
// Given an array of colors, fills in remap with values to remap the
// passed array of colors to BaseColors. Used for loading palette downconversions of PNGs.
void MakeRemap(uint32_t* BaseColors, const uint32_t* colors, uint8_t* remap, const uint8_t* useful, int numcolors);
void MakeGoodRemap(uint32_t* BaseColors, uint8_t* Remap);
// Colorspace conversion RGB <-> HSV
void RGBtoHSV (float r, float g, float b, float *h, float *s, float *v);
void HSVtoRGB (float *r, float *g, float *b, float h, float s, float v);
// Returns the closest color to the one desired. String
// should be of the form "rr gg bb".
int V_GetColorFromString(const uint32_t* palette, const char* colorstring, FScriptPosition* sc = nullptr);
// Scans through the X11R6RGB lump for a matching color
// and returns a color string suitable for V_GetColorFromString.
FString V_GetColorStringByName(const char* name, FScriptPosition* sc = nullptr);
// Tries to get color by name, then by string
int V_GetColor(const uint32_t* palette, const char* str, FScriptPosition* sc = nullptr);
int V_GetColor(const uint32_t* palette, FScanner& sc);

View file

@ -158,7 +158,7 @@ const char *KeyNames[NUM_KEYS] =
FKeyBindings Bindings;
FKeyBindings DoubleBindings;
FKeyBindings AutomapBindings; // this is currently not in use but may be added later.
FKeyBindings AutomapBindings;
static unsigned int DClickTime[NUM_KEYS];
static FixedBitArray<NUM_KEYS> DClicked;
@ -232,7 +232,7 @@ const char *KeyName (int key)
if (KeyNames[key])
return KeyNames[key];
snprintf (name, countof(name), "Key_%d", key);
mysnprintf (name, countof(name), "Key_%d", key);
return name;
}
@ -410,11 +410,11 @@ void FKeyBindings::PerformBind(FCommandLine &argv, const char *msg)
//=============================================================================
//
// This function is first called for functions in custom key sections.
// In this case, matchcmd is non-nullptr, and only keys bound to that command
// In this case, matchcmd is non-null, and only keys bound to that command
// are stored. If a match is found, its binding is set to "\1".
// After all custom key sections are saved, it is called one more for the
// normal Bindings and DoubleBindings sections for this game. In this case
// matchcmd is nullptr and all keys will be stored. The config section was not
// matchcmd is null and all keys will be stored. The config section was not
// previously cleared, so all old bindings are still in place. If the binding
// for a key is empty, the corresponding key in the config is removed as well.
// If a binding is "\1", then the binding itself is cleared, but nothing
@ -458,6 +458,32 @@ void FKeyBindings::ArchiveBindings(FConfigFile *f, const char *matchcmd)
//
//=============================================================================
int FKeyBindings::GetKeysForCommand (const char *cmd, int *first, int *second)
{
int c, i;
*first = *second = c = i = 0;
while (i < NUM_KEYS && c < 2)
{
if (stricmp (cmd, Binds[i]) == 0)
{
if (c++ == 0)
*first = i;
else
*second = i;
}
i++;
}
return c;
}
//=============================================================================
//
//
//
//=============================================================================
TArray<int> FKeyBindings::GetKeysForCommand (const char *cmd)
{
int i = 0;
@ -535,7 +561,7 @@ void C_UnbindAll ()
AutomapBindings.UnbindAll();
}
CCMD (unbindall)
UNSAFE_CCMD (unbindall)
{
C_UnbindAll ();
}
@ -737,21 +763,13 @@ const char* KB_ScanCodeToString(int scancode)
return "";
}
int KB_StringToScanCode(const char* string)
{
for (int i = 0; i < NUM_KEYS; i++)
{
if (KeyNames[i] && !stricmp(string, KeyNames[i])) return i;
}
return 0;
}
void AddCommandString (const char *copy, int keynum);
//=============================================================================
//
//
//
//=============================================================================
bool C_DoKey (event_t *ev, FKeyBindings *binds, FKeyBindings *doublebinds)
{
FString binding;

View file

@ -42,7 +42,6 @@ struct event_t;
class FConfigFile;
class FCommandLine;
const char* KeyName(int key);
void C_NameKeys (char *str, int first, int second);
FString C_NameKeys (int *keys, int count, bool colors = false);
@ -54,6 +53,7 @@ public:
void PerformBind(FCommandLine &argv, const char *msg);
bool DoKey(event_t *ev);
void ArchiveBindings(FConfigFile *F, const char *matchcmd = NULL);
int GetKeysForCommand (const char *cmd, int *first, int *second);
TArray<int> GetKeysForCommand (const char *cmd);
void UnbindACommand (const char *str);
void UnbindAll ();
@ -96,10 +96,6 @@ bool C_DoKey (event_t *ev, FKeyBindings *binds, FKeyBindings *doublebinds);
void C_SetDefaultBindings ();
void C_UnbindAll ();
const char* KB_ScanCodeToString(int scancode); // convert scancode into a string
int KB_StringToScanCode(const char* string); // convert a string into a scancode
extern const char *KeyNames[];
struct FKeyAction
@ -116,13 +112,5 @@ struct FKeySection
};
extern TArray<FKeySection> KeySections;
struct GameFuncDesc
{
const char *action;
const char *description;
bool replaced;
};
#endif //__C_BINDINGS_H__

View file

@ -33,13 +33,13 @@
*/
class FConfigFile;
struct osdfuncparm_t;
struct CCmdFuncParm;
// Class that can parse command lines
class FCommandLine
{
friend int OSD_RegisterFunction(const char* pszName, const char* pszDesc, int (*func)(osdfuncparm_t const* const));
friend int C_RegisterFunction(const char* name, const char* help, int (*func)(CCmdFuncParm const* const));
public:
FCommandLine (const char *commandline, bool no_escapes = false);
~FCommandLine ();

View file

@ -55,6 +55,12 @@
// the new command.
//
//=============================================================================
struct GameFuncDesc
{
const char* action;
const char* description;
bool replaced;
};
static GameFuncDesc con_gamefuncs[] = {
{"+Move_Forward", "Move_Forward"},
@ -122,6 +128,8 @@ static GameFuncDesc con_gamefuncs[] = {
{"+Toggle_Crouch", "Toggle_Crouch"}
};
const char* KB_ScanCodeToString(int scancode); // convert scancode into a string
//=============================================================================
//
//

View file

@ -40,7 +40,7 @@
#include "c_console.h"
#include "c_cvars.h"
#include "c_dispatch.h"
//#include "g_input.h"
#include "gamestate.h"
#include "v_text.h"
#include "filesystem.h"
#include "d_gui.h"
@ -60,18 +60,10 @@
#include "s_soundinternal.h"
#include "engineerrors.h"
#define LEFTMARGIN 8
#define RIGHTMARGIN 8
#define BOTTOMARGIN 12
enum
{
CONTICRATE = 30,
C_BLINKRATE = (CONTICRATE/2),
};
extern bool hud_toggled;
void D_ToggleHud();
@ -107,7 +99,7 @@ int ConWidth;
bool vidactive = false;
bool cursoron = false;
int ConBottom, ConScroll, RowAdjust;
int CursorTicker;
uint64_t CursorTicker;
constate_e ConsoleState = c_up;
@ -517,6 +509,7 @@ static int HistSize;
struct FNotifyText
{
int TimeOut;
int Ticker;
int PrintLevel;
FString Text;
};
@ -545,7 +538,7 @@ CUSTOM_CVAR(Int, con_notifylines, NUMNOTIFIES, CVAR_GLOBALCONFIG | CVAR_ARCHIVE)
}
int PrintColors[PRINTLEVELS+2] = { CR_RED, CR_GOLD, CR_YELLOW, CR_GREEN, CR_GREEN, CR_GOLD };
int PrintColors[PRINTLEVELS+2] = { CR_RED, CR_GOLD, CR_GRAY, CR_GREEN, CR_GREEN, CR_GOLD };
static void setmsgcolor (int index, int color);
@ -639,7 +632,7 @@ void C_InitConsole (int width, int height, bool ingame)
//
//==========================================================================
CCMD (atexit)
UNSAFE_CCMD (atexit)
{
if (argv.argc() == 1)
{
@ -814,7 +807,8 @@ void FNotifyBuffer::AddString(int printlevel, FString source)
FNotifyText newline;
newline.Text = line.Text;
newline.TimeOut = int(con_notifytime * CONTICRATE);
newline.TimeOut = int(con_notifytime * GameTicRate);
newline.Ticker = 0;
newline.PrintLevel = printlevel;
if (AddType == NEWLINE || Text.Size() == 0)
{
@ -1034,12 +1028,6 @@ void C_Ticker()
}
}
if (--CursorTicker <= 0)
{
cursoron ^= 1;
CursorTicker = C_BLINKRATE;
}
lasttic = consoletic;
NotifyStrings.Tick();
if (ConsoleState == c_down)
@ -1063,12 +1051,19 @@ void FNotifyBuffer::Tick()
unsigned i;
for (i = 0; i < Text.Size(); ++i)
{
if (Text[i].TimeOut != 0 && --Text[i].TimeOut <= 0)
Text[i].Ticker++;
}
for (i = 0; i < Text.Size(); ++i)
{
if (Text[i].TimeOut != 0 && Text[i].TimeOut > Text[i].Ticker)
break;
}
if (i < Text.Size())
if (i > 0)
{
Text.Delete(0, i);
FFont* font = generic_ui ? NewSmallFont : AlternativeSmallFont;
Top += font->GetHeight();
}
}
@ -1095,7 +1090,7 @@ void FNotifyBuffer::Draw()
if (notify.TimeOut == 0)
continue;
j = notify.TimeOut;
j = notify.TimeOut - notify.Ticker;
if (j > 0)
{
double alpha = (j < NOTIFYFADETIME) ? 1. * j / NOTIFYFADETIME : 1;
@ -1125,11 +1120,6 @@ void FNotifyBuffer::Draw()
}
else
{
if (canskip)
{
Top += lineadv;
line += lineadv;
}
notify.TimeOut = 0;
}
}
@ -1245,8 +1235,14 @@ void C_DrawConsole ()
if (ConBottom >= 20)
{
//if (gamestate != GS_STARTUP)
if (gamestate != GS_STARTUP)
{
auto now = I_msTime();
if (now > CursorTicker)
{
CursorTicker = now + 500;
cursoron = !cursoron;
}
CmdLine.Draw(left, bottomline, textScale, cursoron);
}
if (RowAdjust && ConBottom >= CurrentConsoleFont->GetHeight()*7/2)
@ -1322,7 +1318,7 @@ void C_ToggleConsole ()
void C_HideConsole ()
{
//if (gamestate != GS_FULLCONSOLE)
if (gamestate != GS_FULLCONSOLE)
{
ConsoleState = c_up;
ConBottom = 0;
@ -1716,7 +1712,7 @@ static bool C_HandleKey (event_t *ev, FCommandBuffer &buffer)
buffer.AppendToYankBuffer = keepappending;
// Ensure that the cursor is always visible while typing
CursorTicker = C_BLINKRATE;
CursorTicker = I_msTime() + 500;
cursoron = 1;
return true;
}
@ -1993,7 +1989,7 @@ static void C_TabComplete (bool goForward)
else
{
CmdLineText.Truncate(TabStart);
CmdLineText << TabCommands[TabPos].TabName.GetChars() << " ";
CmdLineText << TabCommands[TabPos].TabName.GetChars() << ' ';
}
}
CmdLine.SetString(CmdLineText);
@ -2077,39 +2073,3 @@ static bool C_TabCompleteList ()
}
return true;
}
// color code format is as follows:
// ^## sets a color, where ## is the palette number
// ^S# sets a shade, range is 0-7 equiv to shades 0-14
// ^O resets formatting to defaults
const char * OSD_StripColors(char *outBuf, const char *inBuf)
{
const char *ptr = outBuf;
while (*inBuf)
{
if (*inBuf == '^')
{
if (isdigit(*(inBuf+1)))
{
inBuf += 2 + !!isdigit(*(inBuf+2));
continue;
}
else if ((toupper(*(inBuf+1)) == 'O'))
{
inBuf += 2;
continue;
}
else if ((toupper(*(inBuf+1)) == 'S') && isdigit(*(inBuf+2)))
{
inBuf += 3;
continue;
}
}
*(outBuf++) = *(inBuf++);
}
*outBuf = '\0';
return ptr;
}

View file

@ -35,17 +35,14 @@
#include <string.h>
#include <assert.h>
#include "c_cvars.h"
#include "configfile.h"
#include "baselayer.h"
#include "c_console.h"
#include "gamecvars.h"
#include "cmdlib.h"
#include "configfile.h"
#include "c_console.h"
#include "c_dispatch.h"
#include "c_cvars.h"
#include "engineerrors.h"
#include "printf.h"
#include "quotemgr.h"
#include "palutil.h"
struct FLatchedValue
@ -66,6 +63,15 @@ FBaseCVar *CVars = NULL;
int cvar_defflags;
static ConsoleCallbacks* callbacks;
// Install game-specific handlers, mainly to deal with serverinfo and userinfo CVARs.
// This is to keep the console independent of game implementation details for easier reusability.
void C_InstallHandlers(ConsoleCallbacks* cb)
{
callbacks = cb;
}
FBaseCVar::FBaseCVar (const char *var_name, uint32_t flags, void (*callback)(FBaseCVar &), const char *descr)
{
if (var_name != nullptr && (flags & CVAR_SERVERINFO))
@ -74,13 +80,11 @@ FBaseCVar::FBaseCVar (const char *var_name, uint32_t flags, void (*callback)(FBa
// for name's length with terminating null character
static const size_t NAME_LENGHT_MAX = 63;
/*
if (strlen(var_name) > NAME_LENGHT_MAX)
{
I_FatalError("Name of the server console variable \"%s\" is too long.\n"
"Its length should not exceed %zu characters.\n", var_name, NAME_LENGHT_MAX);
}
*/
}
@ -143,22 +147,23 @@ FBaseCVar::~FBaseCVar ()
const char *FBaseCVar::GetHumanString(int precision) const
{
assert(true);
return GetGenericRep(CVAR_String).String;
}
void FBaseCVar::ForceSet (UCVarValue value, ECVarType type, bool nouserinfosend)
{
DoSet (value, type);
if ((Flags & CVAR_USERINFO) && !nouserinfosend && !(Flags & CVAR_IGNORE))
if (callbacks && callbacks->UserInfoChanged) callbacks->UserInfoChanged(this);
if (m_UseCallback)
Callback ();
if ((Flags & CVAR_ARCHIVE))
if ((Flags & CVAR_ARCHIVE) && !(Flags & CVAR_UNSAFECONTEXT))
{
SafeValue = GetGenericRep(CVAR_String).String;
}
Flags &= ~(CVAR_ISDEFAULT);
Flags &= ~(CVAR_ISDEFAULT | CVAR_UNSAFECONTEXT);
}
void FBaseCVar::SetGenericRep (UCVarValue value, ECVarType type)
@ -167,8 +172,7 @@ void FBaseCVar::SetGenericRep (UCVarValue value, ECVarType type)
{
return;
}
#if 0
else if ((Flags & CVAR_LATCH) && gamestate != GS_FULLCONSOLE && gamestate != GS_STARTUP)
else if ((Flags & CVAR_LATCH) && callbacks && callbacks->MustLatch())
{
FLatchedValue latch;
@ -183,17 +187,10 @@ void FBaseCVar::SetGenericRep (UCVarValue value, ECVarType type)
Flags &= ~CVAR_UNSAFECONTEXT;
}
else if ((Flags & CVAR_SERVERINFO) && gamestate != GS_STARTUP && !demoplayback)
else if ((Flags & CVAR_SERVERINFO) && callbacks && callbacks->SendServerInfoChange)
{
if (netgame && !players[consoleplayer].settings_controller)
{
Printf ("Only setting controllers can change %s\n", Name);
Flags &= ~CVAR_UNSAFECONTEXT;
return;
}
D_SendServerInfoChange (this, value, type);
callbacks->SendServerInfoChange (this, value, type);
}
#endif
else
{
ForceSet (value, type);
@ -279,6 +276,7 @@ float FBaseCVar::ToFloat (UCVarValue value, ECVarType type)
}
static char cstrbuf[40];
static GUID cGUID;
static char truestr[] = "true";
static char falsestr[] = "false";
@ -743,11 +741,6 @@ void FStringCVar::DoSet (UCVarValue value, ECVarType type)
//
// Color cvar implementation
//
#if 0
#define APART(c) (((c)>>24)&0xff)
#define RPART(c) (((c)>>16)&0xff)
#define GPART(c) (((c)>>8)&0xff)
#define BPART(c) ((c)&0xff)
FColorCVar::FColorCVar (const char *name, int def, uint32_t flags, void (*callback)(FColorCVar &), const char* descr)
: FIntCVar (name, def, flags, reinterpret_cast<void (*)(FIntCVar &)>(callback), descr)
@ -779,6 +772,11 @@ void FColorCVar::SetGenericRepDefault (UCVarValue value, ECVarType type)
}
}
void FColorCVar::DoSet (UCVarValue value, ECVarType type)
{
Value = ToInt2 (value, type);
}
UCVarValue FColorCVar::FromInt2 (int value, ECVarType type)
{
if (type == CVAR_String)
@ -796,15 +794,15 @@ int FColorCVar::ToInt2 (UCVarValue value, ECVarType type)
{
int ret;
#if 0
if (type == CVAR_String)
{
FString string;
FString string = V_GetColorStringByName(value.String);
// Only allow named colors after the screen exists (i.e. after
// we've got some lumps loaded, so X11R6RGB can be read). Since
// the only time this might be called before that is when loading
// zdoom.ini, this shouldn't be a problem.
if (screen && !(string = V_GetColorStringByName (value.String)).IsEmpty() )
if (string.IsNotEmpty())
{
ret = V_GetColorFromString (NULL, string);
}
@ -814,13 +812,11 @@ int FColorCVar::ToInt2 (UCVarValue value, ECVarType type)
}
}
else
#endif
{
ret = ToInt (value, type);
}
return ret;
}
#endif
//
// More base cvar stuff
@ -855,6 +851,10 @@ void FBaseCVar::ResetToDefault ()
void FBaseCVar::MarkUnsafe()
{
if (!(Flags & CVAR_MOD) && UnsafeExecutionContext)
{
Flags |= CVAR_UNSAFECONTEXT;
}
}
//
@ -940,23 +940,16 @@ void FFlagCVar::DoSet (UCVarValue value, ECVarType type)
{
bool newval = ToBool (value, type);
#if 0
// Server cvars that get changed by this need to use a special message, because
// changes are not processed until the next net update. This is a problem with
// exec scripts because all flags will base their changes off of the value of
// the "master" cvar at the time the script was run, overriding any changes
// another flag might have made to the same cvar earlier in the script.
if ((ValueVar.GetFlags() & CVAR_SERVERINFO) && gamestate != GS_STARTUP && !demoplayback)
if (ValueVar.GetFlags() && callbacks && callbacks->SendServerFlagChange)
{
if (netgame && !players[consoleplayer].settings_controller)
{
Printf ("Only setting controllers can change %s\n", Name);
return;
}
D_SendServerFlagChange (&ValueVar, BitNum, newval);
callbacks->SendServerFlagChange(&ValueVar, BitNum, newval, false);
}
else
#endif
{
int val = *ValueVar;
if (newval)
@ -1044,30 +1037,25 @@ void FMaskCVar::DoSet (UCVarValue value, ECVarType type)
{
int val = ToInt(value, type) << BitNum;
#if 0
// Server cvars that get changed by this need to use a special message, because
// changes are not processed until the next net update. This is a problem with
// exec scripts because all flags will base their changes off of the value of
// the "master" cvar at the time the script was run, overriding any changes
// another flag might have made to the same cvar earlier in the script.
if ((ValueVar.GetFlags() & CVAR_SERVERINFO) && gamestate != GS_STARTUP && !demoplayback)
if (ValueVar.GetFlags() && callbacks && callbacks->SendServerFlagChange)
{
if (netgame && !players[consoleplayer].settings_controller)
{
Printf ("Only setting controllers can change %s\n", Name);
return;
}
// Ugh...
// The network interface needs to process each bit separately.
bool silent = false;
for(int i = 0; i < 32; i++)
{
if (BitVal & (1<<i))
{
D_SendServerFlagChange (&ValueVar, i, !!(val & (1<<i)));
callbacks->SendServerFlagChange (&ValueVar, i, !!(val & (1<<i)), silent);
silent = true; // only warn once if SendServerFlagChange needs to.
}
}
}
else
#endif
{
int vval = *ValueVar;
vval &= ~BitVal;
@ -1088,7 +1076,7 @@ void FilterCompactCVars (TArray<FBaseCVar *> &cvars, uint32_t filter)
// Accumulate all cvars that match the filter flags.
for (FBaseCVar *cvar = CVars; cvar != NULL; cvar = cvar->m_Next)
{
if ((cvar->Flags & filter))
if ((cvar->Flags & filter) && !(cvar->Flags & CVAR_IGNORE))
cvars.Push(cvar);
}
// Now sort them, so they're in a deterministic order and not whatever
@ -1127,7 +1115,7 @@ FString C_GetMassCVarString (uint32_t filter, bool compact)
{
for (cvar = CVars; cvar != NULL; cvar = cvar->m_Next)
{
if ((cvar->Flags & filter) && !(cvar->Flags & (CVAR_NOSAVE)))
if ((cvar->Flags & filter) && !(cvar->Flags & (CVAR_NOSAVE|CVAR_IGNORE)))
{
UCVarValue val = cvar->GetGenericRep(CVAR_String);
dump << '\\' << cvar->GetName() << '\\' << val.String;
@ -1288,6 +1276,24 @@ FBaseCVar *FindCVarSub (const char *var_name, int namelen)
return var;
}
FBaseCVar *GetCVar(int playernum, const char *cvarname)
{
FBaseCVar *cvar = FindCVar(cvarname, nullptr);
// Either the cvar doesn't exist, or it's for a mod that isn't loaded, so return nullptr.
if (cvar == nullptr || (cvar->GetFlags() & CVAR_IGNORE))
{
return nullptr;
}
else
{
// For userinfo cvars, redirect to GetUserCVar
if ((cvar->GetFlags() & CVAR_USERINFO) && callbacks && callbacks->GetUserCVar)
{
return callbacks->GetUserCVar(playernum, cvarname);
}
return cvar;
}
}
//===========================================================================
//
@ -1308,7 +1314,7 @@ FBaseCVar *C_CreateCVar(const char *var_name, ECVarType var_type, uint32_t flags
case CVAR_Int: return new FIntCVar(var_name, 0, flags);
case CVAR_Float: return new FFloatCVar(var_name, 0, flags);
case CVAR_String: return new FStringCVar(var_name, NULL, flags);
//case CVAR_Color: return new FColorCVar(var_name, 0, flags);
case CVAR_Color: return new FColorCVar(var_name, 0, flags);
default: return NULL;
}
}
@ -1319,6 +1325,8 @@ void UnlatchCVars (void)
{
uint32_t oldflags = var.Variable->Flags;
var.Variable->Flags &= ~(CVAR_LATCH | CVAR_SERVERINFO);
if (var.UnsafeContext)
var.Variable->Flags |= CVAR_UNSAFECONTEXT;
var.Variable->SetGenericRep (var.Value, var.Type);
if (var.Type == CVAR_String)
delete[] var.Value.String;
@ -1377,7 +1385,7 @@ void C_ArchiveCVars (FConfigFile *f, uint32_t filter)
while (cvar)
{
if ((cvar->Flags &
(CVAR_GLOBALCONFIG|CVAR_ARCHIVE|CVAR_AUTO|CVAR_SERVERINFO|CVAR_USERINFO|CVAR_NOSAVE|CVAR_VIDEOCONFIG))
(CVAR_GLOBALCONFIG|CVAR_ARCHIVE|CVAR_MOD|CVAR_AUTO|CVAR_USERINFO|CVAR_SERVERINFO|CVAR_NOSAVE|CVAR_CONFIG_ONLY))
== filter)
{
cvarlist.Push(cvar);
@ -1387,10 +1395,9 @@ void C_ArchiveCVars (FConfigFile *f, uint32_t filter)
qsort(cvarlist.Data(), cvarlist.Size(), sizeof(FBaseCVar*), cvarcmp);
for (auto cvar : cvarlist)
{
// This does not work with the menus at use here.
const char* const value = //(cvar->Flags & CVAR_ISDEFAULT)
/*?*/ cvar->GetGenericRep(CVAR_String).String
/*: cvar->SafeValue.GetChars()*/;
const char* const value = (cvar->Flags & CVAR_ISDEFAULT)
? cvar->GetGenericRep(CVAR_String).String
: cvar->SafeValue.GetChars();
f->SetValueForKey(cvar->GetName(), value);
}
}
@ -1399,6 +1406,9 @@ EXTERN_CVAR(Bool, sv_cheats);
void FBaseCVar::CmdSet (const char *newval)
{
if ((GetFlags() & CVAR_CHEAT) && CheckCheatmode ())
return;
MarkUnsafe();
UCVarValue val;
@ -1491,23 +1501,8 @@ CCMD (toggle)
val = var->GetGenericRep (CVAR_Bool);
val.Bool = !val.Bool;
var->SetGenericRep (val, CVAR_Bool);
const char *statestr = argv.argc() <= 2? "*" : argv[2];
if (*statestr == '*')
{
gi->PrintMessage(PRINT_MEDIUM, "\"%s\" = \"%s\"\n", var->GetName(), val.Bool ? "true" : "false");
}
else
{
int state = (int)strtoll(argv[2], nullptr, 0);
if (state != 0)
{
// Order of Duke's quote string varies, some have on first, some off, so use the sign of the parameter to decide.
// Positive means Off/On, negative means On/Off
int quote = state > 0? state + val.Bool : -(state + val.Bool);
auto text = quoteMgr.GetQuote(quote);
if (text) gi->PrintMessage(PRINT_MEDIUM, "%s\n", text);
}
}
Printf ("\"%s\" = \"%s\"\n", var->GetName(),
val.Bool ? "true" : "false");
}
}
}
@ -1533,7 +1528,7 @@ void FBaseCVar::ListVars (const char *filter, bool plain)
else
{
++count;
Printf ("%c%c%c %s = %s\n",
Printf ("%c%c%c%c%c %s = %s\n",
flags & CVAR_ARCHIVE ? 'A' : ' ',
flags & CVAR_USERINFO ? 'U' :
flags & CVAR_SERVERINFO ? 'S' :
@ -1541,6 +1536,8 @@ void FBaseCVar::ListVars (const char *filter, bool plain)
flags & CVAR_NOSET ? '-' :
flags & CVAR_LATCH ? 'L' :
flags & CVAR_UNSETTABLE ? '*' : ' ',
flags & CVAR_MOD ? 'M' : ' ',
flags & CVAR_IGNORE ? 'X' : ' ',
var->GetName(),
var->GetHumanString());
}
@ -1584,3 +1581,4 @@ CCMD (archivecvar)
}
}
}

View file

@ -36,6 +36,7 @@
#include "zstring.h"
#include "tarray.h"
class FSerializer; // this needs to go away.
/*
==========================================================
@ -46,30 +47,29 @@ CVARS (console variables)
enum
{
CVAR_ARCHIVE = 1, // set to cause it to be saved to config
CVAR_USERINFO = 2, // added to userinfo when changed
CVAR_SERVERINFO = 4, // added to serverinfo when changed
CVAR_NOSET = 8, // don't allow change from console at all,
// but can be set from the command line
CVAR_LATCH = 16, // save changes until server restart
CVAR_UNSETTABLE = 32, // can unset this var from console
CVAR_DEMOSAVE = 64, // save the value of this cvar in a demo
CVAR_ISDEFAULT = 128, // is cvar unchanged since creation?
CVAR_NOSAVE = 256, // when used with CVAR_SERVERINFO, do not save var to savegame
CVAR_NOINITCALL = 512, // don't call callback at game start
CVAR_GLOBALCONFIG = 1024, // cvar is saved to global config section
CVAR_VIDEOCONFIG = 2048, // cvar is saved to video config section (not implemented)
CVAR_AUTO = 4096, // allocated; needs to be freed when destroyed
//CVAR_MOD = 8192, // cvar was defined by a mod
//CVAR_IGNORE = 16384,// do not send cvar across the network/inaccesible from ACS (dummy mod cvar)
//CVAR_CHEAT = 32768,// can be set only when sv_cheats is enabled
//CVAR_UNSAFECONTEXT = 65536,// cvar value came from unsafe context
CVAR_VIRTUAL = 0x20000, //do not invoke the callback recursively so it can
CVAR_FRONTEND_BLOOD = 0x10000000, // To mark frontend specific CVARs, so that the other ones can disable them.
CVAR_FRONTEND_EDUKE = 0x20000000,
CVAR_FRONTEND_DUKELIKE = 0x30000000,
CVAR_FRONTEND_REDNUKEM = 0x40000000,
CVAR_FRONTEND_SHADOWWARRIOR = 0x80000000,
CVAR_ARCHIVE = 1, // set to cause it to be saved to config.
CVAR_USERINFO = 1 << 1, // added to userinfo when changed.
CVAR_SERVERINFO = 1 << 2, // added to serverinfo when changed.
CVAR_NOSET = 1 << 3, // don't allow change from console at all,
// but can be set from the command line.
CVAR_LATCH = 1 << 4, // save changes until server restart.
CVAR_UNSETTABLE = 1 << 5, // can unset this var from console.
CVAR_DEMOSAVE = 1 << 6, // save the value of this cvar in a demo.
CVAR_ISDEFAULT = 1 << 7, // is cvar unchanged since creation?
CVAR_AUTO = 1 << 8, // allocated; needs to be freed when destroyed.
CVAR_NOINITCALL = 1 << 9, // don't call callback at game start.
CVAR_GLOBALCONFIG = 1 << 10, // cvar is saved to global config section.
CVAR_VIDEOCONFIG = 1 << 11, // cvar is saved to video config section (not implemented).
CVAR_NOSAVE = 1 << 12, // when used with CVAR_SERVERINFO, do not save var to savegame
// and config.
CVAR_MOD = 1 << 13, // cvar was defined by a mod.
CVAR_IGNORE = 1 << 14, // do not send cvar across the network/inaccesible from ACS
// (dummy mod cvar).
CVAR_CHEAT = 1 << 15, // can be set only when sv_cheats is enabled.
CVAR_UNSAFECONTEXT = 1 << 16, // cvar value came from unsafe context.
CVAR_VIRTUAL = 1 << 17, // do not invoke the callback recursively so it can be used to
// mirror an external variable.
CVAR_CONFIG_ONLY = 1 << 18, // do not save var to savegame and do not send it across network.
};
union UCVarValue
@ -102,6 +102,20 @@ class FConfigFile;
class FxCVar;
class FBaseCVar;
// These are calls into the game code. Having these hard coded in the CVAR implementation has always been the biggest blocker
// for reusing the CVAR module outside of ZDoom. So now they get called through this struct for easier reusability.
struct ConsoleCallbacks
{
void (*UserInfoChanged)(FBaseCVar*);
void (*SendServerInfoChange)(FBaseCVar* cvar, UCVarValue value, ECVarType type);
void (*SendServerFlagChange)(FBaseCVar* cvar, int bitnum, bool set, bool silent);
FBaseCVar* (*GetUserCVar)(int playernum, const char* cvarname);
bool (*MustLatch)();
};
class FBaseCVar
{
public:
@ -128,6 +142,7 @@ public:
void ResetToDefault ();
void SetArchiveBit () { Flags |= CVAR_ARCHIVE; }
void MarkUnsafe();
void MarkSafe() { Flags &= ~CVAR_UNSAFECONTEXT; }
int ToInt()
{
@ -186,7 +201,9 @@ private:
static bool m_UseCallback;
static bool m_DoNoSet;
// These need to go away!
friend FString C_GetMassCVarString (uint32_t filter, bool compact);
friend void C_SerializeCVars(FSerializer& arc, const char* label, uint32_t filter);
friend void C_ReadCVars (uint8_t **demo_p);
friend void C_BackupCVars (void);
friend FBaseCVar *FindCVar (const char *var_name, FBaseCVar **prev);
@ -210,6 +227,8 @@ void C_WriteCVars (uint8_t **demo_p, uint32_t filter, bool compact=false);
// Read all cvars from *demo_p and set them appropriately.
void C_ReadCVars (uint8_t **demo_p);
void C_InstallHandlers(ConsoleCallbacks* cb);
// Backup demo cvars. Called before a demo starts playing to save all
// cvars the demo might change.
void C_BackupCVars (void);
@ -218,6 +237,9 @@ void C_BackupCVars (void);
FBaseCVar *FindCVar (const char *var_name, FBaseCVar **prev);
FBaseCVar *FindCVarSub (const char *var_name, int namelen);
// Used for ACS and DECORATE.
FBaseCVar *GetCVar(int playernum, const char *cvarname);
// Create a new cvar with the specified name and type
FBaseCVar *C_CreateCVar(const char *var_name, ECVarType var_type, uint32_t flags);
@ -259,10 +281,8 @@ public:
protected:
virtual void DoSet (UCVarValue value, ECVarType type);
// int is needed as long as this needs to connect to the menus
public: // also for the menu code which still needs variable references. (Cannot change everything at once.)
int/*bool*/ Value;
int/*bool*/ DefaultValue;
bool Value;
bool DefaultValue;
};
class FIntCVar : public FBaseCVar
@ -287,7 +307,6 @@ public:
protected:
virtual void DoSet (UCVarValue value, ECVarType type);
public: // for the menu code which still needs variable references. (Cannot change everything at once.)
int Value;
int DefaultValue;
@ -317,7 +336,6 @@ public:
protected:
virtual void DoSet (UCVarValue value, ECVarType type) override;
public: // for the menu code which still needs variable references. (Cannot change everything at once.)
float Value;
float DefaultValue;
};
@ -349,7 +367,6 @@ protected:
FString mDefaultValue;
};
#if 0
class FColorCVar : public FIntCVar
{
friend class FxCVar;
@ -371,7 +388,6 @@ protected:
static UCVarValue FromInt2 (int value, ECVarType type);
static int ToInt2 (UCVarValue value, ECVarType type);
};
#endif
class FFlagCVar : public FBaseCVar
{
@ -449,6 +465,11 @@ void C_ForgetCVars (void);
F##type##CVar name (#name, def, flags, cvarfunc_##name); \
static void cvarfunc_##name(F##type##CVar &self)
#define CUSTOM_CVAR_NAMED(type,name,cname,def,flags) \
static void cvarfunc_##name(F##type##CVar &); \
F##type##CVar name (#cname, def, flags, cvarfunc_##name); \
static void cvarfunc_##name(F##type##CVar &self)
#define CVAR(type,name,def,flags) \
F##type##CVar name (#name, def, flags);

View file

@ -40,24 +40,18 @@
#include <ctype.h>
#include "templates.h"
//#include "doomtype.h"
#include "cmdlib.h"
#include "c_console.h"
#include "c_dispatch.h"
#include "m_argv.h"
//#include "g_game.h"
//#include "d_player.h"
#include "gamestate.h"
#include "configfile.h"
#include "printf.h"
#include "c_cvars.h"
#include "v_text.h"
#include "inputstate.h"
#include "c_buttons.h"
//#include "d_net.h"
//#include "d_main.h"
//#include "serializer.h"
//#include "menu/menu.h"
//#include "g_levellocals.h"
// Todo: Get rid of
#include "inputstate.h"
bool D_AddFile(TArray<FString>& wadfiles, const char* file, bool check = true, int position = -1);
// MACROS ------------------------------------------------------------------
@ -77,14 +71,15 @@ protected:
class FWaitingCommand : public FDelayedCommand
{
public:
FWaitingCommand(const char *cmd, int tics)
: Command(cmd), TicsLeft(tics+1)
FWaitingCommand(const char *cmd, int tics, bool unsafe)
: Command(cmd), TicsLeft(tics+1), IsUnsafe(unsafe)
{}
bool Tick() override
{
if (--TicsLeft == 0)
{
UnsafeExecutionScope scope(IsUnsafe);
AddCommandString(Command);
return true;
}
@ -93,6 +88,7 @@ public:
FString Command;
int TicsLeft;
bool IsUnsafe;
};
class FStoredCommand : public FDelayedCommand
@ -107,7 +103,7 @@ public:
if (Text.IsNotEmpty() && Command != nullptr)
{
FCommandLine args(Text);
Command->Run(args, /*current player*/nullptr, 0);
Command->Run(args, 0);
}
return true;
}
@ -172,14 +168,28 @@ static FConsoleCommand *ScanChainForName (FConsoleCommand *start, const char *na
// EXTERNAL DATA DECLARATIONS ----------------------------------------------
// PUBLIC DATA DEFINITIONS -------------------------------------------------
bool ParsingKeyConf, UnsafeExecutionContext;
FString StoredWarp;
FConsoleCommand* Commands[FConsoleCommand::HASH_SIZE];
CVAR (Bool, lookspring, true, CVAR_ARCHIVE); // Generate centerview when -mlook encountered?
FConsoleCommand *Commands[FConsoleCommand::HASH_SIZE];
// PRIVATE DATA DEFINITIONS ------------------------------------------------
static const char *KeyConfCommands[] =
{
"alias",
"defaultbind",
"addkeysection",
"addmenukey",
"addslotdefault",
"weaponsection",
"setslot",
"addplayerclass",
"clearplayerclasses"
};
// CODE --------------------------------------------------------------------
void C_DoCommand (const char *cmd, int keynum)
@ -207,6 +217,25 @@ void C_DoCommand (const char *cmd, int keynum)
const size_t len = end - beg;
if (ParsingKeyConf)
{
int i;
for (i = countof(KeyConfCommands)-1; i >= 0; --i)
{
if (strnicmp (beg, KeyConfCommands[i], len) == 0 &&
KeyConfCommands[i][len] == 0)
{
break;
}
}
if (i < 0)
{
Printf ("Invalid command for KEYCONF: %s\n", beg);
return;
}
}
// Check if this is an action
if (*beg == '+' || *beg == '-')
{
@ -238,23 +267,24 @@ void C_DoCommand (const char *cmd, int keynum)
if ( (com = FindNameInHashTable (Commands, beg, len)) )
{
if (//gamestate != GS_STARTUP ||
if (gamestate != GS_STARTUP || ParsingKeyConf ||
(len == 3 && strnicmp (beg, "set", 3) == 0) ||
(len == 7 && strnicmp (beg, "logfile", 7) == 0) ||
(len == 9 && strnicmp (beg, "unbindall", 9) == 0) ||
(len == 4 && strnicmp (beg, "bind", 4) == 0) ||
(len == 4 && strnicmp (beg, "exec", 4) == 0) ||
(len ==10 && strnicmp (beg, "doublebind", 10) == 0)
(len ==10 && strnicmp (beg, "doublebind", 10) == 0) ||
(len == 6 && strnicmp (beg, "pullin", 6) == 0)
)
{
FCommandLine args (beg);
com->Run (args, /*current player*/nullptr, keynum);
com->Run (args, keynum);
}
else
{
if (len == 4 && strnicmp(beg, "warp", 4) == 0)
{
//StoredWarp = beg;
StoredWarp = beg;
}
else
{
@ -326,7 +356,8 @@ void AddCommandString (const char *text, int keynum)
cmd++;
if (*cmd)
{
if (cmd[0] == 'w' && cmd[1] == 'a' && cmd[2] == 'i' && cmd[3] == 't' &&
if (!ParsingKeyConf &&
cmd[0] == 'w' && cmd[1] == 'a' && cmd[2] == 'i' && cmd[3] == 't' &&
(cmd[4] == 0 || cmd[4] == ' '))
{
int tics;
@ -346,7 +377,7 @@ void AddCommandString (const char *text, int keynum)
// Note that deferred commands lose track of which key
// (if any) they were pressed from.
*brkpt = ';';
auto cmd = new FWaitingCommand(brkpt, tics);
auto cmd = new FWaitingCommand(brkpt, tics, UnsafeExecutionContext);
delayedCommandQueue.AddCommand(cmd);
}
return;
@ -473,9 +504,20 @@ FConsoleCommand::~FConsoleCommand ()
C_RemoveTabCommand (m_Name);
}
void FConsoleCommand::Run (FCommandLine &argv, void *who, int key)
void FConsoleCommand::Run(FCommandLine &argv, int key)
{
m_RunFunc (argv, who, key);
m_RunFunc (argv, key);
}
void FUnsafeConsoleCommand::Run(FCommandLine &args, int key)
{
if (UnsafeExecutionContext)
{
Printf(TEXTCOLOR_RED "Cannot execute unsafe command " TEXTCOLOR_GOLD "%s\n", m_Name);
return;
}
FConsoleCommand::Run (args, key);
}
FConsoleAlias::FConsoleAlias (const char *name, const char *command, bool noSave)
@ -555,6 +597,11 @@ FString BuildString (int argc, FString *argv)
//
//===========================================================================
void FConsoleCommand::PrintCommand()
{
Printf("%s\n", m_Name.GetChars());
}
FString SubstituteAliasParams (FString &command, FCommandLine &args)
{
// Do substitution by replacing %x with the argument x.
@ -790,7 +837,7 @@ CCMD (alias)
{
if (alias->IsAlias ())
{
static_cast<FConsoleAlias *> (alias)->Realias (argv[2], false);
static_cast<FConsoleAlias *> (alias)->Realias (argv[2], ParsingKeyConf);
}
else
{
@ -798,6 +845,10 @@ CCMD (alias)
alias = NULL;
}
}
else if (ParsingKeyConf)
{
new FUnsafeConsoleAlias (argv[1], argv[2]);
}
else
{
new FConsoleAlias (argv[1], argv[2], false);
@ -864,11 +915,6 @@ FExecList *C_ParseCmdLineParams(FExecList *exec)
return exec;
}
void FConsoleCommand::PrintCommand()
{
Printf("%s\n", m_Name.GetChars());
}
bool FConsoleCommand::IsAlias ()
{
return false;
@ -879,7 +925,7 @@ bool FConsoleAlias::IsAlias ()
return true;
}
void FConsoleAlias::Run (FCommandLine &args, void *who, int key)
void FConsoleAlias::Run (FCommandLine &args, int key)
{
if (bRunning)
{
@ -942,10 +988,24 @@ void FConsoleAlias::SafeDelete ()
}
}
void FUnsafeConsoleAlias::Run (FCommandLine &args, int key)
{
UnsafeExecutionScope scope;
FConsoleAlias::Run(args, key);
}
void FExecList::AddCommand(const char *cmd, const char *file)
{
// Pullins are special and need to be separated from general commands.
// They also turned out to be a really bad idea, since they make things
// more complicated. :(
if (file != NULL && strnicmp(cmd, "pullin", 6) == 0 && isspace(cmd[6]))
{
FCommandLine line(cmd);
C_SearchForPullins(this, file, line);
}
// Recursive exec: Parse this file now.
if (strnicmp(cmd, "exec", 4) == 0 && isspace(cmd[4]))
else if (strnicmp(cmd, "exec", 4) == 0 && isspace(cmd[4]))
{
FCommandLine argv(cmd);
for (int i = 1; i < argv.argc(); ++i)
@ -967,6 +1027,14 @@ void FExecList::ExecCommands() const
}
}
void FExecList::AddPullins(TArray<FString> &wads) const
{
for (unsigned i = 0; i < Pullins.Size(); ++i)
{
D_AddFile(wads, Pullins[i]);
}
}
FExecList *C_ParseExecFile(const char *file, FExecList *exec)
{
char cmd[4096];
@ -1026,25 +1094,61 @@ bool C_ExecFile (const char *file)
if (exec != NULL)
{
exec->ExecCommands();
if (exec->Pullins.Size() > 0)
{
Printf(TEXTCOLOR_BOLD "Notice: Pullin files were ignored.\n");
}
delete exec;
}
return exec != NULL;
}
#include "osd.h"
void C_SearchForPullins(FExecList *exec, const char *file, FCommandLine &argv)
{
const char *lastSlash;
assert(exec != NULL);
assert(file != NULL);
#ifdef __unix__
lastSlash = strrchr(file, '/');
#else
const char *lastSlash1, *lastSlash2;
lastSlash1 = strrchr(file, '/');
lastSlash2 = strrchr(file, '\\');
lastSlash = MAX(lastSlash1, lastSlash2);
#endif
for (int i = 1; i < argv.argc(); ++i)
{
// Try looking for the wad in the same directory as the .cfg
// before looking for it in the current directory.
if (lastSlash != NULL)
{
FString path(file, (lastSlash - file) + 1);
path += argv[i];
if (FileExists(path))
{
exec->Pullins.Push(path);
continue;
}
}
exec->Pullins.Push(argv[i]);
}
}
static TArray<FConsoleCommand*> dynccmds; // This needs to be explicitly deleted before shutdown - the names in here may not be valid during the exit handler.
//
// OSD_RegisterFunction() -- Reroutes a Bulid-style CCMD to the new console.
// C_RegisterFunction() -- dynamically register a CCMD.
//
int OSD_RegisterFunction(const char* pszName, const char* pszDesc, int (*func)(osdcmdptr_t))
int C_RegisterFunction(const char* pszName, const char* pszDesc, int (*func)(CCmdFuncPtr))
{
FString nname = pszName;
auto callback = [nname, pszDesc, func](FCommandLine& args, void *, int key)
auto callback = [nname, pszDesc, func](FCommandLine& args, int key)
{
if (args.argc() > 0) args.operator[](0);
osdfuncparm_t param = { args.argc() - 1, nname.GetChars(), (const char**)args._argv + 1, args.cmd };
if (func(&param) != OSDCMD_OK)
CCmdFuncParm param = { args.argc() - 1, nname.GetChars(), (const char**)args._argv + 1, args.cmd };
if (func(&param) != CCMD_OK)
{
Printf("%s\n", pszDesc);
}
@ -1064,43 +1168,10 @@ void C_ClearDynCCmds()
dynccmds.Clear();
}
CCMD (quit)
CCMD (pullin)
{
throw CExitEvent(0);
// Actual handling for pullin is now completely special-cased above
Printf (TEXTCOLOR_BOLD "Pullin" TEXTCOLOR_NORMAL " is only valid from .cfg\n"
"files and only when used at startup.\n");
}
CCMD (exit)
{
throw CExitEvent(0);
}
extern FILE* Logfile;
void execLogfile(const char* fn, bool append)
{
if ((Logfile = fopen(fn, append ? "a" : "w")))
{
const char* timestr = myasctime();
Printf("Log started: %s\n", timestr);
}
else
{
Printf("Could not start log\n");
}
}
CCMD(logfile)
{
if (Logfile)
{
const char* timestr = myasctime();
Printf("Log stopped: %s\n", timestr);
fclose(Logfile);
Logfile = NULL;
}
if (argv.argc() >= 2)
{
execLogfile(argv[1], argv.argc() >= 3 ? !!argv[2] : false);
}
}

View file

@ -34,23 +34,30 @@
#ifndef __C_DISPATCH_H__
#define __C_DISPATCH_H__
#include <stdint.h>
#include <functional>
#include "c_console.h"
#include "zstring.h"
#include "tarray.h"
#include "c_commandline.h"
#include "zstring.h"
class FConfigFile;
// Contains the contents of an exec'ed file
struct FExecList
{
TArray<FString> Commands;
TArray<FString> Pullins;
void AddCommand(const char *cmd, const char *file = NULL);
void AddCommand(const char *cmd, const char *file = nullptr);
void ExecCommands() const;
void AddPullins(TArray<FString> &wads) const;
};
extern bool ParsingKeyConf, UnsafeExecutionContext;
extern FString StoredWarp; // [RH] +warp at the command line
extern bool CheckCheatmode (bool printmsg = true);
@ -69,6 +76,7 @@ void C_ClearDelayedCommands();
void C_DoCommand (const char *cmd, int keynum=0);
FExecList *C_ParseExecFile(const char *file, FExecList *source);
void C_SearchForPullins(FExecList *exec, const char *file, class FCommandLine &args);
bool C_ExecFile(const char *file);
void C_ClearDynCCmds();
@ -81,7 +89,7 @@ void C_ClearAliases ();
// build a single string out of multiple strings
FString BuildString (int argc, FString *argv);
typedef std::function<void(FCommandLine & argv, void *, int key)> CCmdRun;;
typedef std::function<void(FCommandLine & argv, int key)> CCmdRun;;
class FConsoleCommand
{
@ -91,7 +99,7 @@ public:
virtual bool IsAlias ();
void PrintCommand();
virtual void Run (FCommandLine &args, void *instigator, int key);
virtual void Run (FCommandLine &args, int key);
static FConsoleCommand* FindByName (const char* name);
FConsoleCommand *m_Next, **m_Prev;
@ -108,9 +116,25 @@ protected:
};
#define CCMD(n) \
void Cmd_##n (FCommandLine &, void *, int key); \
void Cmd_##n (FCommandLine &, int key); \
FConsoleCommand Cmd_##n##_Ref (#n, Cmd_##n); \
void Cmd_##n (FCommandLine &argv, void *who, int key)
void Cmd_##n (FCommandLine &argv, int key)
class FUnsafeConsoleCommand : public FConsoleCommand
{
public:
FUnsafeConsoleCommand (const char *name, CCmdRun RunFunc)
: FConsoleCommand (name, RunFunc)
{
}
virtual void Run (FCommandLine &args, int key) override;
};
#define UNSAFE_CCMD(n) \
static void Cmd_##n (FCommandLine &, int key); \
static FUnsafeConsoleCommand Cmd_##n##_Ref (#n, Cmd_##n); \
void Cmd_##n (FCommandLine &argv, int key)
const int KEY_DBLCLICKED = 0x8000;
@ -119,7 +143,7 @@ class FConsoleAlias : public FConsoleCommand
public:
FConsoleAlias (const char *name, const char *command, bool noSave);
~FConsoleAlias ();
void Run (FCommandLine &args, void *instigator, int key);
void Run (FCommandLine &args, int key);
bool IsAlias ();
void PrintAlias ();
void Archive (FConfigFile *f);
@ -140,10 +164,51 @@ public:
{
}
virtual void Run (FCommandLine &args, void *instigator, int key) override;
virtual void Run (FCommandLine &args, int key) override;
};
class UnsafeExecutionScope
{
const bool wasEnabled;
public:
explicit UnsafeExecutionScope(const bool enable = true)
: wasEnabled(UnsafeExecutionContext)
{
UnsafeExecutionContext = enable;
}
~UnsafeExecutionScope()
{
UnsafeExecutionContext = wasEnabled;
}
};
void execLogfile(const char *fn, bool append = false);
enum
{
CCMD_OK = 0,
CCMD_SHOWHELP = 1
};
struct CCmdFuncParm
{
int32_t numparms;
const char* name;
const char** parms;
const char* raw;
};
using CCmdFuncPtr = CCmdFuncParm const* const;
// registers a function
// name = name of the function
// help = a short help string
// func = the entry point to the function
int C_RegisterFunction(const char* name, const char* help, int (*func)(CCmdFuncPtr));
#endif //__C_DISPATCH_H__

View file

@ -58,6 +58,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include "glbackend/glbackend.h"
#include "engineerrors.h"
#include "mmulti.h"
#include "gamestate.h"
// The last remains of sdlayer.cpp
double g_beforeSwapTime;
@ -73,6 +74,8 @@ MapRecord *currentLevel; // level that is currently played. (The real level, not
MapRecord* lastLevel; // Same here, for the last level.
MapRecord userMapRecord; // stand-in for the user map.
gamestate_t gamestate = GS_STARTUP;
FILE* hashfile;
FStartupInfo RazeStartupInfo;
@ -691,7 +694,7 @@ int RunGame()
InitStatistics();
M_Init();
SetDefaultStrings();
if (g_gameType & (GAMEFLAG_RR|GAMEFLAG_RRRA)) InitRREndMap(); // this needs to be done better later
if (g_gameType & (GAMEFLAG_RR)) InitRREndMap(); // this needs to be done better later
if (Args->CheckParm("-sounddebug"))
C_DoCommand("stat sounddebug");
@ -705,6 +708,7 @@ int RunGame()
auto exec = C_ParseCmdLineParams(nullptr);
if (exec) exec->ExecCommands();
gamestate = GS_LEVEL;
return gi->app_main();
}
@ -869,3 +873,85 @@ CCMD(printinterface)
{
Printf("Current interface is %s\n", gi->Name());
}
CCMD (togglemsg)
{
FBaseCVar *var, *prev;
UCVarValue val;
if (argv.argc() > 1)
{
if ( (var = FindCVar (argv[1], &prev)) )
{
var->MarkUnsafe();
val = var->GetGenericRep (CVAR_Bool);
val.Bool = !val.Bool;
var->SetGenericRep (val, CVAR_Bool);
const char *statestr = argv.argc() <= 2? "*" : argv[2];
if (*statestr == '*')
{
gi->PrintMessage(PRINT_MEDIUM, "\"%s\" = \"%s\"\n", var->GetName(), val.Bool ? "true" : "false");
}
else
{
int state = (int)strtoll(argv[2], nullptr, 0);
if (state != 0)
{
// Order of Duke's quote string varies, some have on first, some off, so use the sign of the parameter to decide.
// Positive means Off/On, negative means On/Off
int quote = state > 0? state + val.Bool : -(state + val.Bool);
auto text = quoteMgr.GetQuote(quote);
if (text) gi->PrintMessage(PRINT_MEDIUM, "%s\n", text);
}
}
}
}
}
CCMD(quit)
{
throw CExitEvent(0);
}
CCMD(exit)
{
throw CExitEvent(0);
}
extern FILE* Logfile;
void execLogfile(const char* fn, bool append)
{
if ((Logfile = fopen(fn, append ? "a" : "w")))
{
const char* timestr = myasctime();
Printf("Log started: %s\n", timestr);
}
else
{
Printf("Could not start log\n");
}
}
CCMD(logfile)
{
if (Logfile)
{
const char* timestr = myasctime();
Printf("Log stopped: %s\n", timestr);
fclose(Logfile);
Logfile = NULL;
}
if (argv.argc() >= 2)
{
execLogfile(argv[1], argv.argc() >= 3 ? !!argv[2] : false);
}
}
// Just a placeholder for now.
bool CheckCheatmode(bool printmsg)
{
return false;
}

View file

@ -47,6 +47,9 @@
#include "gstrings.h"
#include "quotemgr.h"
#define CVAR_FRONTEND_BLOOD 0
#define CVAR_FRONTEND_DUKELIKE 0
/* Notes
RedNukem has this for the toggle autorun command. Todo: Check what this is supposed to accomplish. The implementation makes no sense at all.
@ -444,6 +447,43 @@ bool G_AllowAutoload()
return true;
}
// color code format is as follows:
// ^## sets a color, where ## is the palette number
// ^S# sets a shade, range is 0-7 equiv to shades 0-14
// ^O resets formatting to defaults
static const char* OSD_StripColors(char* outBuf, const char* inBuf)
{
const char* ptr = outBuf;
while (*inBuf)
{
if (*inBuf == '^')
{
if (isdigit(*(inBuf + 1)))
{
inBuf += 2 + !!isdigit(*(inBuf + 2));
continue;
}
else if ((toupper(*(inBuf + 1)) == 'O'))
{
inBuf += 2;
continue;
}
else if ((toupper(*(inBuf + 1)) == 'S') && isdigit(*(inBuf + 2)))
{
inBuf += 3;
continue;
}
}
*(outBuf++) = *(inBuf++);
}
*outBuf = '\0';
return ptr;
}
CVAR(Bool, adult_lockout, false, CVAR_ARCHIVE)
CUSTOM_CVAR(String, playername, "Player", CVAR_ARCHIVE | CVAR_USERINFO)
{

23
source/core/gamestate.h Normal file
View file

@ -0,0 +1,23 @@
#pragma once
// The current state of the game: whether we are
// playing, gazing at the intermission screen,
// the game final animation, or a demo.
enum gamestate_t : int
{
GS_LEVEL,
GS_INTERMISSION,
GS_FINALE,
GS_DEMOSCREEN,
GS_FULLCONSOLE, // [RH] Fullscreen console
GS_HIDECONSOLE, // [RH] The menu just did something that should hide fs console
GS_STARTUP, // [RH] Console is fullscreen, and game is just starting
GS_TITLELEVEL, // [RH] A combination of GS_LEVEL and GS_DEMOSCREEN
GS_FORCEWIPE = -1,
GS_FORCEWIPEFADE = -2,
GS_FORCEWIPEBURN = -3,
GS_FORCEWIPEMELT = -4
};
extern gamestate_t gamestate;

View file

@ -45,6 +45,7 @@
#include "v_video.h"
#include "v_text.h"
#include "findfile.h"
#include "palutil.h"
#ifndef PATH_MAX
#define PATH_MAX 260

View file

@ -254,225 +254,6 @@ void DCanvas::Resize(int width, int height, bool optimizepitch)
}
//==========================================================================
//
// V_GetColorFromString
//
// Passed a string of the form "#RGB", "#RRGGBB", "R G B", or "RR GG BB",
// returns a number representing that color. If palette is non-NULL, the
// index of the best match in the palette is returned, otherwise the
// RRGGBB value is returned directly.
//
//==========================================================================
int V_GetColorFromString (const uint32_t *palette, const char *cstr, FScriptPosition *sc)
{
int c[3], i, p;
char val[3];
val[2] = '\0';
// Check for HTML-style #RRGGBB or #RGB color string
if (cstr[0] == '#')
{
size_t len = strlen (cstr);
if (len == 7)
{
// Extract each eight-bit component into c[].
for (i = 0; i < 3; ++i)
{
val[0] = cstr[1 + i*2];
val[1] = cstr[2 + i*2];
c[i] = ParseHex (val, sc);
}
}
else if (len == 4)
{
// Extract each four-bit component into c[], expanding to eight bits.
for (i = 0; i < 3; ++i)
{
val[1] = val[0] = cstr[1 + i];
c[i] = ParseHex (val, sc);
}
}
else
{
// Bad HTML-style; pretend it's black.
c[2] = c[1] = c[0] = 0;
}
}
else
{
if (strlen(cstr) == 6)
{
char *p;
int color = strtol(cstr, &p, 16);
if (*p == 0)
{
// RRGGBB string
c[0] = (color & 0xff0000) >> 16;
c[1] = (color & 0xff00) >> 8;
c[2] = (color & 0xff);
}
else goto normal;
}
else
{
normal:
// Treat it as a space-delimited hexadecimal string
for (i = 0; i < 3; ++i)
{
// Skip leading whitespace
while (*cstr <= ' ' && *cstr != '\0')
{
cstr++;
}
// Extract a component and convert it to eight-bit
for (p = 0; *cstr > ' '; ++p, ++cstr)
{
if (p < 2)
{
val[p] = *cstr;
}
}
if (p == 0)
{
c[i] = 0;
}
else
{
if (p == 1)
{
val[1] = val[0];
}
c[i] = ParseHex (val, sc);
}
}
}
}
return MAKERGB(c[0], c[1], c[2]);
}
//==========================================================================
//
// V_GetColorStringByName
//
// Searches for the given color name in x11r6rgb.txt and returns an
// HTML-ish "#RRGGBB" string for it if found or the empty string if not.
//
//==========================================================================
FString V_GetColorStringByName (const char *name, FScriptPosition *sc)
{
char *rgbEnd;
char *rgb, *endp;
int rgblump;
int c[3], step;
size_t namelen;
if (fileSystem.GetNumEntries()==0) return FString();
rgblump = fileSystem.FindFile ("engine/X11R6RGB.txt");
if (rgblump == -1)
{
if (!sc) Printf ("X11R6RGB lump not found\n");
else sc->Message(MSG_WARNING, "X11R6RGB lump not found");
return FString();
}
rgb = (char*)fileSystem.Lock(rgblump);
rgbEnd = rgb + fileSystem.FileLength (rgblump);
step = 0;
namelen = strlen (name);
while (rgb < rgbEnd)
{
// Skip white space
if (*rgb <= ' ')
{
do
{
rgb++;
} while (rgb < rgbEnd && *rgb <= ' ');
}
else if (step == 0 && *rgb == '!')
{ // skip comment lines
do
{
rgb++;
} while (rgb < rgbEnd && *rgb != '\n');
}
else if (step < 3)
{ // collect RGB values
c[step++] = strtoul (rgb, &endp, 10);
if (endp == rgb)
{
break;
}
rgb = endp;
}
else
{ // Check color name
endp = rgb;
// Find the end of the line
while (endp < rgbEnd && *endp != '\n')
endp++;
// Back up over any whitespace
while (endp > rgb && *endp <= ' ')
endp--;
if (endp == rgb)
{
break;
}
size_t checklen = ++endp - rgb;
if (checklen == namelen && strnicmp (rgb, name, checklen) == 0)
{
FString descr;
descr.Format ("#%02x%02x%02x", c[0], c[1], c[2]);
return descr;
}
rgb = endp;
step = 0;
}
}
if (rgb < rgbEnd)
{
if (!sc) Printf ("X11R6RGB lump is corrupt\n");
else sc->Message(MSG_WARNING, "X11R6RGB lump is corrupt");
}
return FString();
}
//==========================================================================
//
// V_GetColor
//
// Works like V_GetColorFromString(), but also understands X11 color names.
//
//==========================================================================
int V_GetColor (const uint32_t *palette, const char *str, FScriptPosition *sc)
{
FString string = V_GetColorStringByName (str, sc);
int res;
if (!string.IsEmpty())
{
res = V_GetColorFromString (palette, string, sc);
}
else
{
res = V_GetColorFromString (palette, str, sc);
}
return res;
}
int V_GetColor(const uint32_t *palette, FScanner &sc)
{
FScriptPosition scc = sc;
return V_GetColor(palette, sc.String, &scc);
}
CCMD(clean)
{
Printf ("CleanXfac: %d\nCleanYfac: %d\n", CleanXfac, CleanYfac);

View file

@ -413,19 +413,6 @@ void V_Init2 ();
void V_Shutdown ();
class FScanner;
struct FScriptPosition;
// Returns the closest color to the one desired. String
// should be of the form "rr gg bb".
int V_GetColorFromString (const uint32_t *palette, const char *colorstring, FScriptPosition *sc = nullptr);
// Scans through the X11R6RGB lump for a matching color
// and returns a color string suitable for V_GetColorFromString.
FString V_GetColorStringByName (const char *name, FScriptPosition *sc = nullptr);
// Tries to get color by name, then by string
int V_GetColor (const uint32_t *palette, const char *str, FScriptPosition *sc = nullptr);
int V_GetColor(const uint32_t *palette, FScanner &sc);
int CheckRatio (int width, int height, int *trueratio=NULL);
static inline int CheckRatio (double width, double height) { return CheckRatio(int(width), int(height)); }
inline bool IsRatioWidescreen(int ratio) { return (ratio & 3) != 0; }

View file

@ -113,7 +113,7 @@ static void ParseStatistics(const char *fn, TArray<FStatistics> &statlist)
try
{
FScanner sc;
sc.OpenFile(fn);
if (!sc.OpenFile(fn)) return;
while (sc.GetString())
{

View file

@ -1,142 +0,0 @@
/*
** bitmap.cpp
**
**---------------------------------------------------------------------------
** Copyright 2008-2019 Christoph Oelckers
** All rights reserved.
**
** Redistribution and use in source and binary forms, with or without
** modification, are permitted provided that the following conditions
** are met:
**
** 1. Redistributions of source code must retain the above copyright
** notice, this list of conditions and the following disclaimer.
** 2. Redistributions in binary form must reproduce the above copyright
** notice, this list of conditions and the following disclaimer in the
** documentation and/or other materials provided with the distribution.
** 3. The name of the author may not be used to endorse or promote products
** derived from this software without specific prior written permission.
**
** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
**---------------------------------------------------------------------------
**
**
*/
#include <assert.h>
#include "bitmap.h"
//===========================================================================
//
// multi-format pixel copy with colormap application
// requires the previously defined conversion classes to work
//
//===========================================================================
template<class TSrc, class TDest, class TBlend>
void iCopyColors(uint8_t *pout, const uint8_t *pin, int count, int step,
uint8_t tr, uint8_t tg, uint8_t tb)
{
int i;
int a;
for(i=0;i<count;i++)
{
a = TSrc::A(pin, tr, tg, tb);
if (TBlend::ProcessAlpha0() || a)
{
TBlend::OpC(pout[TDest::RED], TSrc::R(pin), a);
TBlend::OpC(pout[TDest::GREEN], TSrc::G(pin), a);
TBlend::OpC(pout[TDest::BLUE], TSrc::B(pin), a);
TBlend::OpA(pout[TDest::ALPHA], a);
}
pout+=4;
pin+=step;
}
}
typedef void (*CopyFunc)(uint8_t *pout, const uint8_t *pin, int count, int step, uint8_t r, uint8_t g, uint8_t b);
static const CopyFunc copyfuncs[]=
{
iCopyColors<cRGB, cBGRA, bCopy>,
iCopyColors<cRGBT, cBGRA, bCopy>,
iCopyColors<cRGBA, cBGRA, bCopy>,
iCopyColors<cIA, cBGRA, bCopy>,
iCopyColors<cCMYK, cBGRA, bCopy>,
iCopyColors<cYCbCr, cBGRA, bCopy>,
iCopyColors<cBGR, cBGRA, bCopy>,
iCopyColors<cBGRA, cBGRA, bCopy>,
iCopyColors<cI16, cBGRA, bCopy>,
iCopyColors<cRGB555, cBGRA, bCopy>,
iCopyColors<cPalEntry, cBGRA, bCopy>
};
//===========================================================================
//
// True Color texture copy function
//
//===========================================================================
void FBitmap::CopyPixelDataRGB(int originx, int originy, const uint8_t *patch, int srcwidth,
int srcheight, int step_x, int step_y, int rotate, int ct,
int r, int g, int b)
{
uint8_t *buffer = data + 4 * originx + Pitch * originy;
for (int y=0;y<srcheight;y++)
{
copyfuncs[ct](&buffer[y*Pitch], &patch[y*step_y], srcwidth, step_x, r, g, b);
}
}
template<class TDest, class TBlend>
void iCopyPaletted(uint8_t *buffer, const uint8_t * patch, int srcwidth, int srcheight, int Pitch,
int step_x, int step_y, int rotate, const PalEntry * palette)
{
int x,y,pos;
for (y=0;y<srcheight;y++)
{
pos = y*Pitch;
for (x=0;x<srcwidth;x++,pos+=4)
{
int v=(unsigned char)patch[y*step_y+x*step_x];
int a = palette[v].a;
if (TBlend::ProcessAlpha0() || a)
{
TBlend::OpC(buffer[pos + TDest::RED], palette[v].r, a);
TBlend::OpC(buffer[pos + TDest::GREEN], palette[v].g, a);
TBlend::OpC(buffer[pos + TDest::BLUE], palette[v].b, a);
TBlend::OpA(buffer[pos + TDest::ALPHA], a);
}
}
}
}
typedef void (*CopyPalettedFunc)(uint8_t *buffer, const uint8_t * patch, int srcwidth, int srcheight, int Pitch,
int step_x, int step_y, int rotate, PalEntry * palette);
//===========================================================================
//
// Paletted to True Color texture copy function
//
//===========================================================================
void FBitmap::CopyPixelData(int originx, int originy, const uint8_t * patch, int srcwidth, int srcheight,
int step_x, int step_y, int rotate, const PalEntry * palette)
{
uint8_t *buffer = data + 4*originx + Pitch*originy;
iCopyPaletted<cBGRA, bCopy>(buffer, patch, srcwidth, srcheight, Pitch,
step_x, step_y, rotate, palette);
}

View file

@ -879,7 +879,7 @@ void tileCopySection(int tilenum1, int sx1, int sy1, int xsiz, int ysiz, int til
if (x2 >= 0 && y2 >= 0 && x2 < xsiz2 && y2 < ysiz2)
{
auto src = p1[x1 * ysiz1 + y1];
if (src != 255)
if (src != TRANSPARENT_INDEX)
p2[x2 * ysiz2 + y2] = src;
}

View file

@ -487,7 +487,7 @@ int FPNGTexture::CopyPixels(FBitmap *bmp, int conversion)
else
{
bmp->CopyPixelDataRGB(0, 0, Pixels, Width, Height, 3, pixwidth, 0, CF_RGBT,
NonPaletteTrans[0], NonPaletteTrans[1], NonPaletteTrans[2]);
nullptr, NonPaletteTrans[0], NonPaletteTrans[1], NonPaletteTrans[2]);
transpal = true;
}
break;

View file

@ -40,7 +40,7 @@
#include <stdint.h>
#include "tarray.h"
#include "palentry.h"
#include "textures/bitmap.h"
#include "bitmap.h"
// we do not want to pull in the entirety of build.h here.
extern uint8_t palette[768];

View file

@ -49,6 +49,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
FString C_CON_GetBoundKeyForLastInput(int gameFunc);
const char* C_CON_GetButtonFunc(int num);
const char* KB_ScanCodeToString(int scancode); // convert scancode into a string
BEGIN_DUKE_NS

View file

@ -5260,7 +5260,7 @@ void Net_PrintLag(FString &output)
}
}
int osdcmd_listplayers(osdcmdptr_t parm)
int osdcmd_listplayers(CCmdFuncPtr parm)
{
ENetPeer* currentPeer;
char ipaddr[32];
@ -5292,7 +5292,7 @@ int osdcmd_listplayers(osdcmdptr_t parm)
}
#if 0
static int osdcmd_kick(osdcmdptr_t parm)
static int osdcmd_kick(CCmdFuncPtr parm)
{
ENetPeer* currentPeer;
uint32_t hexaddr;
@ -5330,7 +5330,7 @@ static int osdcmd_kick(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_kickban(osdcmdptr_t parm)
static int osdcmd_kickban(CCmdFuncPtr parm)
{
ENetPeer* currentPeer;
uint32_t hexaddr;

View file

@ -38,7 +38,7 @@ BEGIN_DUKE_NS
struct osdcmd_cheatsinfo osdcmd_cheatsinfo_stat = { -1, 0, 0 };
static int osdcmd_levelwarp(osdcmdptr_t parm)
static int osdcmd_levelwarp(CCmdFuncPtr parm)
{
if (parm->numparms != 2)
return OSDCMD_SHOWHELP;
@ -71,7 +71,7 @@ static int osdcmd_levelwarp(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_map(osdcmdptr_t parm)
static int osdcmd_map(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
@ -149,7 +149,7 @@ foundone:
// the variance of the run times MUST be taken into account (that is, the
// replaying must be performed multiple times for the old and new versions,
// etc.)
static int osdcmd_demo(osdcmdptr_t parm)
static int osdcmd_demo(CCmdFuncPtr parm)
{
if (numplayers > 1)
{
@ -176,7 +176,7 @@ static int osdcmd_demo(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_activatecheat(osdcmdptr_t parm)
static int osdcmd_activatecheat(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
return OSDCMD_SHOWHELP;
@ -189,7 +189,7 @@ static int osdcmd_activatecheat(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_god(osdcmdptr_t UNUSED(parm))
static int osdcmd_god(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
if (numplayers == 1 && g_player[myconnectindex].ps->gm & MODE_GAME)
@ -200,7 +200,7 @@ static int osdcmd_god(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
static int osdcmd_maxhealth(osdcmdptr_t parm)
static int osdcmd_maxhealth(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
return OSDCMD_SHOWHELP;
@ -219,7 +219,7 @@ static int osdcmd_maxhealth(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_noclip(osdcmdptr_t UNUSED(parm))
static int osdcmd_noclip(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -235,7 +235,7 @@ static int osdcmd_noclip(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
int osdcmd_restartmap(osdcmdptr_t UNUSED(parm))
int osdcmd_restartmap(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -245,7 +245,7 @@ int osdcmd_restartmap(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
static int osdcmd_spawn(osdcmdptr_t parm)
static int osdcmd_spawn(CCmdFuncPtr parm)
{
int32_t picnum = 0;
uint16_t cstat=0;
@ -339,7 +339,7 @@ static int osdcmd_spawn(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_setvar(osdcmdptr_t parm)
static int osdcmd_setvar(CCmdFuncPtr parm)
{
if (numplayers > 1)
{
@ -369,7 +369,7 @@ static int osdcmd_setvar(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_addlogvar(osdcmdptr_t parm)
static int osdcmd_addlogvar(CCmdFuncPtr parm)
{
if (numplayers > 1)
{
@ -393,7 +393,7 @@ static int osdcmd_addlogvar(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_setactorvar(osdcmdptr_t parm)
static int osdcmd_setactorvar(CCmdFuncPtr parm)
{
if (numplayers > 1)
{
@ -433,7 +433,7 @@ static int osdcmd_setactorvar(osdcmdptr_t parm)
}
static int osdcmd_give(osdcmdptr_t parm)
static int osdcmd_give(CCmdFuncPtr parm)
{
int32_t i;
@ -486,7 +486,7 @@ static int osdcmd_give(osdcmdptr_t parm)
}
static int osdcmd_dumpmapstate(osdfuncparm_t const * const)
static int osdcmd_dumpmapstate(CCmdFuncParm const * const)
{
// this command takes no parameters
@ -495,7 +495,7 @@ static int osdcmd_dumpmapstate(osdfuncparm_t const * const)
return OSDCMD_OK;
}
static int osdcmd_playerinfo(osdfuncparm_t const * const)
static int osdcmd_playerinfo(CCmdFuncParm const * const)
{
Printf("Your player index is %d.\n", myconnectindex);
@ -514,14 +514,14 @@ static int osdcmd_playerinfo(osdfuncparm_t const * const)
return OSDCMD_OK;
}
static int osdcmd_disconnect(osdcmdptr_t UNUSED(parm))
static int osdcmd_disconnect(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
g_netDisconnect = 1;
return OSDCMD_OK;
}
static int osdcmd_connect(osdcmdptr_t parm)
static int osdcmd_connect(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
return OSDCMD_SHOWHELP;
@ -531,7 +531,7 @@ static int osdcmd_connect(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_password(osdcmdptr_t parm)
static int osdcmd_password(CCmdFuncPtr parm)
{
if (parm->numparms < 1)
{
@ -543,11 +543,11 @@ static int osdcmd_password(osdcmdptr_t parm)
return OSDCMD_OK;
}
int osdcmd_listplayers(osdcmdptr_t parm);
int osdcmd_listplayers(CCmdFuncPtr parm);
static int osdcmd_printtimes(osdcmdptr_t UNUSED(parm))
static int osdcmd_printtimes(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -618,43 +618,43 @@ static int osdcmd_printtimes(osdcmdptr_t UNUSED(parm))
int32_t registerosdcommands(void)
{
#if !defined NETCODE_DISABLE
OSD_RegisterFunction("connect","connect: connects to a multiplayer game", osdcmd_connect);
OSD_RegisterFunction("disconnect","disconnect: disconnects from the local multiplayer game", osdcmd_disconnect);
OSD_RegisterFunction("dumpmapstates", "Dumps current snapshots to CL/Srv_MapStates.bin", osdcmd_dumpmapstate);
C_RegisterFunction("connect","connect: connects to a multiplayer game", osdcmd_connect);
C_RegisterFunction("disconnect","disconnect: disconnects from the local multiplayer game", osdcmd_disconnect);
C_RegisterFunction("dumpmapstates", "Dumps current snapshots to CL/Srv_MapStates.bin", osdcmd_dumpmapstate);
#if 0
OSD_RegisterFunction("kick","kick <id>: kicks a multiplayer client. See listplayers.", osdcmd_kick);
OSD_RegisterFunction("kickban","kickban <id>: kicks a multiplayer client and prevents them from reconnecting. See listplayers.", osdcmd_kickban);
C_RegisterFunction("kick","kick <id>: kicks a multiplayer client. See listplayers.", osdcmd_kick);
C_RegisterFunction("kickban","kickban <id>: kicks a multiplayer client and prevents them from reconnecting. See listplayers.", osdcmd_kickban);
#endif
OSD_RegisterFunction("listplayers","listplayers: lists currently connected multiplayer clients", osdcmd_listplayers);
OSD_RegisterFunction("password","password: sets multiplayer game password", osdcmd_password);
OSD_RegisterFunction("playerinfo", "Prints information about the current player", osdcmd_playerinfo);
C_RegisterFunction("listplayers","listplayers: lists currently connected multiplayer clients", osdcmd_listplayers);
C_RegisterFunction("password","password: sets multiplayer game password", osdcmd_password);
C_RegisterFunction("playerinfo", "Prints information about the current player", osdcmd_playerinfo);
#endif
OSD_RegisterFunction("map","map <mapname>: loads the given map", osdcmd_map);
C_RegisterFunction("map","map <mapname>: loads the given map", osdcmd_map);
if (!VOLUMEONE)
{
OSD_RegisterFunction("demo","demo <demofile or demonum>: starts the given demo", osdcmd_demo);
C_RegisterFunction("demo","demo <demofile or demonum>: starts the given demo", osdcmd_demo);
}
OSD_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
OSD_RegisterFunction("god","god: toggles god mode", osdcmd_god);
OSD_RegisterFunction("activatecheat","activatecheat <id>: activates a cheat code", osdcmd_activatecheat);
OSD_RegisterFunction("maxhealth", "maxhealth <amount>: sets the player's maximum health", osdcmd_maxhealth);
C_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
C_RegisterFunction("god","god: toggles god mode", osdcmd_god);
C_RegisterFunction("activatecheat","activatecheat <id>: activates a cheat code", osdcmd_activatecheat);
C_RegisterFunction("maxhealth", "maxhealth <amount>: sets the player's maximum health", osdcmd_maxhealth);
OSD_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
C_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
OSD_RegisterFunction("levelwarp","levelwarp <e> <m>: warp to episode 'e' and map 'm'", osdcmd_levelwarp);
C_RegisterFunction("levelwarp","levelwarp <e> <m>: warp to episode 'e' and map 'm'", osdcmd_levelwarp);
OSD_RegisterFunction("printtimes", "printtimes: prints VM timing statistics", osdcmd_printtimes);
C_RegisterFunction("printtimes", "printtimes: prints VM timing statistics", osdcmd_printtimes);
OSD_RegisterFunction("restartmap", "restartmap: restarts the current map", osdcmd_restartmap);
OSD_RegisterFunction("addlogvar","addlogvar <gamevar>: prints the value of a gamevar", osdcmd_addlogvar);
OSD_RegisterFunction("setvar","setvar <gamevar> <value>: sets the value of a gamevar", osdcmd_setvar);
OSD_RegisterFunction("setvarvar","setvarvar <gamevar1> <gamevar2>: sets the value of <gamevar1> to <gamevar2>", osdcmd_setvar);
OSD_RegisterFunction("setactorvar","setactorvar <actor#> <gamevar> <value>: sets the value of <actor#>'s <gamevar> to <value>", osdcmd_setactorvar);
C_RegisterFunction("restartmap", "restartmap: restarts the current map", osdcmd_restartmap);
C_RegisterFunction("addlogvar","addlogvar <gamevar>: prints the value of a gamevar", osdcmd_addlogvar);
C_RegisterFunction("setvar","setvar <gamevar> <value>: sets the value of a gamevar", osdcmd_setvar);
C_RegisterFunction("setvarvar","setvarvar <gamevar1> <gamevar2>: sets the value of <gamevar1> to <gamevar2>", osdcmd_setvar);
C_RegisterFunction("setactorvar","setactorvar <actor#> <gamevar> <value>: sets the value of <actor#>'s <gamevar> to <value>", osdcmd_setactorvar);
OSD_RegisterFunction("spawn","spawn <picnum> [palnum] [cstat] [ang] [x y z]: spawns a sprite with the given properties",osdcmd_spawn);
C_RegisterFunction("spawn","spawn <picnum> [palnum] [cstat] [ang] [x y z]: spawns a sprite with the given properties",osdcmd_spawn);
return 0;
}

View file

@ -1427,7 +1427,7 @@ void DrawClock()
auto pixels = TileFiles.tileMakeWritable(kTile3603);
memset(pixels, -1, 4096);
memset(pixels, TRANSPARENT_INDEX, 4096);
if (lCountDown / 30 != nClockVal)
{
@ -2655,7 +2655,7 @@ void CopyTileToBitmap(short nSrcTile, short nDestTile, int xPos, int yPos)
for (int y = 0; y < srcYSize; y++)
{
uint8_t val = *pSrc;
if (val != 0xFF) {
if (val != TRANSPARENT_INDEX) {
*pDestB = val;
}
@ -2739,7 +2739,7 @@ void InitSpiritHead()
{
for (int y = 0; y < 106; y++)
{
if (*pTile != 255)
if (*pTile != TRANSPARENT_INDEX)
{
pixelval[nPixels] = *(pGold + x * 106 + y);
origx[nPixels] = x - 48;
@ -2782,7 +2782,7 @@ void InitSpiritHead()
nHeadTimeStart = (int)totalclock;
memset(Worktile, -1, WorktileSize);
memset(Worktile, TRANSPARENT_INDEX, WorktileSize);
tileInvalidate(kTileRamsesWorkTile, -1, -1);
nPixelsToShow = 0;
@ -2867,7 +2867,7 @@ int DoSpiritHead()
if (nHeadStage < 2)
{
memset(Worktile, -1, WorktileSize);
memset(Worktile, TRANSPARENT_INDEX, WorktileSize);
}
if (nHeadStage < 2 || nHeadStage != 5)

View file

@ -479,7 +479,7 @@ void menu_DoPlasma()
while (nSmokeOffset < nSmokeBottom)
{
uint8_t al = *ptr3;
if (al != 255 && al != 96) {
if (al != TRANSPARENT_INDEX && al != 96) {
break;
}
@ -496,7 +496,7 @@ void menu_DoPlasma()
while (nSmokeOffset > nSmokeTop)
{
uint8_t al = *ptr3;
if (al != 255 && al != 96) {
if (al != TRANSPARENT_INDEX && al != 96) {
break;
}

View file

@ -31,7 +31,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
BEGIN_PS_NS
static int osdcmd_god(osdcmdptr_t UNUSED(parm))
static int osdcmd_god(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -45,7 +45,7 @@ static int osdcmd_god(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
static int osdcmd_noclip(osdcmdptr_t UNUSED(parm))
static int osdcmd_noclip(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -61,7 +61,7 @@ static int osdcmd_noclip(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
static int osdcmd_map(osdcmdptr_t parm)
static int osdcmd_map(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
{
@ -88,7 +88,7 @@ static int osdcmd_map(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_changelevel(osdcmdptr_t parm)
static int osdcmd_changelevel(CCmdFuncPtr parm)
{
char* p;
@ -124,23 +124,23 @@ static int osdcmd_changelevel(osdcmdptr_t parm)
int32_t registerosdcommands(void)
{
//if (VOLUMEONE)
OSD_RegisterFunction("changelevel","changelevel <level>: warps to the given level", osdcmd_changelevel);
OSD_RegisterFunction("map","map <mapname>: loads the given map", osdcmd_map);
// OSD_RegisterFunction("demo","demo <demofile or demonum>: starts the given demo", osdcmd_demo);
C_RegisterFunction("changelevel","changelevel <level>: warps to the given level", osdcmd_changelevel);
C_RegisterFunction("map","map <mapname>: loads the given map", osdcmd_map);
// C_RegisterFunction("demo","demo <demofile or demonum>: starts the given demo", osdcmd_demo);
//}
//OSD_RegisterFunction("cmenu","cmenu <#>: jumps to menu", osdcmd_cmenu);
//C_RegisterFunction("cmenu","cmenu <#>: jumps to menu", osdcmd_cmenu);
//OSD_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
OSD_RegisterFunction("god","god: toggles god mode", osdcmd_god);
//OSD_RegisterFunction("activatecheat","activatecheat <id>: activates a cheat code", osdcmd_activatecheat);
//C_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
C_RegisterFunction("god","god: toggles god mode", osdcmd_god);
//C_RegisterFunction("activatecheat","activatecheat <id>: activates a cheat code", osdcmd_activatecheat);
OSD_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
//OSD_RegisterFunction("restartmap", "restartmap: restarts the current map", osdcmd_restartmap);
//OSD_RegisterFunction("restartsound","restartsound: reinitializes the sound system",osdcmd_restartsound);
C_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
//C_RegisterFunction("restartmap", "restartmap: restarts the current map", osdcmd_restartmap);
//C_RegisterFunction("restartsound","restartsound: reinitializes the sound system",osdcmd_restartsound);
//OSD_RegisterFunction("spawn","spawn <picnum> [palnum] [cstat] [ang] [x y z]: spawns a sprite with the given properties",osdcmd_spawn);
//C_RegisterFunction("spawn","spawn <picnum> [palnum] [cstat] [ang] [x y z]: spawns a sprite with the given properties",osdcmd_spawn);
return 0;
}

View file

@ -78,7 +78,7 @@
#include "gameconfigfile.h"
#include "v_font.h"
#include "i_system.h"
#include "textures/bitmap.h"
#include "bitmap.h"
#include "cmdlib.h"
extern bool batchrun;

View file

@ -3711,7 +3711,7 @@ void Net_PrintLag(FString& output)
}
}
int osdcmd_listplayers(osdcmdptr_t parm)
int osdcmd_listplayers(CCmdFuncPtr parm)
{
ENetPeer* currentPeer;
char ipaddr[32];
@ -3743,7 +3743,7 @@ int osdcmd_listplayers(osdcmdptr_t parm)
}
#if 0
static int osdcmd_kick(osdcmdptr_t parm)
static int osdcmd_kick(CCmdFuncPtr parm)
{
ENetPeer* currentPeer;
uint32_t hexaddr;
@ -3781,7 +3781,7 @@ static int osdcmd_kick(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_kickban(osdcmdptr_t parm)
static int osdcmd_kickban(CCmdFuncPtr parm)
{
ENetPeer* currentPeer;
uint32_t hexaddr;

View file

@ -36,7 +36,7 @@ BEGIN_RR_NS
struct osdcmd_cheatsinfo osdcmd_cheatsinfo_stat = { -1, 0, 0 };
static int osdcmd_levelwarp(osdcmdptr_t parm)
static int osdcmd_levelwarp(CCmdFuncPtr parm)
{
if (parm->numparms != 2)
return OSDCMD_SHOWHELP;
@ -69,7 +69,7 @@ static int osdcmd_levelwarp(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_map(osdcmdptr_t parm)
static int osdcmd_map(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
{
@ -147,7 +147,7 @@ foundone:
// the variance of the run times MUST be taken into account (that is, the
// replaying must be performed multiple times for the old and new versions,
// etc.)
static int osdcmd_demo(osdcmdptr_t parm)
static int osdcmd_demo(CCmdFuncPtr parm)
{
if (numplayers > 1)
{
@ -174,7 +174,7 @@ static int osdcmd_demo(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_activatecheat(osdcmdptr_t parm)
static int osdcmd_activatecheat(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
return OSDCMD_SHOWHELP;
@ -187,7 +187,7 @@ static int osdcmd_activatecheat(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_god(osdcmdptr_t UNUSED(parm))
static int osdcmd_god(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
if (numplayers == 1 && g_player[myconnectindex].ps->gm & MODE_GAME)
@ -198,7 +198,7 @@ static int osdcmd_god(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
static int osdcmd_noclip(osdcmdptr_t UNUSED(parm))
static int osdcmd_noclip(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -214,7 +214,7 @@ static int osdcmd_noclip(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
int osdcmd_restartmap(osdcmdptr_t UNUSED(parm))
int osdcmd_restartmap(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -224,7 +224,7 @@ int osdcmd_restartmap(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
static int osdcmd_spawn(osdcmdptr_t parm)
static int osdcmd_spawn(CCmdFuncPtr parm)
{
int32_t picnum = 0;
uint16_t cstat=0;
@ -319,7 +319,7 @@ static int osdcmd_spawn(osdcmdptr_t parm)
}
static int osdcmd_give(osdcmdptr_t parm)
static int osdcmd_give(CCmdFuncPtr parm)
{
int32_t i;
@ -372,7 +372,7 @@ static int osdcmd_give(osdcmdptr_t parm)
}
#if !defined NETCODE_DISABLE
static int osdcmd_disconnect(osdcmdptr_t UNUSED(parm))
static int osdcmd_disconnect(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
// NUKE-TODO:
@ -381,7 +381,7 @@ static int osdcmd_disconnect(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
static int osdcmd_connect(osdcmdptr_t parm)
static int osdcmd_connect(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
return OSDCMD_SHOWHELP;
@ -391,7 +391,7 @@ static int osdcmd_connect(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_password(osdcmdptr_t parm)
static int osdcmd_password(CCmdFuncPtr parm)
{
if (parm->numparms < 1)
{
@ -403,10 +403,10 @@ static int osdcmd_password(osdcmdptr_t parm)
return OSDCMD_OK;
}
int osdcmd_listplayers(osdcmdptr_t parm);
int osdcmd_listplayers(CCmdFuncPtr parm);
#endif
static int osdcmd_printtimes(osdcmdptr_t UNUSED(parm))
static int osdcmd_printtimes(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -450,44 +450,44 @@ static int osdcmd_printtimes(osdcmdptr_t UNUSED(parm))
int32_t registerosdcommands(void)
{
OSD_RegisterFunction("map","map <mapname>: loads the given map", osdcmd_map);
C_RegisterFunction("map","map <mapname>: loads the given map", osdcmd_map);
if (!VOLUMEONE)
{
OSD_RegisterFunction("demo","demo <demofile or demonum>: starts the given demo", osdcmd_demo);
C_RegisterFunction("demo","demo <demofile or demonum>: starts the given demo", osdcmd_demo);
}
OSD_RegisterFunction("levelwarp","levelwarp <e> <m>: warp to episode 'e' and map 'm'", osdcmd_levelwarp);
C_RegisterFunction("levelwarp","levelwarp <e> <m>: warp to episode 'e' and map 'm'", osdcmd_levelwarp);
#if !defined NETCODE_DISABLE
OSD_RegisterFunction("connect","connect: connects to a multiplayer game", osdcmd_connect);
OSD_RegisterFunction("disconnect","disconnect: disconnects from the local multiplayer game", osdcmd_disconnect);
C_RegisterFunction("connect","connect: connects to a multiplayer game", osdcmd_connect);
C_RegisterFunction("disconnect","disconnect: disconnects from the local multiplayer game", osdcmd_disconnect);
#endif
OSD_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
OSD_RegisterFunction("god","god: toggles god mode", osdcmd_god);
OSD_RegisterFunction("activatecheat","activatecheat <id>: activates a cheat code", osdcmd_activatecheat);
C_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
C_RegisterFunction("god","god: toggles god mode", osdcmd_god);
C_RegisterFunction("activatecheat","activatecheat <id>: activates a cheat code", osdcmd_activatecheat);
#ifdef DEBUGGINGAIDS
OSD_RegisterFunction("inittimer","debug", osdcmd_inittimer);
C_RegisterFunction("inittimer","debug", osdcmd_inittimer);
#endif
#if !defined NETCODE_DISABLE
#if 0
OSD_RegisterFunction("kick","kick <id>: kicks a multiplayer client. See listplayers.", osdcmd_kick);
OSD_RegisterFunction("kickban","kickban <id>: kicks a multiplayer client and prevents them from reconnecting. See listplayers.", osdcmd_kickban);
C_RegisterFunction("kick","kick <id>: kicks a multiplayer client. See listplayers.", osdcmd_kick);
C_RegisterFunction("kickban","kickban <id>: kicks a multiplayer client and prevents them from reconnecting. See listplayers.", osdcmd_kickban);
#endif
OSD_RegisterFunction("listplayers","listplayers: lists currently connected multiplayer clients", osdcmd_listplayers);
C_RegisterFunction("listplayers","listplayers: lists currently connected multiplayer clients", osdcmd_listplayers);
#endif
OSD_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
C_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
#if !defined NETCODE_DISABLE
OSD_RegisterFunction("password","password: sets multiplayer game password", osdcmd_password);
C_RegisterFunction("password","password: sets multiplayer game password", osdcmd_password);
#endif
OSD_RegisterFunction("printtimes", "printtimes: prints VM timing statistics", osdcmd_printtimes);
C_RegisterFunction("printtimes", "printtimes: prints VM timing statistics", osdcmd_printtimes);
OSD_RegisterFunction("restartmap", "restartmap: restarts the current map", osdcmd_restartmap);
C_RegisterFunction("restartmap", "restartmap: restarts the current map", osdcmd_restartmap);
OSD_RegisterFunction("spawn","spawn <picnum> [palnum] [cstat] [ang] [x y z]: spawns a sprite with the given properties",osdcmd_spawn);
C_RegisterFunction("spawn","spawn <picnum> [palnum] [cstat] [ang] [x y z]: spawns a sprite with the given properties",osdcmd_spawn);
return 0;
}

View file

@ -1450,7 +1450,7 @@ static void prelevel(char g)
if (sector[i].ceilingstat&1)
{
if (tilePtr(sector[i].ceilingpicnum) == 0)
if (tilePtr(sector[i].ceilingpicnum) == nullptr)
{
if (sector[i].ceilingpicnum == LA)
for (bsize_t j = 0; j < 5; j++)

View file

@ -5243,7 +5243,7 @@ void G_Thunder(void)
if ((gotpic[RRTILE2577>>3]&(1<<(RRTILE2577&7))))
{
gotpic[RRTILE2577>>3] &= ~(1<<(RRTILE2577&7));
if (tilePtr(RRTILE2577) != 0) // why does this on texture load state???
if (tilePtr(RRTILE2577) != nullptr) // why does this on texture load state???
{
g_visibility = 256;
if (krand2() > 65000)
@ -5276,7 +5276,7 @@ void G_Thunder(void)
if ((gotpic[RRTILE2562>>3]&(1<<(RRTILE2562&7))))
{
gotpic[RRTILE2562>>3] &= ~(1<<(RRTILE2562&7));
if (tilePtr(RRTILE2562) != 0) // why does this on texture load state???
if (tilePtr(RRTILE2562) != nullptr) // why does this on texture load state???
{
if (krand2() > 65000)
{

View file

@ -53,7 +53,7 @@ char boardfilename[BMAX_PATH] = {0};
struct osdcmd_cheatsinfo osdcmd_cheatsinfo_stat = { -1, 0, 0 };
static int osdcmd_map(osdcmdptr_t parm)
static int osdcmd_map(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
{
@ -81,7 +81,7 @@ static int osdcmd_map(osdcmdptr_t parm)
}
static int osdcmd_activatecheat(osdcmdptr_t parm)
static int osdcmd_activatecheat(CCmdFuncPtr parm)
{
if (parm->numparms != 1)
return OSDCMD_SHOWHELP;
@ -93,7 +93,7 @@ static int osdcmd_activatecheat(osdcmdptr_t parm)
return OSDCMD_OK;
}
static int osdcmd_god(osdcmdptr_t UNUSED(parm))
static int osdcmd_god(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -102,7 +102,7 @@ static int osdcmd_god(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
static int osdcmd_noclip(osdcmdptr_t UNUSED(parm))
static int osdcmd_noclip(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -111,7 +111,7 @@ static int osdcmd_noclip(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
int osdcmd_restartmap(osdcmdptr_t UNUSED(parm))
int osdcmd_restartmap(CCmdFuncPtr UNUSED(parm))
{
UNREFERENCED_CONST_PARAMETER(parm);
@ -120,7 +120,7 @@ int osdcmd_restartmap(osdcmdptr_t UNUSED(parm))
return OSDCMD_OK;
}
int osdcmd_levelwarp(osdcmdptr_t parm)
int osdcmd_levelwarp(CCmdFuncPtr parm)
{
if (parm->numparms != 1) return OSDCMD_SHOWHELP;
@ -134,7 +134,7 @@ int osdcmd_levelwarp(osdcmdptr_t parm)
}
#if 0
static int osdcmd_spawn(osdcmdptr_t parm)
static int osdcmd_spawn(CCmdFuncPtr parm)
{
int32_t picnum = 0;
uint16_t cstat=0;
@ -229,7 +229,7 @@ static int osdcmd_spawn(osdcmdptr_t parm)
}
#endif
static int osdcmd_give(osdcmdptr_t parm)
static int osdcmd_give(CCmdFuncPtr parm)
{
int32_t i;
@ -275,18 +275,18 @@ static int osdcmd_give(osdcmdptr_t parm)
int32_t registerosdcommands(void)
{
OSD_RegisterFunction("map","map <mapfile>: loads the given map", osdcmd_map);
OSD_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
OSD_RegisterFunction("god","god: toggles god mode", osdcmd_god);
OSD_RegisterFunction("activatecheat","activatecheat <string>: activates a classic cheat code", osdcmd_activatecheat);
C_RegisterFunction("map","map <mapfile>: loads the given map", osdcmd_map);
C_RegisterFunction("give","give <all|health|weapons|ammo|armor|keys|inventory>: gives requested item", osdcmd_give);
C_RegisterFunction("god","god: toggles god mode", osdcmd_god);
C_RegisterFunction("activatecheat","activatecheat <string>: activates a classic cheat code", osdcmd_activatecheat);
OSD_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
C_RegisterFunction("noclip","noclip: toggles clipping mode", osdcmd_noclip);
OSD_RegisterFunction("levelwarp", "levelwarp <num>: warp to level", osdcmd_levelwarp);
C_RegisterFunction("levelwarp", "levelwarp <num>: warp to level", osdcmd_levelwarp);
OSD_RegisterFunction("restartmap", "restartmap: restarts the current map", osdcmd_restartmap);
C_RegisterFunction("restartmap", "restartmap: restarts the current map", osdcmd_restartmap);
// OSD_RegisterFunction("spawn","spawn <picnum> [palnum] [cstat] [ang] [x y z]: spawns a sprite with the given properties",osdcmd_spawn);
// C_RegisterFunction("spawn","spawn <picnum> [palnum] [cstat] [ang] [x y z]: spawns a sprite with the given properties",osdcmd_spawn);
return 0;
}

View file

@ -35,7 +35,7 @@ LAlt "+Strafe"
RAlt "+Strafe"
LShift "+Run"
RShift "+Run"
Capslock "toggle autorun 85"
Capslock "togglemsg autorun 85"
PgUp "+Look_Up"
PgDn "+Look_Down"
Home "+Aim_Up"

View file

@ -784,7 +784,7 @@ OptionMenu "ActionControlsMenu"// protected
StaticText ""
Control "$CNTRLMNU_RUN" , "+run"
Control "$CNTRLMNU_TOGGLERUN" , "toggle cl_autorun"
Control "$CNTRLMNU_TOGGLERUN" , "toggle autorun"
Control "$CNTRLMNU_STRAFE" , "+strafe"
StaticText ""

757
wadsrc/static/x11r6rgb.txt Normal file
View file

@ -0,0 +1,757 @@
! $XConsortium: rgb.txt,v 10.41 94/02/20 18:39:36 rws Exp $
255 250 250 snow
248 248 255 ghost white
248 248 255 GhostWhite
245 245 245 white smoke
245 245 245 WhiteSmoke
220 220 220 gainsboro
255 250 240 floral white
255 250 240 FloralWhite
253 245 230 old lace
253 245 230 OldLace
250 240 230 linen
250 235 215 antique white
250 235 215 AntiqueWhite
255 239 213 papaya whip
255 239 213 PapayaWhip
255 235 205 blanched almond
255 235 205 BlanchedAlmond
255 228 196 bisque
255 218 185 peach puff
255 218 185 PeachPuff
255 222 173 navajo white
255 222 173 NavajoWhite
255 228 181 moccasin
255 248 220 cornsilk
255 255 240 ivory
255 250 205 lemon chiffon
255 250 205 LemonChiffon
255 245 238 seashell
240 255 240 honeydew
245 255 250 mint cream
245 255 250 MintCream
240 255 255 azure
240 248 255 alice blue
240 248 255 AliceBlue
230 230 250 lavender
255 240 245 lavender blush
255 240 245 LavenderBlush
255 228 225 misty rose
255 228 225 MistyRose
255 255 255 white
0 0 0 black
47 79 79 dark slate gray
47 79 79 DarkSlateGray
47 79 79 dark slate grey
47 79 79 DarkSlateGrey
105 105 105 dim gray
105 105 105 DimGray
105 105 105 dim grey
105 105 105 DimGrey
112 128 144 slate gray
112 128 144 SlateGray
112 128 144 slate grey
112 128 144 SlateGrey
119 136 153 light slate gray
119 136 153 LightSlateGray
119 136 153 light slate grey
119 136 153 LightSlateGrey
190 190 190 gray
190 190 190 grey
211 211 211 light grey
211 211 211 LightGrey
211 211 211 light gray
211 211 211 LightGray
25 25 112 midnight blue
25 25 112 MidnightBlue
0 0 128 navy
0 0 128 navy blue
0 0 128 NavyBlue
100 149 237 cornflower blue
100 149 237 CornflowerBlue
72 61 139 dark slate blue
72 61 139 DarkSlateBlue
106 90 205 slate blue
106 90 205 SlateBlue
123 104 238 medium slate blue
123 104 238 MediumSlateBlue
132 112 255 light slate blue
132 112 255 LightSlateBlue
0 0 205 medium blue
0 0 205 MediumBlue
65 105 225 royal blue
65 105 225 RoyalBlue
0 0 255 blue
30 144 255 dodger blue
30 144 255 DodgerBlue
0 191 255 deep sky blue
0 191 255 DeepSkyBlue
135 206 235 sky blue
135 206 235 SkyBlue
135 206 250 light sky blue
135 206 250 LightSkyBlue
70 130 180 steel blue
70 130 180 SteelBlue
176 196 222 light steel blue
176 196 222 LightSteelBlue
173 216 230 light blue
173 216 230 LightBlue
176 224 230 powder blue
176 224 230 PowderBlue
175 238 238 pale turquoise
175 238 238 PaleTurquoise
0 206 209 dark turquoise
0 206 209 DarkTurquoise
72 209 204 medium turquoise
72 209 204 MediumTurquoise
64 224 208 turquoise
0 255 255 cyan
224 255 255 light cyan
224 255 255 LightCyan
95 158 160 cadet blue
95 158 160 CadetBlue
102 205 170 medium aquamarine
102 205 170 MediumAquamarine
127 255 212 aquamarine
0 100 0 dark green
0 100 0 DarkGreen
85 107 47 dark olive green
85 107 47 DarkOliveGreen
143 188 143 dark sea green
143 188 143 DarkSeaGreen
46 139 87 sea green
46 139 87 SeaGreen
60 179 113 medium sea green
60 179 113 MediumSeaGreen
32 178 170 light sea green
32 178 170 LightSeaGreen
152 251 152 pale green
152 251 152 PaleGreen
0 255 127 spring green
0 255 127 SpringGreen
124 252 0 lawn green
124 252 0 LawnGreen
0 255 0 green
127 255 0 chartreuse
0 250 154 medium spring green
0 250 154 MediumSpringGreen
173 255 47 green yellow
173 255 47 GreenYellow
50 205 50 lime green
50 205 50 LimeGreen
154 205 50 yellow green
154 205 50 YellowGreen
34 139 34 forest green
34 139 34 ForestGreen
107 142 35 olive drab
107 142 35 OliveDrab
189 183 107 dark khaki
189 183 107 DarkKhaki
240 230 140 khaki
238 232 170 pale goldenrod
238 232 170 PaleGoldenrod
250 250 210 light goldenrod yellow
250 250 210 LightGoldenrodYellow
255 255 224 light yellow
255 255 224 LightYellow
255 255 0 yellow
255 215 0 gold
238 221 130 light goldenrod
238 221 130 LightGoldenrod
218 165 32 goldenrod
184 134 11 dark goldenrod
184 134 11 DarkGoldenrod
188 143 143 rosy brown
188 143 143 RosyBrown
205 92 92 indian red
205 92 92 IndianRed
139 69 19 saddle brown
139 69 19 SaddleBrown
160 82 45 sienna
205 133 63 peru
222 184 135 burlywood
245 245 220 beige
245 222 179 wheat
244 164 96 sandy brown
244 164 96 SandyBrown
210 180 140 tan
210 105 30 chocolate
178 34 34 firebrick
165 42 42 brown
233 150 122 dark salmon
233 150 122 DarkSalmon
250 128 114 salmon
255 160 122 light salmon
255 160 122 LightSalmon
255 165 0 orange
255 140 0 dark orange
255 140 0 DarkOrange
255 127 80 coral
240 128 128 light coral
240 128 128 LightCoral
255 99 71 tomato
255 69 0 orange red
255 69 0 OrangeRed
255 0 0 red
255 105 180 hot pink
255 105 180 HotPink
255 20 147 deep pink
255 20 147 DeepPink
255 192 203 pink
255 182 193 light pink
255 182 193 LightPink
219 112 147 pale violet red
219 112 147 PaleVioletRed
176 48 96 maroon
199 21 133 medium violet red
199 21 133 MediumVioletRed
208 32 144 violet red
208 32 144 VioletRed
255 0 255 magenta
238 130 238 violet
221 160 221 plum
218 112 214 orchid
186 85 211 medium orchid
186 85 211 MediumOrchid
153 50 204 dark orchid
153 50 204 DarkOrchid
148 0 211 dark violet
148 0 211 DarkViolet
138 43 226 blue violet
138 43 226 BlueViolet
160 32 240 purple
147 112 219 medium purple
147 112 219 MediumPurple
216 191 216 thistle
255 250 250 snow1
238 233 233 snow2
205 201 201 snow3
139 137 137 snow4
255 245 238 seashell1
238 229 222 seashell2
205 197 191 seashell3
139 134 130 seashell4
255 239 219 AntiqueWhite1
238 223 204 AntiqueWhite2
205 192 176 AntiqueWhite3
139 131 120 AntiqueWhite4
255 228 196 bisque1
238 213 183 bisque2
205 183 158 bisque3
139 125 107 bisque4
255 218 185 PeachPuff1
238 203 173 PeachPuff2
205 175 149 PeachPuff3
139 119 101 PeachPuff4
255 222 173 NavajoWhite1
238 207 161 NavajoWhite2
205 179 139 NavajoWhite3
139 121 94 NavajoWhite4
255 250 205 LemonChiffon1
238 233 191 LemonChiffon2
205 201 165 LemonChiffon3
139 137 112 LemonChiffon4
255 248 220 cornsilk1
238 232 205 cornsilk2
205 200 177 cornsilk3
139 136 120 cornsilk4
255 255 240 ivory1
238 238 224 ivory2
205 205 193 ivory3
139 139 131 ivory4
240 255 240 honeydew1
224 238 224 honeydew2
193 205 193 honeydew3
131 139 131 honeydew4
255 240 245 LavenderBlush1
238 224 229 LavenderBlush2
205 193 197 LavenderBlush3
139 131 134 LavenderBlush4
255 228 225 MistyRose1
238 213 210 MistyRose2
205 183 181 MistyRose3
139 125 123 MistyRose4
240 255 255 azure1
224 238 238 azure2
193 205 205 azure3
131 139 139 azure4
131 111 255 SlateBlue1
122 103 238 SlateBlue2
105 89 205 SlateBlue3
71 60 139 SlateBlue4
72 118 255 RoyalBlue1
67 110 238 RoyalBlue2
58 95 205 RoyalBlue3
39 64 139 RoyalBlue4
0 0 255 blue1
0 0 238 blue2
0 0 205 blue3
0 0 139 blue4
30 144 255 DodgerBlue1
28 134 238 DodgerBlue2
24 116 205 DodgerBlue3
16 78 139 DodgerBlue4
99 184 255 SteelBlue1
92 172 238 SteelBlue2
79 148 205 SteelBlue3
54 100 139 SteelBlue4
0 191 255 DeepSkyBlue1
0 178 238 DeepSkyBlue2
0 154 205 DeepSkyBlue3
0 104 139 DeepSkyBlue4
135 206 255 SkyBlue1
126 192 238 SkyBlue2
108 166 205 SkyBlue3
74 112 139 SkyBlue4
176 226 255 LightSkyBlue1
164 211 238 LightSkyBlue2
141 182 205 LightSkyBlue3
96 123 139 LightSkyBlue4
198 226 255 SlateGray1
185 211 238 SlateGray2
159 182 205 SlateGray3
108 123 139 SlateGray4
202 225 255 LightSteelBlue1
188 210 238 LightSteelBlue2
162 181 205 LightSteelBlue3
110 123 139 LightSteelBlue4
191 239 255 LightBlue1
178 223 238 LightBlue2
154 192 205 LightBlue3
104 131 139 LightBlue4
224 255 255 LightCyan1
209 238 238 LightCyan2
180 205 205 LightCyan3
122 139 139 LightCyan4
187 255 255 PaleTurquoise1
174 238 238 PaleTurquoise2
150 205 205 PaleTurquoise3
102 139 139 PaleTurquoise4
152 245 255 CadetBlue1
142 229 238 CadetBlue2
122 197 205 CadetBlue3
83 134 139 CadetBlue4
0 245 255 turquoise1
0 229 238 turquoise2
0 197 205 turquoise3
0 134 139 turquoise4
0 255 255 cyan1
0 238 238 cyan2
0 205 205 cyan3
0 139 139 cyan4
151 255 255 DarkSlateGray1
141 238 238 DarkSlateGray2
121 205 205 DarkSlateGray3
82 139 139 DarkSlateGray4
127 255 212 aquamarine1
118 238 198 aquamarine2
102 205 170 aquamarine3
69 139 116 aquamarine4
193 255 193 DarkSeaGreen1
180 238 180 DarkSeaGreen2
155 205 155 DarkSeaGreen3
105 139 105 DarkSeaGreen4
84 255 159 SeaGreen1
78 238 148 SeaGreen2
67 205 128 SeaGreen3
46 139 87 SeaGreen4
154 255 154 PaleGreen1
144 238 144 PaleGreen2
124 205 124 PaleGreen3
84 139 84 PaleGreen4
0 255 127 SpringGreen1
0 238 118 SpringGreen2
0 205 102 SpringGreen3
0 139 69 SpringGreen4
0 255 0 green1
0 238 0 green2
0 205 0 green3
0 139 0 green4
127 255 0 chartreuse1
118 238 0 chartreuse2
102 205 0 chartreuse3
69 139 0 chartreuse4
192 255 62 OliveDrab1
179 238 58 OliveDrab2
154 205 50 OliveDrab3
105 139 34 OliveDrab4
202 255 112 DarkOliveGreen1
188 238 104 DarkOliveGreen2
162 205 90 DarkOliveGreen3
110 139 61 DarkOliveGreen4
255 246 143 khaki1
238 230 133 khaki2
205 198 115 khaki3
139 134 78 khaki4
255 236 139 LightGoldenrod1
238 220 130 LightGoldenrod2
205 190 112 LightGoldenrod3
139 129 76 LightGoldenrod4
255 255 224 LightYellow1
238 238 209 LightYellow2
205 205 180 LightYellow3
139 139 122 LightYellow4
255 255 0 yellow1
238 238 0 yellow2
205 205 0 yellow3
139 139 0 yellow4
255 215 0 gold1
238 201 0 gold2
205 173 0 gold3
139 117 0 gold4
255 193 37 goldenrod1
238 180 34 goldenrod2
205 155 29 goldenrod3
139 105 20 goldenrod4
255 185 15 DarkGoldenrod1
238 173 14 DarkGoldenrod2
205 149 12 DarkGoldenrod3
139 101 8 DarkGoldenrod4
255 193 193 RosyBrown1
238 180 180 RosyBrown2
205 155 155 RosyBrown3
139 105 105 RosyBrown4
255 106 106 IndianRed1
238 99 99 IndianRed2
205 85 85 IndianRed3
139 58 58 IndianRed4
255 130 71 sienna1
238 121 66 sienna2
205 104 57 sienna3
139 71 38 sienna4
255 211 155 burlywood1
238 197 145 burlywood2
205 170 125 burlywood3
139 115 85 burlywood4
255 231 186 wheat1
238 216 174 wheat2
205 186 150 wheat3
139 126 102 wheat4
255 165 79 tan1
238 154 73 tan2
205 133 63 tan3
139 90 43 tan4
255 127 36 chocolate1
238 118 33 chocolate2
205 102 29 chocolate3
139 69 19 chocolate4
255 48 48 firebrick1
238 44 44 firebrick2
205 38 38 firebrick3
139 26 26 firebrick4
255 64 64 brown1
238 59 59 brown2
205 51 51 brown3
139 35 35 brown4
255 140 105 salmon1
238 130 98 salmon2
205 112 84 salmon3
139 76 57 salmon4
255 160 122 LightSalmon1
238 149 114 LightSalmon2
205 129 98 LightSalmon3
139 87 66 LightSalmon4
255 165 0 orange1
238 154 0 orange2
205 133 0 orange3
139 90 0 orange4
255 127 0 DarkOrange1
238 118 0 DarkOrange2
205 102 0 DarkOrange3
139 69 0 DarkOrange4
255 114 86 coral1
238 106 80 coral2
205 91 69 coral3
139 62 47 coral4
255 99 71 tomato1
238 92 66 tomato2
205 79 57 tomato3
139 54 38 tomato4
255 69 0 OrangeRed1
238 64 0 OrangeRed2
205 55 0 OrangeRed3
139 37 0 OrangeRed4
255 0 0 red1
238 0 0 red2
205 0 0 red3
139 0 0 red4
255 20 147 DeepPink1
238 18 137 DeepPink2
205 16 118 DeepPink3
139 10 80 DeepPink4
255 110 180 HotPink1
238 106 167 HotPink2
205 96 144 HotPink3
139 58 98 HotPink4
255 181 197 pink1
238 169 184 pink2
205 145 158 pink3
139 99 108 pink4
255 174 185 LightPink1
238 162 173 LightPink2
205 140 149 LightPink3
139 95 101 LightPink4
255 130 171 PaleVioletRed1
238 121 159 PaleVioletRed2
205 104 137 PaleVioletRed3
139 71 93 PaleVioletRed4
255 52 179 maroon1
238 48 167 maroon2
205 41 144 maroon3
139 28 98 maroon4
255 62 150 VioletRed1
238 58 140 VioletRed2
205 50 120 VioletRed3
139 34 82 VioletRed4
255 0 255 magenta1
238 0 238 magenta2
205 0 205 magenta3
139 0 139 magenta4
255 131 250 orchid1
238 122 233 orchid2
205 105 201 orchid3
139 71 137 orchid4
255 187 255 plum1
238 174 238 plum2
205 150 205 plum3
139 102 139 plum4
224 102 255 MediumOrchid1
209 95 238 MediumOrchid2
180 82 205 MediumOrchid3
122 55 139 MediumOrchid4
191 62 255 DarkOrchid1
178 58 238 DarkOrchid2
154 50 205 DarkOrchid3
104 34 139 DarkOrchid4
155 48 255 purple1
145 44 238 purple2
125 38 205 purple3
85 26 139 purple4
171 130 255 MediumPurple1
159 121 238 MediumPurple2
137 104 205 MediumPurple3
93 71 139 MediumPurple4
255 225 255 thistle1
238 210 238 thistle2
205 181 205 thistle3
139 123 139 thistle4
0 0 0 gray0
0 0 0 grey0
3 3 3 gray1
3 3 3 grey1
5 5 5 gray2
5 5 5 grey2
8 8 8 gray3
8 8 8 grey3
10 10 10 gray4
10 10 10 grey4
13 13 13 gray5
13 13 13 grey5
15 15 15 gray6
15 15 15 grey6
18 18 18 gray7
18 18 18 grey7
20 20 20 gray8
20 20 20 grey8
23 23 23 gray9
23 23 23 grey9
26 26 26 gray10
26 26 26 grey10
28 28 28 gray11
28 28 28 grey11
31 31 31 gray12
31 31 31 grey12
33 33 33 gray13
33 33 33 grey13
36 36 36 gray14
36 36 36 grey14
38 38 38 gray15
38 38 38 grey15
41 41 41 gray16
41 41 41 grey16
43 43 43 gray17
43 43 43 grey17
46 46 46 gray18
46 46 46 grey18
48 48 48 gray19
48 48 48 grey19
51 51 51 gray20
51 51 51 grey20
54 54 54 gray21
54 54 54 grey21
56 56 56 gray22
56 56 56 grey22
59 59 59 gray23
59 59 59 grey23
61 61 61 gray24
61 61 61 grey24
64 64 64 gray25
64 64 64 grey25
66 66 66 gray26
66 66 66 grey26
69 69 69 gray27
69 69 69 grey27
71 71 71 gray28
71 71 71 grey28
74 74 74 gray29
74 74 74 grey29
77 77 77 gray30
77 77 77 grey30
79 79 79 gray31
79 79 79 grey31
82 82 82 gray32
82 82 82 grey32
84 84 84 gray33
84 84 84 grey33
87 87 87 gray34
87 87 87 grey34
89 89 89 gray35
89 89 89 grey35
92 92 92 gray36
92 92 92 grey36
94 94 94 gray37
94 94 94 grey37
97 97 97 gray38
97 97 97 grey38
99 99 99 gray39
99 99 99 grey39
102 102 102 gray40
102 102 102 grey40
105 105 105 gray41
105 105 105 grey41
107 107 107 gray42
107 107 107 grey42
110 110 110 gray43
110 110 110 grey43
112 112 112 gray44
112 112 112 grey44
115 115 115 gray45
115 115 115 grey45
117 117 117 gray46
117 117 117 grey46
120 120 120 gray47
120 120 120 grey47
122 122 122 gray48
122 122 122 grey48
125 125 125 gray49
125 125 125 grey49
127 127 127 gray50
127 127 127 grey50
130 130 130 gray51
130 130 130 grey51
133 133 133 gray52
133 133 133 grey52
135 135 135 gray53
135 135 135 grey53
138 138 138 gray54
138 138 138 grey54
140 140 140 gray55
140 140 140 grey55
143 143 143 gray56
143 143 143 grey56
145 145 145 gray57
145 145 145 grey57
148 148 148 gray58
148 148 148 grey58
150 150 150 gray59
150 150 150 grey59
153 153 153 gray60
153 153 153 grey60
156 156 156 gray61
156 156 156 grey61
158 158 158 gray62
158 158 158 grey62
161 161 161 gray63
161 161 161 grey63
163 163 163 gray64
163 163 163 grey64
166 166 166 gray65
166 166 166 grey65
168 168 168 gray66
168 168 168 grey66
171 171 171 gray67
171 171 171 grey67
173 173 173 gray68
173 173 173 grey68
176 176 176 gray69
176 176 176 grey69
179 179 179 gray70
179 179 179 grey70
181 181 181 gray71
181 181 181 grey71
184 184 184 gray72
184 184 184 grey72
186 186 186 gray73
186 186 186 grey73
189 189 189 gray74
189 189 189 grey74
191 191 191 gray75
191 191 191 grey75
194 194 194 gray76
194 194 194 grey76
196 196 196 gray77
196 196 196 grey77
199 199 199 gray78
199 199 199 grey78
201 201 201 gray79
201 201 201 grey79
204 204 204 gray80
204 204 204 grey80
207 207 207 gray81
207 207 207 grey81
209 209 209 gray82
209 209 209 grey82
212 212 212 gray83
212 212 212 grey83
214 214 214 gray84
214 214 214 grey84
217 217 217 gray85
217 217 217 grey85
219 219 219 gray86
219 219 219 grey86
222 222 222 gray87
222 222 222 grey87
224 224 224 gray88
224 224 224 grey88
227 227 227 gray89
227 227 227 grey89
229 229 229 gray90
229 229 229 grey90
232 232 232 gray91
232 232 232 grey91
235 235 235 gray92
235 235 235 grey92
237 237 237 gray93
237 237 237 grey93
240 240 240 gray94
240 240 240 grey94
242 242 242 gray95
242 242 242 grey95
245 245 245 gray96
245 245 245 grey96
247 247 247 gray97
247 247 247 grey97
250 250 250 gray98
250 250 250 grey98
252 252 252 gray99
252 252 252 grey99
255 255 255 gray100
255 255 255 grey100
169 169 169 dark grey
169 169 169 DarkGrey
169 169 169 dark gray
169 169 169 DarkGray
0 0 139 dark blue
0 0 139 DarkBlue
0 139 139 dark cyan
0 139 139 DarkCyan
139 0 139 dark magenta
139 0 139 DarkMagenta
139 0 0 dark red
139 0 0 DarkRed
144 238 144 light green
144 238 144 LightGreen