mirror of
https://github.com/ZDoom/qzdoom.git
synced 2024-11-10 14:51:51 +00:00
- scriptified the entire OptionMenu class and all still existing native subclasses.
This commit is contained in:
parent
12db190f41
commit
46c0d27fe7
8 changed files with 471 additions and 551 deletions
|
@ -124,13 +124,6 @@ DEFINE_ACTION_FUNCTION(IJoystickConfig, SetAxisMap)
|
||||||
|
|
||||||
DOptionMenuDescriptor *UpdateJoystickConfigMenu(IJoystickConfig *joy);
|
DOptionMenuDescriptor *UpdateJoystickConfigMenu(IJoystickConfig *joy);
|
||||||
|
|
||||||
class DJoystickConfigMenu : public DOptionMenu
|
|
||||||
{
|
|
||||||
DECLARE_CLASS(DJoystickConfigMenu, DOptionMenu)
|
|
||||||
};
|
|
||||||
|
|
||||||
IMPLEMENT_CLASS(DJoystickConfigMenu, false, false)
|
|
||||||
|
|
||||||
/*=======================================
|
/*=======================================
|
||||||
*
|
*
|
||||||
* Joystick Menu
|
* Joystick Menu
|
||||||
|
@ -295,7 +288,7 @@ void UpdateJoystickMenu(IJoystickConfig *selected)
|
||||||
if (i == (int)Joysticks.Size())
|
if (i == (int)Joysticks.Size())
|
||||||
{
|
{
|
||||||
SELECTED_JOYSTICK = NULL;
|
SELECTED_JOYSTICK = NULL;
|
||||||
if (DMenu::CurrentMenu != NULL && DMenu::CurrentMenu->IsKindOf(RUNTIME_CLASS(DJoystickConfigMenu)))
|
if (DMenu::CurrentMenu != NULL && DMenu::CurrentMenu->IsKindOf("JoystickConfigMenu"))
|
||||||
{
|
{
|
||||||
DMenu::CurrentMenu->Close();
|
DMenu::CurrentMenu->Close();
|
||||||
}
|
}
|
||||||
|
|
|
@ -378,6 +378,24 @@ void DMenu::Ticker ()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DEFINE_ACTION_FUNCTION(DMenu, Ticker)
|
||||||
|
{
|
||||||
|
PARAM_SELF_PROLOGUE(DMenu);
|
||||||
|
self->Drawer();
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void DMenu::CallTicker()
|
||||||
|
{
|
||||||
|
IFVIRTUAL(DMenu, Ticker)
|
||||||
|
{
|
||||||
|
VMValue params[] = { (DObject*)this };
|
||||||
|
GlobalVMStack.Call(func, params, 1, nullptr, 0, nullptr);
|
||||||
|
}
|
||||||
|
else Drawer();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void DMenu::Drawer ()
|
void DMenu::Drawer ()
|
||||||
{
|
{
|
||||||
if (this == DMenu::CurrentMenu && BackbuttonAlpha > 0 && m_show_backbutton >= 0 && m_use_mouse)
|
if (this == DMenu::CurrentMenu && BackbuttonAlpha > 0 && m_show_backbutton >= 0 && m_use_mouse)
|
||||||
|
@ -608,10 +626,14 @@ void M_SetMenu(FName menu, int param)
|
||||||
else if ((*desc)->IsKindOf(RUNTIME_CLASS(DOptionMenuDescriptor)))
|
else if ((*desc)->IsKindOf(RUNTIME_CLASS(DOptionMenuDescriptor)))
|
||||||
{
|
{
|
||||||
DOptionMenuDescriptor *ld = static_cast<DOptionMenuDescriptor*>(*desc);
|
DOptionMenuDescriptor *ld = static_cast<DOptionMenuDescriptor*>(*desc);
|
||||||
const PClass *cls = ld->mClass == nullptr? RUNTIME_CLASS(DOptionMenu) : ld->mClass;
|
const PClass *cls = ld->mClass == nullptr? PClass::FindClass("OptionMenu") : ld->mClass;
|
||||||
|
|
||||||
DOptionMenu *newmenu = (DOptionMenu *)cls->CreateNew();
|
DMenu *newmenu = (DMenu*)cls->CreateNew();
|
||||||
newmenu->Init(DMenu::CurrentMenu, ld);
|
IFVIRTUALPTRNAME(newmenu, "OptionMenu", Init)
|
||||||
|
{
|
||||||
|
VMValue params[3] = { newmenu, DMenu::CurrentMenu, ld };
|
||||||
|
GlobalVMStack.Call(func, params, 3, nullptr, 0);
|
||||||
|
}
|
||||||
M_ActivateMenu(newmenu);
|
M_ActivateMenu(newmenu);
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
|
@ -847,7 +869,7 @@ void M_Ticker (void)
|
||||||
DMenu::MenuTime++;
|
DMenu::MenuTime++;
|
||||||
if (DMenu::CurrentMenu != nullptr && menuactive != MENU_Off)
|
if (DMenu::CurrentMenu != nullptr && menuactive != MENU_Off)
|
||||||
{
|
{
|
||||||
DMenu::CurrentMenu->Ticker();
|
DMenu::CurrentMenu->CallTicker();
|
||||||
|
|
||||||
for (int i = 0; i < NUM_MKEYS; ++i)
|
for (int i = 0; i < NUM_MKEYS; ++i)
|
||||||
{
|
{
|
||||||
|
@ -856,7 +878,7 @@ void M_Ticker (void)
|
||||||
if (MenuButtonTickers[i] > 0 && --MenuButtonTickers[i] <= 0)
|
if (MenuButtonTickers[i] > 0 && --MenuButtonTickers[i] <= 0)
|
||||||
{
|
{
|
||||||
MenuButtonTickers[i] = KEY_REPEAT_RATE;
|
MenuButtonTickers[i] = KEY_REPEAT_RATE;
|
||||||
DMenu::CurrentMenu->MenuEvent(i, MenuButtonOrigin[i]);
|
DMenu::CurrentMenu->CallMenuEvent(i, MenuButtonOrigin[i]);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1170,9 +1192,6 @@ CCMD(undocolorpic)
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
//native void OptionMenuDescriptor.CalcIndent();
|
|
||||||
//native OptionMenuItem OptionMenuDescriptor.GetItem(Name iname);
|
|
||||||
|
|
||||||
DEFINE_FIELD(DMenu, mParentMenu)
|
DEFINE_FIELD(DMenu, mParentMenu)
|
||||||
|
|
||||||
DEFINE_FIELD(DMenuDescriptor, mMenuName)
|
DEFINE_FIELD(DMenuDescriptor, mMenuName)
|
||||||
|
@ -1211,12 +1230,6 @@ DEFINE_FIELD(DOptionMenuDescriptor, mIndent)
|
||||||
DEFINE_FIELD(DOptionMenuDescriptor, mPosition)
|
DEFINE_FIELD(DOptionMenuDescriptor, mPosition)
|
||||||
DEFINE_FIELD(DOptionMenuDescriptor, mDontDim)
|
DEFINE_FIELD(DOptionMenuDescriptor, mDontDim)
|
||||||
|
|
||||||
DEFINE_FIELD(DOptionMenu, CanScrollUp)
|
|
||||||
DEFINE_FIELD(DOptionMenu, CanScrollDown)
|
|
||||||
DEFINE_FIELD(DOptionMenu, VisBottom)
|
|
||||||
DEFINE_FIELD(DOptionMenu, mFocusControl)
|
|
||||||
DEFINE_FIELD(DOptionMenu, mDesc)
|
|
||||||
|
|
||||||
DEFINE_FIELD(FOptionMenuSettings, mTitleColor)
|
DEFINE_FIELD(FOptionMenuSettings, mTitleColor)
|
||||||
DEFINE_FIELD(FOptionMenuSettings, mFontColor)
|
DEFINE_FIELD(FOptionMenuSettings, mFontColor)
|
||||||
DEFINE_FIELD(FOptionMenuSettings, mFontColorValue)
|
DEFINE_FIELD(FOptionMenuSettings, mFontColorValue)
|
||||||
|
|
|
@ -282,6 +282,7 @@ public:
|
||||||
bool CallResponder(event_t *ev);
|
bool CallResponder(event_t *ev);
|
||||||
bool CallMenuEvent(int mkey, bool fromcontroller);
|
bool CallMenuEvent(int mkey, bool fromcontroller);
|
||||||
bool CallMouseEvent(int type, int x, int y);
|
bool CallMouseEvent(int type, int x, int y);
|
||||||
|
void CallTicker();
|
||||||
void CallDrawer();
|
void CallDrawer();
|
||||||
|
|
||||||
bool MouseEventBack(int type, int x, int y);
|
bool MouseEventBack(int type, int x, int y);
|
||||||
|
@ -394,50 +395,6 @@ typedef TMap< FName, FOptionValues* > FOptionMap;
|
||||||
extern FOptionMap OptionValues;
|
extern FOptionMap OptionValues;
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Option menu class runs a menu described by a DOptionMenuDescriptor
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
class DOptionMenu : public DMenu
|
|
||||||
{
|
|
||||||
DECLARE_CLASS(DOptionMenu, DMenu)
|
|
||||||
HAS_OBJECT_POINTERS;
|
|
||||||
|
|
||||||
public: // needs to be public for script access
|
|
||||||
bool CanScrollUp;
|
|
||||||
bool CanScrollDown;
|
|
||||||
int VisBottom;
|
|
||||||
DMenuItemBase *mFocusControl;
|
|
||||||
DOptionMenuDescriptor *mDesc;
|
|
||||||
|
|
||||||
//public:
|
|
||||||
DMenuItemBase *GetItem(FName name);
|
|
||||||
DOptionMenu(DMenu *parent = NULL, DOptionMenuDescriptor *desc = NULL);
|
|
||||||
virtual void Init(DMenu *parent = NULL, DOptionMenuDescriptor *desc = NULL);
|
|
||||||
int FirstSelectable();
|
|
||||||
bool Responder (event_t *ev);
|
|
||||||
bool MenuEvent (int mkey, bool fromcontroller);
|
|
||||||
bool MouseEvent(int type, int x, int y);
|
|
||||||
void Ticker ();
|
|
||||||
void Drawer ();
|
|
||||||
const DOptionMenuDescriptor *GetDescriptor() const { return mDesc; }
|
|
||||||
void SetFocus(DMenuItemBase *fc)
|
|
||||||
{
|
|
||||||
mFocusControl = fc;
|
|
||||||
}
|
|
||||||
bool CheckFocus(DMenuItemBase *fc)
|
|
||||||
{
|
|
||||||
return mFocusControl == fc;
|
|
||||||
}
|
|
||||||
void ReleaseFocus()
|
|
||||||
{
|
|
||||||
mFocusControl = NULL;
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
//
|
//
|
||||||
// Input some text
|
// Input some text
|
||||||
|
|
|
@ -700,7 +700,7 @@ static void ParseOptionMenuBody(FScanner &sc, DOptionMenuDescriptor *desc)
|
||||||
{
|
{
|
||||||
sc.MustGetString();
|
sc.MustGetString();
|
||||||
const PClass *cls = PClass::FindClass(sc.String);
|
const PClass *cls = PClass::FindClass(sc.String);
|
||||||
if (cls == nullptr || !cls->IsDescendantOf(RUNTIME_CLASS(DOptionMenu)))
|
if (cls == nullptr || !cls->IsDescendantOf("OptionMenu"))
|
||||||
{
|
{
|
||||||
sc.ScriptError("Unknown menu class '%s'", sc.String);
|
sc.ScriptError("Unknown menu class '%s'", sc.String);
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
** Handler class for the option menus and associated items
|
** Handler class for the option menus and associated items
|
||||||
**
|
**
|
||||||
**---------------------------------------------------------------------------
|
**---------------------------------------------------------------------------
|
||||||
** Copyright 2010 Christoph Oelckers
|
** Copyright 2010-2017 Christoph Oelckers
|
||||||
** All rights reserved.
|
** All rights reserved.
|
||||||
**
|
**
|
||||||
** Redistribution and use in source and binary forms, with or without
|
** Redistribution and use in source and binary forms, with or without
|
||||||
|
@ -49,431 +49,12 @@
|
||||||
#include "menu/menu.h"
|
#include "menu/menu.h"
|
||||||
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
// Draws a string in the console font, scaled to the 8x8 cells
|
|
||||||
// used by the default console font.
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void M_DrawConText (int color, int x, int y, const char *str)
|
|
||||||
{
|
|
||||||
screen->DrawText (ConFont, color, x, y, str,
|
|
||||||
DTA_CellX, 8 * CleanXfac_1,
|
|
||||||
DTA_CellY, 8 * CleanYfac_1,
|
|
||||||
TAG_DONE);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
IMPLEMENT_CLASS(DOptionMenu, false, false)
|
|
||||||
|
|
||||||
IMPLEMENT_POINTERS_START(DOptionMenu)
|
|
||||||
IMPLEMENT_POINTER(mFocusControl)
|
|
||||||
IMPLEMENT_POINTERS_END
|
|
||||||
|
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
//
|
//
|
||||||
//
|
//
|
||||||
//
|
//
|
||||||
//=============================================================================
|
//=============================================================================
|
||||||
|
|
||||||
DOptionMenu::DOptionMenu(DMenu *parent, DOptionMenuDescriptor *desc)
|
|
||||||
: DMenu(parent)
|
|
||||||
{
|
|
||||||
CanScrollUp = false;
|
|
||||||
CanScrollDown = false;
|
|
||||||
VisBottom = 0;
|
|
||||||
mFocusControl = NULL;
|
|
||||||
Init(parent, desc);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void DOptionMenu::Init(DMenu *parent, DOptionMenuDescriptor *desc)
|
|
||||||
{
|
|
||||||
mParentMenu = parent;
|
|
||||||
GC::WriteBarrier(this, parent);
|
|
||||||
mDesc = desc;
|
|
||||||
if (mDesc != NULL && mDesc->mSelectedItem == -1) mDesc->mSelectedItem = FirstSelectable();
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
int DOptionMenu::FirstSelectable()
|
|
||||||
{
|
|
||||||
if (mDesc != NULL)
|
|
||||||
{
|
|
||||||
// Go down to the first selectable item
|
|
||||||
int i = -1;
|
|
||||||
do
|
|
||||||
{
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
while (i < (int)mDesc->mItems.Size() && !mDesc->mItems[i]->Selectable());
|
|
||||||
if (i>=0 && i < (int)mDesc->mItems.Size()) return i;
|
|
||||||
}
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
DMenuItemBase *DOptionMenu::GetItem(FName name)
|
|
||||||
{
|
|
||||||
for(unsigned i=0;i<mDesc->mItems.Size(); i++)
|
|
||||||
{
|
|
||||||
FName nm = mDesc->mItems[i]->GetAction(NULL);
|
|
||||||
if (nm == name) return mDesc->mItems[i];
|
|
||||||
}
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DOptionMenu::Responder (event_t *ev)
|
|
||||||
{
|
|
||||||
if (ev->type == EV_GUI_Event)
|
|
||||||
{
|
|
||||||
if (ev->subtype == EV_GUI_WheelUp)
|
|
||||||
{
|
|
||||||
int scrollamt = MIN(2, mDesc->mScrollPos);
|
|
||||||
mDesc->mScrollPos -= scrollamt;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
else if (ev->subtype == EV_GUI_WheelDown)
|
|
||||||
{
|
|
||||||
if (CanScrollDown)
|
|
||||||
{
|
|
||||||
if (VisBottom < (int)(mDesc->mItems.Size()-2))
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos += 2;
|
|
||||||
VisBottom += 2;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos++;
|
|
||||||
VisBottom++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return Super::Responder(ev);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DOptionMenu::MenuEvent (int mkey, bool fromcontroller)
|
|
||||||
{
|
|
||||||
int startedAt = mDesc->mSelectedItem;
|
|
||||||
|
|
||||||
switch (mkey)
|
|
||||||
{
|
|
||||||
case MKEY_Up:
|
|
||||||
if (mDesc->mSelectedItem == -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = FirstSelectable();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
do
|
|
||||||
{
|
|
||||||
--mDesc->mSelectedItem;
|
|
||||||
|
|
||||||
if (mDesc->mScrollPos > 0 &&
|
|
||||||
mDesc->mSelectedItem <= mDesc->mScrollTop + mDesc->mScrollPos)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = MAX(mDesc->mSelectedItem - mDesc->mScrollTop - 1, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mDesc->mSelectedItem < 0)
|
|
||||||
{
|
|
||||||
// Figure out how many lines of text fit on the menu
|
|
||||||
int y = mDesc->mPosition;
|
|
||||||
|
|
||||||
if (y <= 0)
|
|
||||||
{
|
|
||||||
if (BigFont && mDesc->mTitle.IsNotEmpty())
|
|
||||||
{
|
|
||||||
y = -y + BigFont->GetHeight();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
y = -y;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
y *= CleanYfac_1;
|
|
||||||
int rowheight = OptionSettings.mLinespacing * CleanYfac_1;
|
|
||||||
int maxitems = (screen->GetHeight() - rowheight - y) / rowheight + 1;
|
|
||||||
|
|
||||||
mDesc->mScrollPos = MAX (0, (int)mDesc->mItems.Size() - maxitems + mDesc->mScrollTop);
|
|
||||||
mDesc->mSelectedItem = mDesc->mItems.Size()-1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
while (!mDesc->mItems[mDesc->mSelectedItem]->Selectable() && mDesc->mSelectedItem != startedAt);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case MKEY_Down:
|
|
||||||
if (mDesc->mSelectedItem == -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = FirstSelectable();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
do
|
|
||||||
{
|
|
||||||
++mDesc->mSelectedItem;
|
|
||||||
|
|
||||||
if (CanScrollDown && mDesc->mSelectedItem == VisBottom)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos++;
|
|
||||||
VisBottom++;
|
|
||||||
}
|
|
||||||
if (mDesc->mSelectedItem >= (int)mDesc->mItems.Size())
|
|
||||||
{
|
|
||||||
if (startedAt == -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = -1;
|
|
||||||
mDesc->mScrollPos = -1;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = 0;
|
|
||||||
mDesc->mScrollPos = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
while (!mDesc->mItems[mDesc->mSelectedItem]->Selectable() && mDesc->mSelectedItem != startedAt);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case MKEY_PageUp:
|
|
||||||
if (mDesc->mScrollPos > 0)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos -= VisBottom - mDesc->mScrollPos - mDesc->mScrollTop;
|
|
||||||
if (mDesc->mScrollPos < 0)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = 0;
|
|
||||||
}
|
|
||||||
if (mDesc->mSelectedItem != -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = mDesc->mScrollTop + mDesc->mScrollPos + 1;
|
|
||||||
while (!mDesc->mItems[mDesc->mSelectedItem]->Selectable())
|
|
||||||
{
|
|
||||||
if (++mDesc->mSelectedItem >= (int)mDesc->mItems.Size())
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (mDesc->mScrollPos > mDesc->mSelectedItem)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = mDesc->mSelectedItem;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case MKEY_PageDown:
|
|
||||||
if (CanScrollDown)
|
|
||||||
{
|
|
||||||
int pagesize = VisBottom - mDesc->mScrollPos - mDesc->mScrollTop;
|
|
||||||
mDesc->mScrollPos += pagesize;
|
|
||||||
if (mDesc->mScrollPos + mDesc->mScrollTop + pagesize > (int)mDesc->mItems.Size())
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = mDesc->mItems.Size() - mDesc->mScrollTop - pagesize;
|
|
||||||
}
|
|
||||||
if (mDesc->mSelectedItem != -1)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = mDesc->mScrollTop + mDesc->mScrollPos;
|
|
||||||
while (!mDesc->mItems[mDesc->mSelectedItem]->Selectable())
|
|
||||||
{
|
|
||||||
if (++mDesc->mSelectedItem >= (int)mDesc->mItems.Size())
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (mDesc->mScrollPos > mDesc->mSelectedItem)
|
|
||||||
{
|
|
||||||
mDesc->mScrollPos = mDesc->mSelectedItem;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case MKEY_Enter:
|
|
||||||
if (mDesc->mSelectedItem >= 0 && mDesc->mItems[mDesc->mSelectedItem]->Activate())
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
// fall through to default
|
|
||||||
default:
|
|
||||||
if (mDesc->mSelectedItem >= 0 &&
|
|
||||||
mDesc->mItems[mDesc->mSelectedItem]->MenuEvent(mkey, fromcontroller)) return true;
|
|
||||||
return Super::MenuEvent(mkey, fromcontroller);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mDesc->mSelectedItem != startedAt)
|
|
||||||
{
|
|
||||||
S_Sound (CHAN_VOICE | CHAN_UI, "menu/cursor", snd_menuvolume, ATTN_NONE);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
bool DOptionMenu::MouseEvent(int type, int x, int y)
|
|
||||||
{
|
|
||||||
y = (y / CleanYfac_1) - mDesc->mDrawTop;
|
|
||||||
|
|
||||||
if (mFocusControl)
|
|
||||||
{
|
|
||||||
mFocusControl->MouseEvent(type, x, y);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
int yline = (y / OptionSettings.mLinespacing);
|
|
||||||
if (yline >= mDesc->mScrollTop)
|
|
||||||
{
|
|
||||||
yline += mDesc->mScrollPos;
|
|
||||||
}
|
|
||||||
if ((unsigned)yline < mDesc->mItems.Size() && mDesc->mItems[yline]->Selectable())
|
|
||||||
{
|
|
||||||
if (yline != mDesc->mSelectedItem)
|
|
||||||
{
|
|
||||||
mDesc->mSelectedItem = yline;
|
|
||||||
//S_Sound (CHAN_VOICE | CHAN_UI, "menu/cursor", snd_menuvolume, ATTN_NONE);
|
|
||||||
}
|
|
||||||
mDesc->mItems[yline]->MouseEvent(type, x, y);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
mDesc->mSelectedItem = -1;
|
|
||||||
return Super::MouseEvent(type, x, y);
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void DOptionMenu::Ticker ()
|
|
||||||
{
|
|
||||||
Super::Ticker();
|
|
||||||
for(unsigned i=0;i<mDesc->mItems.Size(); i++)
|
|
||||||
{
|
|
||||||
mDesc->mItems[i]->Ticker();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
void DOptionMenu::Drawer ()
|
|
||||||
{
|
|
||||||
int y = mDesc->mPosition;
|
|
||||||
|
|
||||||
if (y <= 0)
|
|
||||||
{
|
|
||||||
if (BigFont && mDesc->mTitle.IsNotEmpty())
|
|
||||||
{
|
|
||||||
const char *tt = mDesc->mTitle;
|
|
||||||
if (*tt == '$') tt = GStrings(tt+1);
|
|
||||||
screen->DrawText (BigFont, OptionSettings.mTitleColor,
|
|
||||||
(screen->GetWidth() - BigFont->StringWidth(tt) * CleanXfac_1) / 2, 10*CleanYfac_1,
|
|
||||||
tt, DTA_CleanNoMove_1, true, TAG_DONE);
|
|
||||||
y = -y + BigFont->GetHeight();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
y = -y;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
mDesc->mDrawTop = y;
|
|
||||||
int fontheight = OptionSettings.mLinespacing * CleanYfac_1;
|
|
||||||
y *= CleanYfac_1;
|
|
||||||
|
|
||||||
int indent = mDesc->mIndent;
|
|
||||||
if (indent > 280)
|
|
||||||
{ // kludge for the compatibility options with their extremely long labels
|
|
||||||
if (indent + 40 <= CleanWidth_1)
|
|
||||||
{
|
|
||||||
indent = (screen->GetWidth() - ((indent + 40) * CleanXfac_1)) / 2 + indent * CleanXfac_1;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
indent = screen->GetWidth() - 40 * CleanXfac_1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
indent = (indent - 160) * CleanXfac_1 + screen->GetWidth() / 2;
|
|
||||||
}
|
|
||||||
|
|
||||||
int ytop = y + mDesc->mScrollTop * 8 * CleanYfac_1;
|
|
||||||
int lastrow = screen->GetHeight() - SmallFont->GetHeight() * CleanYfac_1;
|
|
||||||
|
|
||||||
unsigned i;
|
|
||||||
for (i = 0; i < mDesc->mItems.Size() && y <= lastrow; i++, y += fontheight)
|
|
||||||
{
|
|
||||||
// Don't scroll the uppermost items
|
|
||||||
if ((int)i == mDesc->mScrollTop)
|
|
||||||
{
|
|
||||||
i += mDesc->mScrollPos;
|
|
||||||
if (i >= mDesc->mItems.Size()) break; // skipped beyond end of menu
|
|
||||||
}
|
|
||||||
bool isSelected = mDesc->mSelectedItem == (int)i;
|
|
||||||
int cur_indent = mDesc->mItems[i]->Draw(mDesc, y, indent, isSelected);
|
|
||||||
if (cur_indent >= 0 && isSelected && mDesc->mItems[i]->Selectable())
|
|
||||||
{
|
|
||||||
if (((DMenu::MenuTime%8) < 6) || DMenu::CurrentMenu != this)
|
|
||||||
{
|
|
||||||
M_DrawConText(OptionSettings.mFontColorSelection, cur_indent + 3 * CleanXfac_1, y+fontheight-9*CleanYfac_1, "\xd");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
CanScrollUp = (mDesc->mScrollPos > 0);
|
|
||||||
CanScrollDown = (i < mDesc->mItems.Size());
|
|
||||||
VisBottom = i - 1;
|
|
||||||
|
|
||||||
if (CanScrollUp)
|
|
||||||
{
|
|
||||||
M_DrawConText(CR_ORANGE, 3 * CleanXfac_1, ytop, "\x1a");
|
|
||||||
}
|
|
||||||
if (CanScrollDown)
|
|
||||||
{
|
|
||||||
M_DrawConText(CR_ORANGE, 3 * CleanXfac_1, y - 8*CleanYfac_1, "\x1b");
|
|
||||||
}
|
|
||||||
Super::Drawer();
|
|
||||||
}
|
|
||||||
|
|
||||||
void DOptionMenuDescriptor::CalcIndent()
|
void DOptionMenuDescriptor::CalcIndent()
|
||||||
{
|
{
|
||||||
// calculate the menu indent
|
// calculate the menu indent
|
||||||
|
|
|
@ -22,7 +22,7 @@ inline unsigned GetVirtualIndex(PClass *cls, const char *funcname)
|
||||||
#define IFVIRTUALPTRNAME(self, cls, funcname) \
|
#define IFVIRTUALPTRNAME(self, cls, funcname) \
|
||||||
static unsigned VIndex = ~0u; \
|
static unsigned VIndex = ~0u; \
|
||||||
if (VIndex == ~0u) { \
|
if (VIndex == ~0u) { \
|
||||||
VIndex = GetVirtualIndex(PClass::FindActor(cls), #funcname); \
|
VIndex = GetVirtualIndex(PClass::FindClass(cls), #funcname); \
|
||||||
assert(VIndex != ~0u); \
|
assert(VIndex != ~0u); \
|
||||||
} \
|
} \
|
||||||
auto clss = self->GetClass(); \
|
auto clss = self->GetClass(); \
|
||||||
|
|
|
@ -104,6 +104,7 @@ class Menu : Object native
|
||||||
native virtual bool Responder(InputEvent ev);
|
native virtual bool Responder(InputEvent ev);
|
||||||
native virtual bool MenuEvent (int mkey, bool fromcontroller);
|
native virtual bool MenuEvent (int mkey, bool fromcontroller);
|
||||||
native virtual bool MouseEvent(int type, int mx, int my);
|
native virtual bool MouseEvent(int type, int mx, int my);
|
||||||
|
native virtual void Ticker();
|
||||||
native virtual void Drawer();
|
native virtual void Drawer();
|
||||||
native void Close();
|
native void Close();
|
||||||
native MenuItemBase GetItem(Name n);
|
native MenuItemBase GetItem(Name n);
|
||||||
|
@ -200,66 +201,3 @@ class OptionMenuDescriptor : MenuDescriptor native
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class OptionMenu : Menu native
|
|
||||||
{
|
|
||||||
native OptionMenuDescriptor mDesc;
|
|
||||||
native bool CanScrollUp;
|
|
||||||
native bool CanScrollDown;
|
|
||||||
native int VisBottom;
|
|
||||||
native OptionMenuItem mFocusControl;
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
virtual void Init(Menu parent, OptionMenuDescriptor desc)
|
|
||||||
{
|
|
||||||
mParentMenu = parent;
|
|
||||||
mDesc = desc;
|
|
||||||
if (mDesc != NULL && mDesc.mSelectedItem == -1) mDesc.mSelectedItem = FirstSelectable();
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
//=============================================================================
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//
|
|
||||||
//=============================================================================
|
|
||||||
|
|
||||||
int FirstSelectable()
|
|
||||||
{
|
|
||||||
if (mDesc != NULL)
|
|
||||||
{
|
|
||||||
// Go down to the first selectable item
|
|
||||||
int i = -1;
|
|
||||||
do
|
|
||||||
{
|
|
||||||
i++;
|
|
||||||
}
|
|
||||||
while (i < mDesc.mItems.Size() && !mDesc.mItems[i].Selectable());
|
|
||||||
if (i>=0 && i < mDesc.mItems.Size()) return i;
|
|
||||||
}
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
override void SetFocus(MenuItemBase fc)
|
|
||||||
{
|
|
||||||
mFocusControl = OptionMenuItem(fc);
|
|
||||||
}
|
|
||||||
|
|
||||||
override bool CheckFocus(MenuItemBase fc)
|
|
||||||
{
|
|
||||||
return mFocusControl == fc;
|
|
||||||
}
|
|
||||||
|
|
||||||
override void ReleaseFocus()
|
|
||||||
{
|
|
||||||
mFocusControl = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,439 @@
|
||||||
|
/*
|
||||||
|
** optionmenu.cpp
|
||||||
|
** Handler class for the option menus and associated items
|
||||||
|
**
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
** Copyright 2010-2017 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.
|
||||||
|
**---------------------------------------------------------------------------
|
||||||
|
**
|
||||||
|
*/
|
||||||
|
|
||||||
|
class OptionMenu : Menu
|
||||||
|
{
|
||||||
|
OptionMenuDescriptor mDesc;
|
||||||
|
bool CanScrollUp;
|
||||||
|
bool CanScrollDown;
|
||||||
|
int VisBottom;
|
||||||
|
OptionMenuItem mFocusControl;
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
virtual void Init(Menu parent, OptionMenuDescriptor desc)
|
||||||
|
{
|
||||||
|
mParentMenu = parent;
|
||||||
|
mDesc = desc;
|
||||||
|
if (mDesc != NULL && mDesc.mSelectedItem == -1) mDesc.mSelectedItem = FirstSelectable();
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
int FirstSelectable()
|
||||||
|
{
|
||||||
|
if (mDesc != NULL)
|
||||||
|
{
|
||||||
|
// Go down to the first selectable item
|
||||||
|
int i = -1;
|
||||||
|
do
|
||||||
|
{
|
||||||
|
i++;
|
||||||
|
}
|
||||||
|
while (i < mDesc.mItems.Size() && !mDesc.mItems[i].Selectable());
|
||||||
|
if (i>=0 && i < mDesc.mItems.Size()) return i;
|
||||||
|
}
|
||||||
|
return -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
override bool Responder (InputEvent ev)
|
||||||
|
{
|
||||||
|
if (ev.type == InputEvent.GUI_Event)
|
||||||
|
{
|
||||||
|
if (ev.subtype == InputEvent.GUI_WheelUp)
|
||||||
|
{
|
||||||
|
int scrollamt = MIN(2, mDesc.mScrollPos);
|
||||||
|
mDesc.mScrollPos -= scrollamt;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else if (ev.subtype == InputEvent.GUI_WheelDown)
|
||||||
|
{
|
||||||
|
if (CanScrollDown)
|
||||||
|
{
|
||||||
|
if (VisBottom >= 0 && VisBottom < (mDesc.mItems.Size()-2))
|
||||||
|
{
|
||||||
|
mDesc.mScrollPos += 2;
|
||||||
|
VisBottom += 2;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mDesc.mScrollPos++;
|
||||||
|
VisBottom++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return Super.Responder(ev);
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
override bool MenuEvent (int mkey, bool fromcontroller)
|
||||||
|
{
|
||||||
|
int startedAt = mDesc.mSelectedItem;
|
||||||
|
|
||||||
|
switch (mkey)
|
||||||
|
{
|
||||||
|
case MKEY_Up:
|
||||||
|
if (mDesc.mSelectedItem == -1)
|
||||||
|
{
|
||||||
|
mDesc.mSelectedItem = FirstSelectable();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
do
|
||||||
|
{
|
||||||
|
--mDesc.mSelectedItem;
|
||||||
|
|
||||||
|
if (mDesc.mScrollPos > 0 &&
|
||||||
|
mDesc.mSelectedItem <= mDesc.mScrollTop + mDesc.mScrollPos)
|
||||||
|
{
|
||||||
|
mDesc.mScrollPos = MAX(mDesc.mSelectedItem - mDesc.mScrollTop - 1, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mDesc.mSelectedItem < 0)
|
||||||
|
{
|
||||||
|
// Figure out how many lines of text fit on the menu
|
||||||
|
int y = mDesc.mPosition;
|
||||||
|
|
||||||
|
if (y <= 0)
|
||||||
|
{
|
||||||
|
if (BigFont && mDesc.mTitle.Length() > 0)
|
||||||
|
{
|
||||||
|
y = -y + BigFont.GetHeight();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
y = -y;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
y *= CleanYfac_1;
|
||||||
|
int rowheight = OptionMenuSettings.mLinespacing * CleanYfac_1;
|
||||||
|
int maxitems = (screen.GetHeight() - rowheight - y) / rowheight + 1;
|
||||||
|
|
||||||
|
mDesc.mScrollPos = MAX (0, mDesc.mItems.Size() - maxitems + mDesc.mScrollTop);
|
||||||
|
mDesc.mSelectedItem = mDesc.mItems.Size()-1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
while (!mDesc.mItems[mDesc.mSelectedItem].Selectable() && mDesc.mSelectedItem != startedAt);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case MKEY_Down:
|
||||||
|
if (mDesc.mSelectedItem == -1)
|
||||||
|
{
|
||||||
|
mDesc.mSelectedItem = FirstSelectable();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
do
|
||||||
|
{
|
||||||
|
++mDesc.mSelectedItem;
|
||||||
|
|
||||||
|
if (CanScrollDown && mDesc.mSelectedItem == VisBottom)
|
||||||
|
{
|
||||||
|
mDesc.mScrollPos++;
|
||||||
|
VisBottom++;
|
||||||
|
}
|
||||||
|
if (mDesc.mSelectedItem >= mDesc.mItems.Size())
|
||||||
|
{
|
||||||
|
if (startedAt == -1)
|
||||||
|
{
|
||||||
|
mDesc.mSelectedItem = -1;
|
||||||
|
mDesc.mScrollPos = -1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mDesc.mSelectedItem = 0;
|
||||||
|
mDesc.mScrollPos = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
while (!mDesc.mItems[mDesc.mSelectedItem].Selectable() && mDesc.mSelectedItem != startedAt);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case MKEY_PageUp:
|
||||||
|
if (mDesc.mScrollPos > 0)
|
||||||
|
{
|
||||||
|
mDesc.mScrollPos -= VisBottom - mDesc.mScrollPos - mDesc.mScrollTop;
|
||||||
|
if (mDesc.mScrollPos < 0)
|
||||||
|
{
|
||||||
|
mDesc.mScrollPos = 0;
|
||||||
|
}
|
||||||
|
if (mDesc.mSelectedItem != -1)
|
||||||
|
{
|
||||||
|
mDesc.mSelectedItem = mDesc.mScrollTop + mDesc.mScrollPos + 1;
|
||||||
|
while (!mDesc.mItems[mDesc.mSelectedItem].Selectable())
|
||||||
|
{
|
||||||
|
if (++mDesc.mSelectedItem >= mDesc.mItems.Size())
|
||||||
|
{
|
||||||
|
mDesc.mSelectedItem = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (mDesc.mScrollPos > mDesc.mSelectedItem)
|
||||||
|
{
|
||||||
|
mDesc.mScrollPos = mDesc.mSelectedItem;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case MKEY_PageDown:
|
||||||
|
if (CanScrollDown)
|
||||||
|
{
|
||||||
|
int pagesize = VisBottom - mDesc.mScrollPos - mDesc.mScrollTop;
|
||||||
|
mDesc.mScrollPos += pagesize;
|
||||||
|
if (mDesc.mScrollPos + mDesc.mScrollTop + pagesize > mDesc.mItems.Size())
|
||||||
|
{
|
||||||
|
mDesc.mScrollPos = mDesc.mItems.Size() - mDesc.mScrollTop - pagesize;
|
||||||
|
}
|
||||||
|
if (mDesc.mSelectedItem != -1)
|
||||||
|
{
|
||||||
|
mDesc.mSelectedItem = mDesc.mScrollTop + mDesc.mScrollPos;
|
||||||
|
while (!mDesc.mItems[mDesc.mSelectedItem].Selectable())
|
||||||
|
{
|
||||||
|
if (++mDesc.mSelectedItem >= mDesc.mItems.Size())
|
||||||
|
{
|
||||||
|
mDesc.mSelectedItem = 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (mDesc.mScrollPos > mDesc.mSelectedItem)
|
||||||
|
{
|
||||||
|
mDesc.mScrollPos = mDesc.mSelectedItem;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case MKEY_Enter:
|
||||||
|
if (mDesc.mSelectedItem >= 0 && mDesc.mItems[mDesc.mSelectedItem].Activate())
|
||||||
|
{
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
// fall through to default
|
||||||
|
default:
|
||||||
|
if (mDesc.mSelectedItem >= 0 &&
|
||||||
|
mDesc.mItems[mDesc.mSelectedItem].MenuEvent(mkey, fromcontroller)) return true;
|
||||||
|
return Super.MenuEvent(mkey, fromcontroller);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mDesc.mSelectedItem != startedAt)
|
||||||
|
{
|
||||||
|
MenuSound ("menu/cursor");
|
||||||
|
}
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
override bool MouseEvent(int type, int x, int y)
|
||||||
|
{
|
||||||
|
y = (y / CleanYfac_1) - mDesc.mDrawTop;
|
||||||
|
|
||||||
|
if (mFocusControl)
|
||||||
|
{
|
||||||
|
mFocusControl.MouseEvent(type, x, y);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
int yline = (y / OptionMenuSettings.mLinespacing);
|
||||||
|
if (yline >= mDesc.mScrollTop)
|
||||||
|
{
|
||||||
|
yline += mDesc.mScrollPos;
|
||||||
|
}
|
||||||
|
if (yline >= 0 && yline < mDesc.mItems.Size() && mDesc.mItems[yline].Selectable())
|
||||||
|
{
|
||||||
|
if (yline != mDesc.mSelectedItem)
|
||||||
|
{
|
||||||
|
mDesc.mSelectedItem = yline;
|
||||||
|
//S_Sound (CHAN_VOICE | CHAN_UI, "menu/cursor", snd_menuvolume, ATTN_NONE);
|
||||||
|
}
|
||||||
|
mDesc.mItems[yline].MouseEvent(type, x, y);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
mDesc.mSelectedItem = -1;
|
||||||
|
return Super.MouseEvent(type, x, y);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
override void Ticker ()
|
||||||
|
{
|
||||||
|
Super.Ticker();
|
||||||
|
for(int i = 0; i < mDesc.mItems.Size(); i++)
|
||||||
|
{
|
||||||
|
mDesc.mItems[i].Ticker();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
override void Drawer ()
|
||||||
|
{
|
||||||
|
int y = mDesc.mPosition;
|
||||||
|
|
||||||
|
if (y <= 0)
|
||||||
|
{
|
||||||
|
if (BigFont && mDesc.mTitle.Length() > 0)
|
||||||
|
{
|
||||||
|
let tt = Stringtable.Localize(mDesc.mTitle);
|
||||||
|
screen.DrawText (BigFont, OptionMenuSettings.mTitleColor,
|
||||||
|
(screen.GetWidth() - BigFont.StringWidth(tt) * CleanXfac_1) / 2, 10*CleanYfac_1,
|
||||||
|
tt, DTA_CleanNoMove_1, true);
|
||||||
|
y = -y + BigFont.GetHeight();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
y = -y;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
mDesc.mDrawTop = y;
|
||||||
|
int fontheight = OptionMenuSettings.mLinespacing * CleanYfac_1;
|
||||||
|
y *= CleanYfac_1;
|
||||||
|
|
||||||
|
int indent = mDesc.mIndent;
|
||||||
|
if (indent > 280)
|
||||||
|
{ // kludge for the compatibility options with their extremely long labels
|
||||||
|
if (indent + 40 <= CleanWidth_1)
|
||||||
|
{
|
||||||
|
indent = (screen.GetWidth() - ((indent + 40) * CleanXfac_1)) / 2 + indent * CleanXfac_1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
indent = screen.GetWidth() - 40 * CleanXfac_1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
indent = (indent - 160) * CleanXfac_1 + screen.GetWidth() / 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
int ytop = y + mDesc.mScrollTop * 8 * CleanYfac_1;
|
||||||
|
int lastrow = screen.GetHeight() - SmallFont.GetHeight() * CleanYfac_1;
|
||||||
|
|
||||||
|
int i;
|
||||||
|
for (i = 0; i < mDesc.mItems.Size() && y <= lastrow; i++)
|
||||||
|
{
|
||||||
|
// Don't scroll the uppermost items
|
||||||
|
if (i == mDesc.mScrollTop)
|
||||||
|
{
|
||||||
|
i += mDesc.mScrollPos;
|
||||||
|
if (i >= mDesc.mItems.Size()) break; // skipped beyond end of menu
|
||||||
|
}
|
||||||
|
bool isSelected = mDesc.mSelectedItem == i;
|
||||||
|
int cur_indent = mDesc.mItems[i].Draw(mDesc, y, indent, isSelected);
|
||||||
|
if (cur_indent >= 0 && isSelected && mDesc.mItems[i].Selectable())
|
||||||
|
{
|
||||||
|
if (((MenuTime() % 8) < 6) || GetCurrentMenu() != self)
|
||||||
|
{
|
||||||
|
DrawConText(OptionMenuSettings.mFontColorSelection, cur_indent + 3 * CleanXfac_1, y+fontheight-9*CleanYfac_1, "\xd");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
y += fontheight;
|
||||||
|
}
|
||||||
|
|
||||||
|
CanScrollUp = (mDesc.mScrollPos > 0);
|
||||||
|
CanScrollDown = (i < mDesc.mItems.Size());
|
||||||
|
VisBottom = i - 1;
|
||||||
|
|
||||||
|
if (CanScrollUp)
|
||||||
|
{
|
||||||
|
DrawConText(Font.CR_ORANGE, 3 * CleanXfac_1, ytop, "\x1a");
|
||||||
|
}
|
||||||
|
if (CanScrollDown)
|
||||||
|
{
|
||||||
|
DrawConText(Font.CR_ORANGE, 3 * CleanXfac_1, y - 8*CleanYfac_1, "\x1b");
|
||||||
|
}
|
||||||
|
Super.Drawer();
|
||||||
|
}
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
override void SetFocus(MenuItemBase fc)
|
||||||
|
{
|
||||||
|
mFocusControl = OptionMenuItem(fc);
|
||||||
|
}
|
||||||
|
|
||||||
|
override bool CheckFocus(MenuItemBase fc)
|
||||||
|
{
|
||||||
|
return mFocusControl == fc;
|
||||||
|
}
|
||||||
|
|
||||||
|
override void ReleaseFocus()
|
||||||
|
{
|
||||||
|
mFocusControl = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
class GameplayMenu : OptionMenu
|
class GameplayMenu : OptionMenu
|
||||||
|
@ -29,3 +461,9 @@ class CompatibilityMenu : OptionMenu
|
||||||
DTA_CleanNoMove_1, true);
|
DTA_CleanNoMove_1, true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
class JoystickConfigMenu : OptionMenu
|
||||||
|
{
|
||||||
|
// This is not really needed anymore but needs to be kept for old MENUDEFs that keep the entry
|
||||||
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue