mirror of
https://github.com/DrBeef/Raze.git
synced 2024-11-15 08:52:00 +00:00
- added ZDoom's keybinding class and some needed support code.
Not hooked up yet with the game.
This commit is contained in:
parent
12a02cb456
commit
73e64ff0b2
11 changed files with 1809 additions and 0 deletions
|
@ -782,7 +782,11 @@ set (PCH_SOURCES
|
||||||
common/fonts/fontchars.cpp
|
common/fonts/fontchars.cpp
|
||||||
|
|
||||||
common/console/c_cvars.cpp
|
common/console/c_cvars.cpp
|
||||||
|
common/console/c_bind.cpp
|
||||||
|
common/console/c_commandline.cpp
|
||||||
|
common/console/d_event.cpp
|
||||||
|
|
||||||
|
common/utility/i_time.cpp
|
||||||
common/utility/name.cpp
|
common/utility/name.cpp
|
||||||
common/utility/cmdlib.cpp
|
common/utility/cmdlib.cpp
|
||||||
common/utility/m_argv.cpp
|
common/utility/m_argv.cpp
|
||||||
|
|
792
source/common/console/c_bind.cpp
Normal file
792
source/common/console/c_bind.cpp
Normal file
|
@ -0,0 +1,792 @@
|
||||||
|
/*
|
||||||
|
** c_bind.cpp
|
||||||
|
** Functions for using and maintaining key bindings
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** 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 <stdint.h>
|
||||||
|
|
||||||
|
//#include "doomtype.h"
|
||||||
|
#include "keydef.h"
|
||||||
|
#include "c_commandline.h"
|
||||||
|
#include "c_bind.h"
|
||||||
|
//#include "g_level.h"
|
||||||
|
//#include "hu_stuff.h"
|
||||||
|
#include "configfile.h"
|
||||||
|
//#include "d_event.h"
|
||||||
|
#include "filesystem.h"
|
||||||
|
#include "templates.h"
|
||||||
|
#include "i_time.h"
|
||||||
|
//#include "menu/menu.h"
|
||||||
|
#include "printf.h"
|
||||||
|
#include "v_text.h"
|
||||||
|
#include "d_event.h"
|
||||||
|
|
||||||
|
|
||||||
|
const char *KeyNames[NUM_KEYS] =
|
||||||
|
{
|
||||||
|
// This array is dependant on the particular keyboard input
|
||||||
|
// codes generated in i_input.c. If they change there, they
|
||||||
|
// also need to change here. In this case, we use the
|
||||||
|
// DirectInput codes and assume a qwerty keyboard layout.
|
||||||
|
// See <dinput.h> for the DIK_* codes
|
||||||
|
|
||||||
|
nullptr, "Escape", "1", "2", "3", "4", "5", "6", //00
|
||||||
|
"7", "8", "9", "0", "-", "=", "Backspace","Tab", //08
|
||||||
|
"Q", "W", "E", "R", "T", "Y", "U", "I", //10
|
||||||
|
"O", "P", "[", "]", "Enter", "Ctrl", "A", "S", //18
|
||||||
|
"D", "F", "G", "H", "J", "K", "L", ";", //20
|
||||||
|
"'", "`", "Shift", "\\", "Z", "X", "C", "V", //28
|
||||||
|
"B", "N", "M", ",", ".", "/", "RShift", "KP*", //30
|
||||||
|
"Alt", "Space", "CapsLock", "F1", "F2", "F3", "F4", "F5", //38
|
||||||
|
"F6", "F7", "F8", "F9", "F10", "NumLock", "Scroll", "KP7", //40
|
||||||
|
"KP8", "KP9", "KP-", "KP4", "KP5", "KP6", "KP+", "KP1", //48
|
||||||
|
"KP2", "KP3", "KP0", "KP.", nullptr, nullptr, "OEM102", "F11", //50
|
||||||
|
"F12", nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, //58
|
||||||
|
nullptr, nullptr, nullptr, nullptr, "F13", "F14", "F15", "F16", //60
|
||||||
|
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, //68
|
||||||
|
"Kana", nullptr, nullptr, "Abnt_C1", nullptr, nullptr, nullptr, nullptr, //70
|
||||||
|
nullptr, "Convert", nullptr, "NoConvert",nullptr, "Yen", "Abnt_C2", nullptr, //78
|
||||||
|
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, //80
|
||||||
|
nullptr, nullptr, nullptr, nullptr, nullptr, "KP=", nullptr, nullptr, //88
|
||||||
|
"Circumflex","@", ":", "_", "Kanji", "Stop", "Ax", "Unlabeled",//90
|
||||||
|
nullptr, "PrevTrack",nullptr, nullptr, "KP-Enter", "RCtrl", nullptr, nullptr, //98
|
||||||
|
"Mute", "Calculator","Play", nullptr, "Stop", nullptr, nullptr, nullptr, //A0
|
||||||
|
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, "VolDown", nullptr, //A8
|
||||||
|
"VolUp", nullptr, "WebHome", "KP,", nullptr, "KP/", nullptr, "SysRq", //B0
|
||||||
|
"RAlt", nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, //B8
|
||||||
|
nullptr, nullptr, nullptr, nullptr, nullptr, "Pause", nullptr, "Home", //C0
|
||||||
|
"UpArrow", "PgUp", nullptr, "LeftArrow",nullptr, "RightArrow",nullptr, "End", //C8
|
||||||
|
"DownArrow","PgDn", "Ins", "Del", nullptr, nullptr, nullptr, nullptr, //D0
|
||||||
|
#ifdef __APPLE__
|
||||||
|
nullptr, nullptr, nullptr, "Command", nullptr, "Apps", "Power", "Sleep", //D8
|
||||||
|
#else // !__APPLE__
|
||||||
|
nullptr, nullptr, nullptr, "LWin", "RWin", "Apps", "Power", "Sleep", //D8
|
||||||
|
#endif // __APPLE__
|
||||||
|
nullptr, nullptr, nullptr, "Wake", nullptr, "Search", "Favorites","Refresh", //E0
|
||||||
|
"WebStop", "WebForward","WebBack", "MyComputer","Mail", "MediaSelect",nullptr, nullptr, //E8
|
||||||
|
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, //F0
|
||||||
|
nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, nullptr, //F8
|
||||||
|
|
||||||
|
// non-keyboard buttons that can be bound
|
||||||
|
"Mouse1", "Mouse2", "Mouse3", "Mouse4", // 8 mouse buttons
|
||||||
|
"Mouse5", "Mouse6", "Mouse7", "Mouse8",
|
||||||
|
|
||||||
|
"Joy1", "Joy2", "Joy3", "Joy4", // 128 joystick buttons!
|
||||||
|
"Joy5", "Joy6", "Joy7", "Joy8",
|
||||||
|
"Joy9", "Joy10", "Joy11", "Joy12",
|
||||||
|
"Joy13", "Joy14", "Joy15", "Joy16",
|
||||||
|
"Joy17", "Joy18", "Joy19", "Joy20",
|
||||||
|
"Joy21", "Joy22", "Joy23", "Joy24",
|
||||||
|
"Joy25", "Joy26", "Joy27", "Joy28",
|
||||||
|
"Joy29", "Joy30", "Joy31", "Joy32",
|
||||||
|
"Joy33", "Joy34", "Joy35", "Joy36",
|
||||||
|
"Joy37", "Joy38", "Joy39", "Joy40",
|
||||||
|
"Joy41", "Joy42", "Joy43", "Joy44",
|
||||||
|
"Joy45", "Joy46", "Joy47", "Joy48",
|
||||||
|
"Joy49", "Joy50", "Joy51", "Joy52",
|
||||||
|
"Joy53", "Joy54", "Joy55", "Joy56",
|
||||||
|
"Joy57", "Joy58", "Joy59", "Joy60",
|
||||||
|
"Joy61", "Joy62", "Joy63", "Joy64",
|
||||||
|
"Joy65", "Joy66", "Joy67", "Joy68",
|
||||||
|
"Joy69", "Joy70", "Joy71", "Joy72",
|
||||||
|
"Joy73", "Joy74", "Joy75", "Joy76",
|
||||||
|
"Joy77", "Joy78", "Joy79", "Joy80",
|
||||||
|
"Joy81", "Joy82", "Joy83", "Joy84",
|
||||||
|
"Joy85", "Joy86", "Joy87", "Joy88",
|
||||||
|
"Joy89", "Joy90", "Joy91", "Joy92",
|
||||||
|
"Joy93", "Joy94", "Joy95", "Joy96",
|
||||||
|
"Joy97", "Joy98", "Joy99", "Joy100",
|
||||||
|
"Joy101", "Joy102", "Joy103", "Joy104",
|
||||||
|
"Joy105", "Joy106", "Joy107", "Joy108",
|
||||||
|
"Joy109", "Joy110", "Joy111", "Joy112",
|
||||||
|
"Joy113", "Joy114", "Joy115", "Joy116",
|
||||||
|
"Joy117", "Joy118", "Joy119", "Joy120",
|
||||||
|
"Joy121", "Joy122", "Joy123", "Joy124",
|
||||||
|
"Joy125", "Joy126", "Joy127", "Joy128",
|
||||||
|
|
||||||
|
"POV1Up", "POV1Right","POV1Down", "POV1Left", // First POV hat
|
||||||
|
"POV2Up", "POV2Right","POV2Down", "POV2Left", // Second POV hat
|
||||||
|
"POV3Up", "POV3Right","POV3Down", "POV3Left", // Third POV hat
|
||||||
|
"POV4Up", "POV4Right","POV4Down", "POV4Left", // Fourth POV hat
|
||||||
|
|
||||||
|
"MWheelUp", "MWheelDown", // the mouse wheel
|
||||||
|
"MWheelRight", "MWheelLeft",
|
||||||
|
|
||||||
|
"Axis1Plus","Axis1Minus","Axis2Plus","Axis2Minus", // joystick axes as buttons
|
||||||
|
"Axis3Plus","Axis3Minus","Axis4Plus","Axis4Minus",
|
||||||
|
"Axis5Plus","Axis5Minus","Axis6Plus","Axis6Minus",
|
||||||
|
"Axis7Plus","Axis7Minus","Axis8Plus","Axis8Minus",
|
||||||
|
|
||||||
|
"LStickRight","LStickLeft","LStickDown","LStickUp", // Gamepad axis-based buttons
|
||||||
|
"RStickRight","RStickLeft","RStickDown","RStickUp",
|
||||||
|
|
||||||
|
"DPadUp","DPadDown","DPadLeft","DPadRight", // Gamepad buttons
|
||||||
|
"Pad_Start","Pad_Back","LThumb","RThumb",
|
||||||
|
"LShoulder","RShoulder","LTrigger","RTrigger",
|
||||||
|
"Pad_A", "Pad_B", "Pad_X", "Pad_Y"
|
||||||
|
};
|
||||||
|
|
||||||
|
FKeyBindings Bindings;
|
||||||
|
FKeyBindings DoubleBindings;
|
||||||
|
FKeyBindings AutomapBindings; // this is currently not in use but may be added later.
|
||||||
|
|
||||||
|
static unsigned int DClickTime[NUM_KEYS];
|
||||||
|
static FixedBitArray<NUM_KEYS> DClicked;
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
static int GetKeyFromName (const char *name)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
// Names of the form #xxx are translated to key xxx automatically
|
||||||
|
if (name[0] == '#' && name[1] != 0)
|
||||||
|
{
|
||||||
|
return atoi (name + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Otherwise, we scan the KeyNames[] array for a matching name
|
||||||
|
for (i = 0; i < NUM_KEYS; i++)
|
||||||
|
{
|
||||||
|
if (KeyNames[i] && !stricmp (KeyNames[i], name))
|
||||||
|
return i;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
static int GetConfigKeyFromName (const char *key)
|
||||||
|
{
|
||||||
|
int keynum = GetKeyFromName(key);
|
||||||
|
if (keynum == 0)
|
||||||
|
{
|
||||||
|
if (stricmp (key, "LeftBracket") == 0)
|
||||||
|
{
|
||||||
|
keynum = GetKeyFromName ("[");
|
||||||
|
}
|
||||||
|
else if (stricmp (key, "RightBracket") == 0)
|
||||||
|
{
|
||||||
|
keynum = GetKeyFromName ("]");
|
||||||
|
}
|
||||||
|
else if (stricmp (key, "Equals") == 0)
|
||||||
|
{
|
||||||
|
keynum = GetKeyFromName ("=");
|
||||||
|
}
|
||||||
|
else if (stricmp (key, "KP-Equals") == 0)
|
||||||
|
{
|
||||||
|
keynum = GetKeyFromName ("kp=");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return keynum;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
static const char *KeyName (int key)
|
||||||
|
{
|
||||||
|
static char name[5];
|
||||||
|
|
||||||
|
if (KeyNames[key])
|
||||||
|
return KeyNames[key];
|
||||||
|
|
||||||
|
snprintf (name, countof(name), "Key_%d", key);
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
static const char *ConfigKeyName(int keynum)
|
||||||
|
{
|
||||||
|
const char *name = KeyName(keynum);
|
||||||
|
if (name[1] == 0) // Make sure given name is config-safe
|
||||||
|
{
|
||||||
|
if (name[0] == '[')
|
||||||
|
return "LeftBracket";
|
||||||
|
else if (name[0] == ']')
|
||||||
|
return "RightBracket";
|
||||||
|
else if (name[0] == '=')
|
||||||
|
return "Equals";
|
||||||
|
else if (strcmp (name, "kp=") == 0)
|
||||||
|
return "KP-Equals";
|
||||||
|
}
|
||||||
|
return name;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void C_NameKeys (char *str, int first, int second)
|
||||||
|
{
|
||||||
|
int c = 0;
|
||||||
|
|
||||||
|
*str = 0;
|
||||||
|
if (second == first) second = 0;
|
||||||
|
if (first)
|
||||||
|
{
|
||||||
|
c++;
|
||||||
|
strcpy (str, KeyName (first));
|
||||||
|
if (second)
|
||||||
|
strcat (str, TEXTCOLOR_BLACK ", " TEXTCOLOR_NORMAL);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (second)
|
||||||
|
{
|
||||||
|
c++;
|
||||||
|
strcat (str, KeyName (second));
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!c)
|
||||||
|
*str = '\0';
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
FString C_NameKeys (int *keys, int count)
|
||||||
|
{
|
||||||
|
FString result;
|
||||||
|
for (int i = 0; i < count; i++)
|
||||||
|
{
|
||||||
|
int key = keys[i];
|
||||||
|
if (key == 0) continue;
|
||||||
|
for (int j = 0; j < count; j++)
|
||||||
|
{
|
||||||
|
if (key == keys[j])
|
||||||
|
{
|
||||||
|
key = 0;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (key == 0) continue;
|
||||||
|
if (result.IsNotEmpty()) result += TEXTCOLOR_BLACK ", " TEXTCOLOR_NORMAL;
|
||||||
|
result += KeyName(key);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void FKeyBindings::DoBind (const char *key, const char *bind)
|
||||||
|
{
|
||||||
|
int keynum = GetConfigKeyFromName (key);
|
||||||
|
if (keynum != 0)
|
||||||
|
{
|
||||||
|
Binds[keynum] = bind;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void FKeyBindings::UnbindAll ()
|
||||||
|
{
|
||||||
|
for (int i = 0; i < NUM_KEYS; ++i)
|
||||||
|
{
|
||||||
|
Binds[i] = "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void FKeyBindings::UnbindKey(const char *key)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
if ( (i = GetKeyFromName (key)) )
|
||||||
|
{
|
||||||
|
Binds[i] = "";
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Printf ("Unknown key \"%s\"\n", key);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void FKeyBindings::PerformBind(FCommandLine &argv, const char *msg)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
if (argv.argc() > 1)
|
||||||
|
{
|
||||||
|
i = GetKeyFromName (argv[1]);
|
||||||
|
if (!i)
|
||||||
|
{
|
||||||
|
Printf ("Unknown key \"%s\"\n", argv[1]);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (argv.argc() == 2)
|
||||||
|
{
|
||||||
|
Printf ("\"%s\" = \"%s\"\n", argv[1], Binds[i].GetChars());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Binds[i] = argv[2];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Printf ("%s:\n", msg);
|
||||||
|
|
||||||
|
for (i = 0; i < NUM_KEYS; i++)
|
||||||
|
{
|
||||||
|
if (!Binds[i].IsEmpty())
|
||||||
|
Printf ("%s \"%s\"\n", KeyName (i), Binds[i].GetChars());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
// 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
|
||||||
|
// 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
|
||||||
|
// 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
|
||||||
|
// happens to the entry in the config.
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void FKeyBindings::ArchiveBindings(FConfigFile *f, const char *matchcmd)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = 0; i < NUM_KEYS; i++)
|
||||||
|
{
|
||||||
|
if (Binds[i].IsEmpty())
|
||||||
|
{
|
||||||
|
if (matchcmd == nullptr)
|
||||||
|
{
|
||||||
|
f->ClearKey(ConfigKeyName(i));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (matchcmd == nullptr || stricmp(Binds[i], matchcmd) == 0)
|
||||||
|
{
|
||||||
|
if (Binds[i][0] == '\1')
|
||||||
|
{
|
||||||
|
Binds[i] = "";
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
f->SetValueForKey(ConfigKeyName(i), Binds[i]);
|
||||||
|
if (matchcmd != nullptr)
|
||||||
|
{ // If saving a specific command, set a marker so that
|
||||||
|
// it does not get saved in the general binding list.
|
||||||
|
Binds[i] = "\1";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
TArray<int> FKeyBindings::GetKeysForCommand (const char *cmd)
|
||||||
|
{
|
||||||
|
int i = 0;
|
||||||
|
TArray<int> result;
|
||||||
|
|
||||||
|
while (i < NUM_KEYS)
|
||||||
|
{
|
||||||
|
if (stricmp (cmd, Binds[i]) == 0)
|
||||||
|
{
|
||||||
|
result.Push(i);
|
||||||
|
}
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void FKeyBindings::UnbindACommand (const char *str)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
|
||||||
|
for (i = 0; i < NUM_KEYS; i++)
|
||||||
|
{
|
||||||
|
if (!stricmp (str, Binds[i]))
|
||||||
|
{
|
||||||
|
Binds[i] = "";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void FKeyBindings::DefaultBind(const char *keyname, const char *cmd)
|
||||||
|
{
|
||||||
|
int key = GetKeyFromName (keyname);
|
||||||
|
if (key == 0)
|
||||||
|
{
|
||||||
|
Printf ("Unknown key \"%s\"\n", keyname);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!Binds[key].IsEmpty())
|
||||||
|
{ // This key is already bound.
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
for (int i = 0; i < NUM_KEYS; ++i)
|
||||||
|
{
|
||||||
|
if (!Binds[i].IsEmpty() && stricmp (Binds[i], cmd) == 0)
|
||||||
|
{ // This command is already bound to a key.
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// It is safe to do the bind, so do it.
|
||||||
|
Binds[key] = cmd;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void C_UnbindAll ()
|
||||||
|
{
|
||||||
|
Bindings.UnbindAll();
|
||||||
|
DoubleBindings.UnbindAll();
|
||||||
|
AutomapBindings.UnbindAll();
|
||||||
|
}
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
CCMD (unbindall)
|
||||||
|
{
|
||||||
|
C_UnbindAll ();
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
CCMD (unbind)
|
||||||
|
{
|
||||||
|
if (argv.argc() > 1)
|
||||||
|
{
|
||||||
|
Bindings.UnbindKey(argv[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
CCMD (undoublebind)
|
||||||
|
{
|
||||||
|
if (argv.argc() > 1)
|
||||||
|
{
|
||||||
|
DoubleBindings.UnbindKey(argv[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
CCMD (unmapbind)
|
||||||
|
{
|
||||||
|
if (argv.argc() > 1)
|
||||||
|
{
|
||||||
|
AutomapBindings.UnbindKey(argv[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
CCMD (bind)
|
||||||
|
{
|
||||||
|
Bindings.PerformBind(argv, "Current key bindings");
|
||||||
|
}
|
||||||
|
|
||||||
|
CCMD (doublebind)
|
||||||
|
{
|
||||||
|
DoubleBindings.PerformBind(argv, "Current key doublebindings");
|
||||||
|
}
|
||||||
|
|
||||||
|
CCMD (mapbind)
|
||||||
|
{
|
||||||
|
AutomapBindings.PerformBind(argv, "Current automap key bindings");
|
||||||
|
}
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// CCMD defaultbind
|
||||||
|
//
|
||||||
|
// Binds a command to a key if that key is not already bound and if
|
||||||
|
// that command is not already bound to another key.
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
CCMD (defaultbind)
|
||||||
|
{
|
||||||
|
if (argv.argc() < 3)
|
||||||
|
{
|
||||||
|
Printf ("Usage: defaultbind <key> <command>\n");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Bindings.DefaultBind(argv[1], argv[2]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
CCMD (rebind)
|
||||||
|
{
|
||||||
|
FKeyBindings *bindings;
|
||||||
|
|
||||||
|
if (key == 0)
|
||||||
|
{
|
||||||
|
Printf ("Rebind cannot be used from the console\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (key & KEY_DBLCLICKED)
|
||||||
|
{
|
||||||
|
bindings = &DoubleBindings;
|
||||||
|
key &= KEY_DBLCLICKED-1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
bindings = &Bindings;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (argv.argc() > 1)
|
||||||
|
{
|
||||||
|
bindings->SetBind(key, argv[1]);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void C_BindDefaults ()
|
||||||
|
{
|
||||||
|
#if 0
|
||||||
|
int lump, lastlump = 0;
|
||||||
|
|
||||||
|
while ((lump = Wads.FindLump("DEFBINDS", &lastlump)) != -1)
|
||||||
|
{
|
||||||
|
FScanner sc(lump);
|
||||||
|
|
||||||
|
while (sc.GetString())
|
||||||
|
{
|
||||||
|
FKeyBindings *dest = &Bindings;
|
||||||
|
int key;
|
||||||
|
|
||||||
|
// bind destination is optional and is the same as the console command
|
||||||
|
if (sc.Compare("bind"))
|
||||||
|
{
|
||||||
|
sc.MustGetString();
|
||||||
|
}
|
||||||
|
else if (sc.Compare("doublebind"))
|
||||||
|
{
|
||||||
|
dest = &DoubleBindings;
|
||||||
|
sc.MustGetString();
|
||||||
|
}
|
||||||
|
else if (sc.Compare("mapbind"))
|
||||||
|
{
|
||||||
|
dest = &AutomapBindings;
|
||||||
|
sc.MustGetString();
|
||||||
|
}
|
||||||
|
key = GetConfigKeyFromName(sc.String);
|
||||||
|
sc.MustGetString();
|
||||||
|
dest->SetBind(key, sc.String);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
CCMD(binddefaults)
|
||||||
|
{
|
||||||
|
C_BindDefaults ();
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
void C_SetDefaultBindings ()
|
||||||
|
{
|
||||||
|
C_UnbindAll ();
|
||||||
|
C_BindDefaults ();
|
||||||
|
}
|
||||||
|
|
||||||
|
void AddCommandString (const char *copy, int keynum);
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
bool C_DoKey (event_t *ev, FKeyBindings *binds, FKeyBindings *doublebinds)
|
||||||
|
{
|
||||||
|
FString binding;
|
||||||
|
bool dclick;
|
||||||
|
unsigned int nowtime;
|
||||||
|
|
||||||
|
if (ev->type != EV_KeyDown && ev->type != EV_KeyUp)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if ((unsigned int)ev->data1 >= NUM_KEYS)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
dclick = false;
|
||||||
|
|
||||||
|
nowtime = (unsigned)I_msTime();
|
||||||
|
if (doublebinds != nullptr && int(DClickTime[ev->data1] - nowtime) > 0 && ev->type == EV_KeyDown)
|
||||||
|
{
|
||||||
|
// Key pressed for a double click
|
||||||
|
binding = doublebinds->GetBinding(ev->data1);
|
||||||
|
DClicked.Set(ev->data1);
|
||||||
|
dclick = true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (ev->type == EV_KeyDown)
|
||||||
|
{ // Key pressed for a normal press
|
||||||
|
binding = binds->GetBinding(ev->data1);
|
||||||
|
DClickTime[ev->data1] = nowtime + 571;
|
||||||
|
}
|
||||||
|
else if (doublebinds != nullptr && DClicked[ev->data1])
|
||||||
|
{ // Key released from a double click
|
||||||
|
binding = doublebinds->GetBinding(ev->data1);
|
||||||
|
DClicked.Clear(ev->data1);
|
||||||
|
DClickTime[ev->data1] = 0;
|
||||||
|
dclick = true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{ // Key released from a normal press
|
||||||
|
binding = binds->GetBinding(ev->data1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
if (binding.IsEmpty())
|
||||||
|
{
|
||||||
|
binding = binds->GetBinding(ev->data1);
|
||||||
|
dclick = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!binding.IsEmpty())// && (chatmodeon == 0 || ev->data1 < 256))
|
||||||
|
{
|
||||||
|
if (ev->type == EV_KeyUp && binding[0] != '+')
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
char *copy = binding.LockBuffer();
|
||||||
|
|
||||||
|
if (ev->type == EV_KeyUp)
|
||||||
|
{
|
||||||
|
copy[0] = '-';
|
||||||
|
}
|
||||||
|
|
||||||
|
AddCommandString (copy, dclick ? ev->data1 | KEY_DBLCLICKED : ev->data1);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
#include "osd.h"
|
||||||
|
void AddCommandString(const char* copy, int keynum)
|
||||||
|
{
|
||||||
|
if (*copy == '+')
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
else if (*copy == '-')
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
else OSD_Dispatch(copy);
|
||||||
|
}
|
109
source/common/console/c_bind.h
Normal file
109
source/common/console/c_bind.h
Normal file
|
@ -0,0 +1,109 @@
|
||||||
|
/*
|
||||||
|
** c_bind.h
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** 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.
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
**
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __C_BINDINGS_H__
|
||||||
|
#define __C_BINDINGS_H__
|
||||||
|
|
||||||
|
#include "keydef.h"
|
||||||
|
#include "zstring.h"
|
||||||
|
#include "tarray.h"
|
||||||
|
|
||||||
|
struct event_t;
|
||||||
|
class FConfigFile;
|
||||||
|
class FCommandLine;
|
||||||
|
|
||||||
|
void C_NameKeys (char *str, int first, int second);
|
||||||
|
FString C_NameKeys (int *keys, int count);
|
||||||
|
|
||||||
|
class FKeyBindings
|
||||||
|
{
|
||||||
|
FString Binds[NUM_KEYS];
|
||||||
|
|
||||||
|
public:
|
||||||
|
void PerformBind(FCommandLine &argv, const char *msg);
|
||||||
|
bool DoKey(event_t *ev);
|
||||||
|
void ArchiveBindings(FConfigFile *F, const char *matchcmd = NULL);
|
||||||
|
TArray<int> GetKeysForCommand (const char *cmd);
|
||||||
|
void UnbindACommand (const char *str);
|
||||||
|
void UnbindAll ();
|
||||||
|
void UnbindKey(const char *key);
|
||||||
|
void DoBind (const char *key, const char *bind);
|
||||||
|
void DefaultBind(const char *keyname, const char *cmd);
|
||||||
|
|
||||||
|
void SetBind(unsigned int key, const char *bind)
|
||||||
|
{
|
||||||
|
if (key < NUM_KEYS) Binds[key] = bind;
|
||||||
|
}
|
||||||
|
|
||||||
|
const FString &GetBinding(unsigned int index) const
|
||||||
|
{
|
||||||
|
return Binds[index];
|
||||||
|
}
|
||||||
|
|
||||||
|
const char *GetBind(unsigned int index) const
|
||||||
|
{
|
||||||
|
if (index < NUM_KEYS) return Binds[index].GetChars();
|
||||||
|
else return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
extern FKeyBindings Bindings;
|
||||||
|
extern FKeyBindings DoubleBindings;
|
||||||
|
extern FKeyBindings AutomapBindings;
|
||||||
|
extern FKeyBindings MenuBindings;
|
||||||
|
|
||||||
|
|
||||||
|
bool C_DoKey (event_t *ev, FKeyBindings *binds, FKeyBindings *doublebinds);
|
||||||
|
|
||||||
|
// Stuff used by the customize controls menu
|
||||||
|
void C_SetDefaultBindings ();
|
||||||
|
void C_UnbindAll ();
|
||||||
|
|
||||||
|
extern const char *KeyNames[];
|
||||||
|
|
||||||
|
struct FKeyAction
|
||||||
|
{
|
||||||
|
FString mTitle;
|
||||||
|
FString mAction;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct FKeySection
|
||||||
|
{
|
||||||
|
FString mTitle;
|
||||||
|
FString mSection;
|
||||||
|
TArray<FKeyAction> mActions;
|
||||||
|
};
|
||||||
|
extern TArray<FKeySection> KeySections;
|
||||||
|
|
||||||
|
#endif //__C_BINDINGS_H__
|
204
source/common/console/c_commandline.cpp
Normal file
204
source/common/console/c_commandline.cpp
Normal file
|
@ -0,0 +1,204 @@
|
||||||
|
/*
|
||||||
|
** c_dispatch.cpp
|
||||||
|
** Functions for executing console commands and aliases
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** Copyright 1998-2007 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.
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
**
|
||||||
|
*/
|
||||||
|
|
||||||
|
// HEADER FILES ------------------------------------------------------------
|
||||||
|
|
||||||
|
#include <stdlib.h>
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
#include <ctype.h>
|
||||||
|
|
||||||
|
#include "c_commandline.h"
|
||||||
|
#include "c_cvars.h"
|
||||||
|
#include "v_text.h"
|
||||||
|
|
||||||
|
// ParseCommandLine
|
||||||
|
//
|
||||||
|
// Parse a command line (passed in args). If argc is non-NULL, it will
|
||||||
|
// be set to the number of arguments. If argv is non-NULL, it will be
|
||||||
|
// filled with pointers to each argument; argv[0] should be initialized
|
||||||
|
// to point to a buffer large enough to hold all the arguments. The
|
||||||
|
// return value is the necessary size of this buffer.
|
||||||
|
//
|
||||||
|
// Special processing:
|
||||||
|
// Inside quoted strings, \" becomes just "
|
||||||
|
// \\ becomes just a single backslash
|
||||||
|
// \c becomes just TEXTCOLOR_ESCAPE
|
||||||
|
// $<cvar> is replaced by the contents of <cvar>
|
||||||
|
|
||||||
|
static long ParseCommandLine(const char* args, int* argc, char** argv, bool no_escapes)
|
||||||
|
{
|
||||||
|
int count;
|
||||||
|
char* buffplace;
|
||||||
|
|
||||||
|
count = 0;
|
||||||
|
buffplace = NULL;
|
||||||
|
if (argv != NULL)
|
||||||
|
{
|
||||||
|
buffplace = argv[0];
|
||||||
|
}
|
||||||
|
|
||||||
|
for (;;)
|
||||||
|
{
|
||||||
|
while (*args <= ' ' && *args)
|
||||||
|
{ // skip white space
|
||||||
|
args++;
|
||||||
|
}
|
||||||
|
if (*args == 0)
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
else if (*args == '\"')
|
||||||
|
{ // read quoted string
|
||||||
|
char stuff;
|
||||||
|
if (argv != NULL)
|
||||||
|
{
|
||||||
|
argv[count] = buffplace;
|
||||||
|
}
|
||||||
|
count++;
|
||||||
|
args++;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
stuff = *args++;
|
||||||
|
if (!no_escapes && stuff == '\\' && *args == '\"')
|
||||||
|
{
|
||||||
|
stuff = '\"', args++;
|
||||||
|
}
|
||||||
|
else if (!no_escapes && stuff == '\\' && *args == '\\')
|
||||||
|
{
|
||||||
|
args++;
|
||||||
|
}
|
||||||
|
else if (!no_escapes && stuff == '\\' && *args == 'c')
|
||||||
|
{
|
||||||
|
stuff = TEXTCOLOR_ESCAPE, args++;
|
||||||
|
}
|
||||||
|
else if (stuff == '\"')
|
||||||
|
{
|
||||||
|
stuff = 0;
|
||||||
|
}
|
||||||
|
else if (stuff == 0)
|
||||||
|
{
|
||||||
|
args--;
|
||||||
|
}
|
||||||
|
if (argv != NULL)
|
||||||
|
{
|
||||||
|
*buffplace = stuff;
|
||||||
|
}
|
||||||
|
buffplace++;
|
||||||
|
} while (stuff);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{ // read unquoted string
|
||||||
|
const char* start = args++, * end;
|
||||||
|
FBaseCVar* var;
|
||||||
|
UCVarValue val;
|
||||||
|
|
||||||
|
while (*args && *args > ' ' && *args != '\"')
|
||||||
|
args++;
|
||||||
|
if (*start == '$' && (var = FindCVarSub(start + 1, int(args - start - 1))))
|
||||||
|
{
|
||||||
|
val = var->GetGenericRep(CVAR_String);
|
||||||
|
start = val.String;
|
||||||
|
end = start + strlen(start);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
end = args;
|
||||||
|
}
|
||||||
|
if (argv != NULL)
|
||||||
|
{
|
||||||
|
argv[count] = buffplace;
|
||||||
|
while (start < end)
|
||||||
|
*buffplace++ = *start++;
|
||||||
|
*buffplace++ = 0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
buffplace += end - start + 1;
|
||||||
|
}
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (argc != NULL)
|
||||||
|
{
|
||||||
|
*argc = count;
|
||||||
|
}
|
||||||
|
return (long)(buffplace - (char*)0);
|
||||||
|
}
|
||||||
|
|
||||||
|
FCommandLine::FCommandLine (const char *commandline, bool no_escapes)
|
||||||
|
{
|
||||||
|
cmd = commandline;
|
||||||
|
_argc = -1;
|
||||||
|
_argv = NULL;
|
||||||
|
noescapes = no_escapes;
|
||||||
|
}
|
||||||
|
|
||||||
|
FCommandLine::~FCommandLine ()
|
||||||
|
{
|
||||||
|
if (_argv != NULL)
|
||||||
|
{
|
||||||
|
delete[] _argv;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void FCommandLine::Shift()
|
||||||
|
{
|
||||||
|
// Only valid after _argv has been filled.
|
||||||
|
for (int i = 1; i < _argc; ++i)
|
||||||
|
{
|
||||||
|
_argv[i - 1] = _argv[i];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int FCommandLine::argc ()
|
||||||
|
{
|
||||||
|
if (_argc == -1)
|
||||||
|
{
|
||||||
|
argsize = ParseCommandLine (cmd, &_argc, NULL, noescapes);
|
||||||
|
}
|
||||||
|
return _argc;
|
||||||
|
}
|
||||||
|
|
||||||
|
char *FCommandLine::operator[] (int i)
|
||||||
|
{
|
||||||
|
if (_argv == NULL)
|
||||||
|
{
|
||||||
|
int count = argc();
|
||||||
|
_argv = new char *[count + (argsize+sizeof(char*)-1)/sizeof(char*)];
|
||||||
|
_argv[0] = (char *)_argv + count*sizeof(char *);
|
||||||
|
ParseCommandLine (cmd, NULL, _argv, noescapes);
|
||||||
|
}
|
||||||
|
return _argv[i];
|
||||||
|
}
|
60
source/common/console/c_commandline.h
Normal file
60
source/common/console/c_commandline.h
Normal file
|
@ -0,0 +1,60 @@
|
||||||
|
/*
|
||||||
|
** c_dispatch.h
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** 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.
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
**
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __C_DISPATCH_H__
|
||||||
|
#define __C_DISPATCH_H__
|
||||||
|
|
||||||
|
class FConfigFile;
|
||||||
|
|
||||||
|
const int KEY_DBLCLICKED = 0x8000;
|
||||||
|
// Class that can parse command lines
|
||||||
|
class FCommandLine
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
FCommandLine (const char *commandline, bool no_escapes = false);
|
||||||
|
~FCommandLine ();
|
||||||
|
int argc ();
|
||||||
|
char *operator[] (int i);
|
||||||
|
const char *args () { return cmd; }
|
||||||
|
void Shift();
|
||||||
|
|
||||||
|
private:
|
||||||
|
const char *cmd;
|
||||||
|
int _argc;
|
||||||
|
char **_argv;
|
||||||
|
long argsize;
|
||||||
|
bool noescapes;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
#endif //__C_DISPATCH_H__
|
233
source/common/console/d_event.cpp
Normal file
233
source/common/console/d_event.cpp
Normal file
|
@ -0,0 +1,233 @@
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
//
|
||||||
|
// Copyright 1993-1996 id Software
|
||||||
|
// Copyright 1999-2016 Randy Heit
|
||||||
|
// Copyright 2002-2016 Christoph Oelckers
|
||||||
|
//
|
||||||
|
// This program is free software: you can redistribute it and/or modify
|
||||||
|
// it under the terms of the GNU General Public License as published by
|
||||||
|
// the Free Software Foundation, either version 2 of the License, or
|
||||||
|
// (at your option) any later version.
|
||||||
|
//
|
||||||
|
// This program is distributed in the hope that it will be useful,
|
||||||
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
// GNU General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU General Public License
|
||||||
|
// along with this program. If not, see http://www.gnu.org/licenses/
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
#include "c_bind.h"
|
||||||
|
#include "d_event.h"
|
||||||
|
#include "d_gui.h"
|
||||||
|
|
||||||
|
int eventhead;
|
||||||
|
int eventtail;
|
||||||
|
event_t events[MAXEVENTS];
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// G_Responder
|
||||||
|
// Process the event for the game
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
bool G_Responder (event_t *ev)
|
||||||
|
{
|
||||||
|
#if 0
|
||||||
|
// any other key pops up menu if in demos
|
||||||
|
// [RH] But only if the key isn't bound to a "special" command
|
||||||
|
if (gameaction == ga_nothing &&
|
||||||
|
(demoplayback || gamestate == GS_DEMOSCREEN || gamestate == GS_TITLELEVEL))
|
||||||
|
{
|
||||||
|
const char *cmd = Bindings.GetBind (ev->data1);
|
||||||
|
|
||||||
|
if (ev->type == EV_KeyDown)
|
||||||
|
{
|
||||||
|
|
||||||
|
if (!cmd || (
|
||||||
|
strnicmp (cmd, "menu_", 5) &&
|
||||||
|
stricmp (cmd, "toggleconsole") &&
|
||||||
|
stricmp (cmd, "sizeup") &&
|
||||||
|
stricmp (cmd, "sizedown") &&
|
||||||
|
stricmp (cmd, "togglemap") &&
|
||||||
|
stricmp (cmd, "spynext") &&
|
||||||
|
stricmp (cmd, "spyprev") &&
|
||||||
|
stricmp (cmd, "chase") &&
|
||||||
|
stricmp (cmd, "+showscores") &&
|
||||||
|
stricmp (cmd, "bumpgamma") &&
|
||||||
|
stricmp (cmd, "screenshot")))
|
||||||
|
{
|
||||||
|
M_StartControlPanel(true);
|
||||||
|
M_SetMenu(NAME_Mainmenu, -1);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return C_DoKey (ev, &Bindings, &DoubleBindings);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (cmd && cmd[0] == '+')
|
||||||
|
return C_DoKey (ev, &Bindings, &DoubleBindings);
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
if (gamestate == GS_LEVEL)
|
||||||
|
{
|
||||||
|
if (ST_Responder (ev))
|
||||||
|
return true; // status window ate it
|
||||||
|
if (!viewactive && primaryLevel->automap->Responder (ev, false))
|
||||||
|
return true; // automap ate it
|
||||||
|
}
|
||||||
|
else if (gamestate == GS_FINALE)
|
||||||
|
{
|
||||||
|
if (F_Responder (ev))
|
||||||
|
return true; // finale ate the event
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
|
switch (ev->type)
|
||||||
|
{
|
||||||
|
case EV_KeyDown:
|
||||||
|
if (C_DoKey (ev, &Bindings, &DoubleBindings))
|
||||||
|
return true;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case EV_KeyUp:
|
||||||
|
C_DoKey (ev, &Bindings, &DoubleBindings);
|
||||||
|
break;
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
// [RH] mouse buttons are sent as key up/down events
|
||||||
|
case EV_Mouse:
|
||||||
|
mousex = (int)(ev->x * mouse_sensitivity);
|
||||||
|
mousey = (int)(ev->y * mouse_sensitivity);
|
||||||
|
break;
|
||||||
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
|
// [RH] If the view is active, give the automap a chance at
|
||||||
|
// the events *last* so that any bound keys get precedence.
|
||||||
|
|
||||||
|
#if 0
|
||||||
|
if (gamestate == GS_LEVEL && viewactive && primaryLevel->automap)
|
||||||
|
return primaryLevel->automap->Responder (ev, true);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
return (ev->type == EV_KeyDown ||
|
||||||
|
ev->type == EV_Mouse);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// D_ProcessEvents
|
||||||
|
//
|
||||||
|
// Send all the events of the given timestamp down the responder chain.
|
||||||
|
// Events are asynchronous inputs generally generated by the game user.
|
||||||
|
// Events can be discarded if no responder claims them
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
void D_ProcessEvents (void)
|
||||||
|
{
|
||||||
|
event_t *ev;
|
||||||
|
for (; eventtail != eventhead ; eventtail = (eventtail+1)&(MAXEVENTS-1))
|
||||||
|
{
|
||||||
|
ev = &events[eventtail];
|
||||||
|
if (ev->type == EV_None)
|
||||||
|
continue;
|
||||||
|
if (ev->type == EV_DeviceChange)
|
||||||
|
(void)0;//UpdateJoystickMenu(I_UpdateDeviceList());
|
||||||
|
#if 0
|
||||||
|
if (C_Responder (ev))
|
||||||
|
continue; // console ate the event
|
||||||
|
if (M_Responder (ev))
|
||||||
|
continue; // menu ate the event
|
||||||
|
#endif
|
||||||
|
G_Responder (ev);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// D_PostEvent
|
||||||
|
//
|
||||||
|
// Called by the I/O functions when input is detected.
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
void D_PostEvent (const event_t *ev)
|
||||||
|
{
|
||||||
|
// Do not post duplicate consecutive EV_DeviceChange events.
|
||||||
|
if (ev->type == EV_DeviceChange && events[eventhead].type == EV_DeviceChange)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
events[eventhead] = *ev;
|
||||||
|
#if 0
|
||||||
|
if (ev->type == EV_Mouse && menuactive == MENU_Off && ConsoleState != c_down && ConsoleState != c_falling && !primaryLevel->localEventManager->Responder(ev) && !paused)
|
||||||
|
{
|
||||||
|
if (Button_Mlook.bDown || freelook)
|
||||||
|
{
|
||||||
|
int look = int(ev->y * m_pitch * mouse_sensitivity * 16.0);
|
||||||
|
if (invertmouse)
|
||||||
|
look = -look;
|
||||||
|
G_AddViewPitch (look, true);
|
||||||
|
events[eventhead].y = 0;
|
||||||
|
}
|
||||||
|
if (!Button_Strafe.bDown && !lookstrafe)
|
||||||
|
{
|
||||||
|
G_AddViewAngle (int(ev->x * m_yaw * mouse_sensitivity * 8.0), true);
|
||||||
|
events[eventhead].x = 0;
|
||||||
|
}
|
||||||
|
if ((events[eventhead].x | events[eventhead].y) == 0)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
eventhead = (eventhead+1)&(MAXEVENTS-1);
|
||||||
|
}
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// D_RemoveNextCharEvent
|
||||||
|
//
|
||||||
|
// Removes the next EV_GUI_Char event in the input queue. Used by the menu,
|
||||||
|
// since it (generally) consumes EV_GUI_KeyDown events and not EV_GUI_Char
|
||||||
|
// events, and it needs to ensure that there is no left over input when it's
|
||||||
|
// done. If there are multiple EV_GUI_KeyDowns before the EV_GUI_Char, then
|
||||||
|
// there are dead chars involved, so those should be removed, too. We do
|
||||||
|
// this by changing the message type to EV_None rather than by actually
|
||||||
|
// removing the event from the queue.
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
void D_RemoveNextCharEvent()
|
||||||
|
{
|
||||||
|
assert(events[eventtail].type == EV_GUI_Event && events[eventtail].subtype == EV_GUI_KeyDown);
|
||||||
|
for (int evnum = eventtail; evnum != eventhead; evnum = (evnum+1) & (MAXEVENTS-1))
|
||||||
|
{
|
||||||
|
event_t *ev = &events[evnum];
|
||||||
|
if (ev->type != EV_GUI_Event)
|
||||||
|
break;
|
||||||
|
if (ev->subtype == EV_GUI_KeyDown || ev->subtype == EV_GUI_Char)
|
||||||
|
{
|
||||||
|
ev->type = EV_None;
|
||||||
|
if (ev->subtype == EV_GUI_Char)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
72
source/common/console/d_event.h
Normal file
72
source/common/console/d_event.h
Normal file
|
@ -0,0 +1,72 @@
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
//
|
||||||
|
// Copyright 1993-1996 id Software
|
||||||
|
// Copyright 1999-2016 Randy Heit
|
||||||
|
// Copyright 2002-2016 Christoph Oelckers
|
||||||
|
//
|
||||||
|
// This program is free software: you can redistribute it and/or modify
|
||||||
|
// it under the terms of the GNU General Public License as published by
|
||||||
|
// the Free Software Foundation, either version 3 of the License, or
|
||||||
|
// (at your option) any later version.
|
||||||
|
//
|
||||||
|
// This program is distributed in the hope that it will be useful,
|
||||||
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
// GNU General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU General Public License
|
||||||
|
// along with this program. If not, see http://www.gnu.org/licenses/
|
||||||
|
//
|
||||||
|
//-----------------------------------------------------------------------------
|
||||||
|
|
||||||
|
|
||||||
|
#ifndef __D_EVENT_H__
|
||||||
|
#define __D_EVENT_H__
|
||||||
|
|
||||||
|
|
||||||
|
#include <functional>
|
||||||
|
|
||||||
|
|
||||||
|
//
|
||||||
|
// Event handling.
|
||||||
|
//
|
||||||
|
|
||||||
|
// Input event types.
|
||||||
|
enum EGenericEvent
|
||||||
|
{
|
||||||
|
EV_None,
|
||||||
|
EV_KeyDown, // data1: scan code, data2: Qwerty ASCII code
|
||||||
|
EV_KeyUp, // same
|
||||||
|
EV_Mouse, // x, y: mouse movement deltas
|
||||||
|
EV_GUI_Event, // subtype specifies actual event
|
||||||
|
EV_DeviceChange,// a device has been connected or removed
|
||||||
|
};
|
||||||
|
|
||||||
|
// Event structure.
|
||||||
|
struct event_t
|
||||||
|
{
|
||||||
|
uint8_t type;
|
||||||
|
uint8_t subtype;
|
||||||
|
int16_t data1; // keys / mouse/joystick buttons
|
||||||
|
int16_t data2;
|
||||||
|
int16_t data3;
|
||||||
|
int x; // mouse/joystick x move
|
||||||
|
int y; // mouse/joystick y move
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
// Called by IO functions when input is detected.
|
||||||
|
void D_PostEvent (const event_t* ev);
|
||||||
|
void D_RemoveNextCharEvent();
|
||||||
|
|
||||||
|
|
||||||
|
//
|
||||||
|
// GLOBAL VARIABLES
|
||||||
|
//
|
||||||
|
#define MAXEVENTS 128
|
||||||
|
|
||||||
|
extern event_t events[MAXEVENTS];
|
||||||
|
|
||||||
|
|
||||||
|
#endif
|
115
source/common/console/d_gui.h
Normal file
115
source/common/console/d_gui.h
Normal file
|
@ -0,0 +1,115 @@
|
||||||
|
/*
|
||||||
|
** d_gui.h
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** 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.
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
**
|
||||||
|
** So when do I get a real UT-like windowing system?
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef __D_GUI_H__
|
||||||
|
#define __D_GUI_H__
|
||||||
|
|
||||||
|
// For a GUIEvent, x and y specify absolute location of mouse pointer
|
||||||
|
enum EGUIEvent
|
||||||
|
{
|
||||||
|
EV_GUI_None,
|
||||||
|
EV_GUI_KeyDown, // data1: unshifted ASCII, data2: shifted ASCII, data3: modifiers
|
||||||
|
EV_GUI_KeyRepeat, // same
|
||||||
|
EV_GUI_KeyUp, // same
|
||||||
|
EV_GUI_Char, // data1: translated character (for user text input), data2: alt down?
|
||||||
|
EV_GUI_FirstMouseEvent,
|
||||||
|
EV_GUI_MouseMove,
|
||||||
|
EV_GUI_LButtonDown,
|
||||||
|
EV_GUI_LButtonUp,
|
||||||
|
EV_GUI_LButtonDblClick,
|
||||||
|
EV_GUI_MButtonDown,
|
||||||
|
EV_GUI_MButtonUp,
|
||||||
|
EV_GUI_MButtonDblClick,
|
||||||
|
EV_GUI_RButtonDown,
|
||||||
|
EV_GUI_RButtonUp,
|
||||||
|
EV_GUI_RButtonDblClick,
|
||||||
|
EV_GUI_WheelUp, // data3: shift/ctrl/alt
|
||||||
|
EV_GUI_WheelDown, // "
|
||||||
|
EV_GUI_WheelRight, // "
|
||||||
|
EV_GUI_WheelLeft, // "
|
||||||
|
EV_GUI_BackButtonDown,
|
||||||
|
EV_GUI_BackButtonUp,
|
||||||
|
EV_GUI_FwdButtonDown,
|
||||||
|
EV_GUI_FwdButtonUp,
|
||||||
|
EV_GUI_LastMouseEvent,
|
||||||
|
};
|
||||||
|
|
||||||
|
enum GUIKeyModifiers
|
||||||
|
{
|
||||||
|
GKM_SHIFT = 1,
|
||||||
|
GKM_CTRL = 2,
|
||||||
|
GKM_ALT = 4,
|
||||||
|
GKM_META = 8,
|
||||||
|
GKM_LBUTTON = 16
|
||||||
|
};
|
||||||
|
|
||||||
|
// Special codes for some GUI keys, including a few real ASCII codes.
|
||||||
|
enum ESpecialGUIKeys
|
||||||
|
{
|
||||||
|
GK_PGDN = 1,
|
||||||
|
GK_PGUP = 2,
|
||||||
|
GK_HOME = 3,
|
||||||
|
GK_END = 4,
|
||||||
|
GK_LEFT = 5,
|
||||||
|
GK_RIGHT = 6,
|
||||||
|
GK_ALERT = 7, // ASCII bell
|
||||||
|
GK_BACKSPACE= 8, // ASCII
|
||||||
|
GK_TAB = 9, // ASCII
|
||||||
|
GK_LINEFEED = 10, // ASCII
|
||||||
|
GK_DOWN = 10,
|
||||||
|
GK_VTAB = 11, // ASCII
|
||||||
|
GK_UP = 11,
|
||||||
|
GK_FORMFEED = 12, // ASCII
|
||||||
|
GK_RETURN = 13, // ASCII
|
||||||
|
GK_F1 = 14,
|
||||||
|
GK_F2 = 15,
|
||||||
|
GK_F3 = 16,
|
||||||
|
GK_F4 = 17,
|
||||||
|
GK_F5 = 18,
|
||||||
|
GK_F6 = 19,
|
||||||
|
GK_F7 = 20,
|
||||||
|
GK_F8 = 21,
|
||||||
|
GK_F9 = 22,
|
||||||
|
GK_F10 = 23,
|
||||||
|
GK_F11 = 24,
|
||||||
|
GK_F12 = 25,
|
||||||
|
GK_DEL = 26,
|
||||||
|
GK_ESCAPE = 27, // ASCII
|
||||||
|
GK_FREE1 = 28,
|
||||||
|
GK_FREE2 = 29,
|
||||||
|
GK_BACK = 30, // browser back key
|
||||||
|
GK_CESCAPE = 31 // color escape
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif //__D_GUI_H__
|
136
source/common/console/keydef.h
Normal file
136
source/common/console/keydef.h
Normal file
|
@ -0,0 +1,136 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
//
|
||||||
|
// Keyboard definition. Everything below = 0x100 matches
|
||||||
|
// a mode 1 keyboard scan code.
|
||||||
|
//
|
||||||
|
|
||||||
|
enum EKeyCodes
|
||||||
|
{
|
||||||
|
KEY_PAUSE = 0xc5, // DIK_PAUSE
|
||||||
|
KEY_RIGHTARROW = 0xcd, // DIK_RIGHT
|
||||||
|
KEY_LEFTARROW = 0xcb, // DIK_LEFT
|
||||||
|
KEY_UPARROW = 0xc8, // DIK_UP
|
||||||
|
KEY_DOWNARROW = 0xd0, // DIK_DOWN
|
||||||
|
KEY_ESCAPE = 0x01, // DIK_ESCAPE
|
||||||
|
KEY_ENTER = 0x1c, // DIK_RETURN
|
||||||
|
KEY_SPACE = 0x39, // DIK_SPACE
|
||||||
|
KEY_TAB = 0x0f, // DIK_TAB
|
||||||
|
KEY_F1 = 0x3b, // DIK_F1
|
||||||
|
KEY_F2 = 0x3c, // DIK_F2
|
||||||
|
KEY_F3 = 0x3d, // DIK_F3
|
||||||
|
KEY_F4 = 0x3e, // DIK_F4
|
||||||
|
KEY_F5 = 0x3f, // DIK_F5
|
||||||
|
KEY_F6 = 0x40, // DIK_F6
|
||||||
|
KEY_F7 = 0x41, // DIK_F7
|
||||||
|
KEY_F8 = 0x42, // DIK_F8
|
||||||
|
KEY_F9 = 0x43, // DIK_F9
|
||||||
|
KEY_F10 = 0x44, // DIK_F10
|
||||||
|
KEY_F11 = 0x57, // DIK_F11
|
||||||
|
KEY_F12 = 0x58, // DIK_F12
|
||||||
|
KEY_GRAVE = 0x29, // DIK_GRAVE
|
||||||
|
|
||||||
|
KEY_BACKSPACE = 0x0e, // DIK_BACK
|
||||||
|
|
||||||
|
KEY_EQUALS = 0x0d, // DIK_EQUALS
|
||||||
|
KEY_MINUS = 0x0c, // DIK_MINUS
|
||||||
|
|
||||||
|
KEY_LSHIFT = 0x2A, // DIK_LSHIFT
|
||||||
|
KEY_LCTRL = 0x1d, // DIK_LCONTROL
|
||||||
|
KEY_LALT = 0x38, // DIK_LMENU
|
||||||
|
|
||||||
|
KEY_RSHIFT = 0x36,
|
||||||
|
KEY_RCTRL = 0x9d,
|
||||||
|
KEY_RALT = 0xb8,
|
||||||
|
|
||||||
|
KEY_INS = 0xd2, // DIK_INSERT
|
||||||
|
KEY_DEL = 0xd3, // DIK_DELETE
|
||||||
|
KEY_END = 0xcf, // DIK_END
|
||||||
|
KEY_HOME = 0xc7, // DIK_HOME
|
||||||
|
KEY_PGUP = 0xc9, // DIK_PRIOR
|
||||||
|
KEY_PGDN = 0xd1, // DIK_NEXT
|
||||||
|
|
||||||
|
KEY_MOUSE1 = 0x100,
|
||||||
|
KEY_MOUSE2 = 0x101,
|
||||||
|
KEY_MOUSE3 = 0x102,
|
||||||
|
KEY_MOUSE4 = 0x103,
|
||||||
|
KEY_MOUSE5 = 0x104,
|
||||||
|
KEY_MOUSE6 = 0x105,
|
||||||
|
KEY_MOUSE7 = 0x106,
|
||||||
|
KEY_MOUSE8 = 0x107,
|
||||||
|
|
||||||
|
KEY_FIRSTJOYBUTTON = 0x108,
|
||||||
|
KEY_JOY1 = KEY_FIRSTJOYBUTTON+0,
|
||||||
|
KEY_JOY2,
|
||||||
|
KEY_JOY3,
|
||||||
|
KEY_JOY4,
|
||||||
|
KEY_JOY5,
|
||||||
|
KEY_JOY6,
|
||||||
|
KEY_JOY7,
|
||||||
|
KEY_JOY8,
|
||||||
|
KEY_LASTJOYBUTTON = 0x187,
|
||||||
|
KEY_JOYPOV1_UP = 0x188,
|
||||||
|
KEY_JOYPOV1_RIGHT = 0x189,
|
||||||
|
KEY_JOYPOV1_DOWN = 0x18a,
|
||||||
|
KEY_JOYPOV1_LEFT = 0x18b,
|
||||||
|
KEY_JOYPOV2_UP = 0x18c,
|
||||||
|
KEY_JOYPOV3_UP = 0x190,
|
||||||
|
KEY_JOYPOV4_UP = 0x194,
|
||||||
|
|
||||||
|
KEY_MWHEELUP = 0x198,
|
||||||
|
KEY_MWHEELDOWN = 0x199,
|
||||||
|
KEY_MWHEELRIGHT = 0x19A,
|
||||||
|
KEY_MWHEELLEFT = 0x19B,
|
||||||
|
|
||||||
|
KEY_JOYAXIS1PLUS = 0x19C,
|
||||||
|
KEY_JOYAXIS1MINUS = 0x19D,
|
||||||
|
KEY_JOYAXIS2PLUS = 0x19E,
|
||||||
|
KEY_JOYAXIS2MINUS = 0x19F,
|
||||||
|
KEY_JOYAXIS3PLUS = 0x1A0,
|
||||||
|
KEY_JOYAXIS3MINUS = 0x1A1,
|
||||||
|
KEY_JOYAXIS4PLUS = 0x1A2,
|
||||||
|
KEY_JOYAXIS4MINUS = 0x1A3,
|
||||||
|
KEY_JOYAXIS5PLUS = 0x1A4,
|
||||||
|
KEY_JOYAXIS5MINUS = 0x1A5,
|
||||||
|
KEY_JOYAXIS6PLUS = 0x1A6,
|
||||||
|
KEY_JOYAXIS6MINUS = 0x1A7,
|
||||||
|
KEY_JOYAXIS7PLUS = 0x1A8,
|
||||||
|
KEY_JOYAXIS7MINUS = 0x1A9,
|
||||||
|
KEY_JOYAXIS8PLUS = 0x1AA,
|
||||||
|
KEY_JOYAXIS8MINUS = 0x1AB,
|
||||||
|
|
||||||
|
KEY_PAD_LTHUMB_RIGHT = 0x1AC,
|
||||||
|
KEY_PAD_LTHUMB_LEFT = 0x1AD,
|
||||||
|
KEY_PAD_LTHUMB_DOWN = 0x1AE,
|
||||||
|
KEY_PAD_LTHUMB_UP = 0x1AF,
|
||||||
|
|
||||||
|
KEY_PAD_RTHUMB_RIGHT = 0x1B0,
|
||||||
|
KEY_PAD_RTHUMB_LEFT = 0x1B1,
|
||||||
|
KEY_PAD_RTHUMB_DOWN = 0x1B2,
|
||||||
|
KEY_PAD_RTHUMB_UP = 0x1B3,
|
||||||
|
|
||||||
|
KEY_PAD_DPAD_UP = 0x1B4,
|
||||||
|
KEY_PAD_DPAD_DOWN = 0x1B5,
|
||||||
|
KEY_PAD_DPAD_LEFT = 0x1B6,
|
||||||
|
KEY_PAD_DPAD_RIGHT = 0x1B7,
|
||||||
|
KEY_PAD_START = 0x1B8,
|
||||||
|
KEY_PAD_BACK = 0x1B9,
|
||||||
|
KEY_PAD_LTHUMB = 0x1BA,
|
||||||
|
KEY_PAD_RTHUMB = 0x1BB,
|
||||||
|
KEY_PAD_LSHOULDER = 0x1BC,
|
||||||
|
KEY_PAD_RSHOULDER = 0x1BD,
|
||||||
|
KEY_PAD_LTRIGGER = 0x1BE,
|
||||||
|
KEY_PAD_RTRIGGER = 0x1BF,
|
||||||
|
KEY_PAD_A = 0x1C0,
|
||||||
|
KEY_PAD_B = 0x1C1,
|
||||||
|
KEY_PAD_X = 0x1C2,
|
||||||
|
KEY_PAD_Y = 0x1C3,
|
||||||
|
|
||||||
|
NUM_KEYS = 0x1C4,
|
||||||
|
|
||||||
|
NUM_JOYAXISBUTTONS = 8,
|
||||||
|
};
|
||||||
|
|
75
source/common/utility/i_time.cpp
Normal file
75
source/common/utility/i_time.cpp
Normal file
|
@ -0,0 +1,75 @@
|
||||||
|
/*
|
||||||
|
** i_time.cpp
|
||||||
|
** Implements the timer
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** Copyright 1998-2016 Randy Heit
|
||||||
|
** Copyright 2017 Magnus Norddahl
|
||||||
|
** 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 <chrono>
|
||||||
|
#include <thread>
|
||||||
|
#include "i_time.h"
|
||||||
|
#include "c_cvars.h"
|
||||||
|
#include "printf.h"
|
||||||
|
|
||||||
|
//==========================================================================
|
||||||
|
//
|
||||||
|
// Tick time functions
|
||||||
|
//
|
||||||
|
//==========================================================================
|
||||||
|
|
||||||
|
static double TimeScale = 1.0;
|
||||||
|
|
||||||
|
static uint64_t GetClockTimeNS()
|
||||||
|
{
|
||||||
|
using namespace std::chrono;
|
||||||
|
return (uint64_t)((duration_cast<microseconds>(steady_clock::now().time_since_epoch()).count()) * (uint64_t)(TimeScale * 1000));
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint64_t MSToNS(unsigned int ms)
|
||||||
|
{
|
||||||
|
return static_cast<uint64_t>(ms) * 1'000'000;
|
||||||
|
}
|
||||||
|
|
||||||
|
static uint64_t NSToMS(uint64_t ns)
|
||||||
|
{
|
||||||
|
return static_cast<uint64_t>(ns / 1'000'000);
|
||||||
|
}
|
||||||
|
|
||||||
|
uint64_t I_nsTime()
|
||||||
|
{
|
||||||
|
return GetClockTimeNS();
|
||||||
|
}
|
||||||
|
|
||||||
|
uint64_t I_msTime()
|
||||||
|
{
|
||||||
|
return NSToMS(I_nsTime());
|
||||||
|
}
|
||||||
|
|
9
source/common/utility/i_time.h
Normal file
9
source/common/utility/i_time.h
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
|
// [RH] Returns millisecond-accurate time
|
||||||
|
uint64_t I_msTime();
|
||||||
|
|
||||||
|
// Nanosecond-accurate time
|
||||||
|
uint64_t I_nsTime();
|
Loading…
Reference in a new issue