Stateful editing

This commit is contained in:
Learath 2020-02-28 18:25:27 +03:00
parent f2103881c8
commit d2498f257c
4 changed files with 129 additions and 99 deletions

View file

@ -1309,7 +1309,7 @@ void CEditor::DoToolbar(CUIRect ToolBar)
{
TB_Bottom.VSplitLeft(60.0f, &Button, &TB_Bottom);
{
int (*pPopupFunc)(CEditor *peditor, CUIRect View) = NULL;
int (*pPopupFunc)(CEditor *peditor, CUIRect View, void *pContext) = NULL;
const char *aButtonName = "Modifier";
float Height = 0.0f;
int Checked = -1;
@ -3482,9 +3482,29 @@ void CEditor::RenderLayers(CUIRect ToolBox, CUIRect View)
m_SelectedGroup = g;
SelectLayer(i);
}
static int s_LayerPopupID = 0;
static CLayerPopupContext s_LayerPopupContext = {};
if(Result == 2)
UiInvokePopupMenu(&s_LayerPopupID, 0, UI()->MouseX(), UI()->MouseY(), 120, 300, PopupLayer);
{
if(m_lSelectedLayers.size() > 1)
{
bool AllTile = true;
for(int i = 0; AllTile && i < m_lSelectedLayers.size(); i++)
{
if(m_Map.m_lGroups[m_SelectedGroup]->m_lLayers[i]->m_Type == LAYERTYPE_TILES)
s_LayerPopupContext.m_aLayers.add((CLayerTiles *)m_Map.m_lGroups[m_SelectedGroup]->m_lLayers[i]);
else
AllTile = false;
}
// Don't allow editing if all selected layers are tile layers
if(!AllTile)
s_LayerPopupContext.m_aLayers.clear();
}
else
s_LayerPopupContext.m_aLayers.clear();
UiInvokePopupMenu(&s_LayerPopupContext, 0, UI()->MouseX(), UI()->MouseY(), 120, 300, PopupLayer, &s_LayerPopupContext);
}
}
LayerCur += 14.0f;
@ -3694,7 +3714,7 @@ static void ModifyIndexDeleted(int *pIndex)
*pIndex = *pIndex - 1;
}
int CEditor::PopupImage(CEditor *pEditor, CUIRect View)
int CEditor::PopupImage(CEditor *pEditor, CUIRect View, void *pContext)
{
static int s_ReplaceButton = 0;
static int s_RemoveButton = 0;
@ -3744,7 +3764,7 @@ int CEditor::PopupImage(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupSound(CEditor *pEditor, CUIRect View)
int CEditor::PopupSound(CEditor *pEditor, CUIRect View, void *pContext)
{
static int s_ReplaceButton = 0;
static int s_RemoveButton = 0;
@ -5440,7 +5460,7 @@ void CEditor::RenderServerSettingsEditor(CUIRect View)
UI()->ClipDisable();
}
int CEditor::PopupMenuFile(CEditor *pEditor, CUIRect View)
int CEditor::PopupMenuFile(CEditor *pEditor, CUIRect View, void *pContext)
{
static int s_NewMapButton = 0;
static int s_SaveButton = 0;

View file

@ -537,7 +537,13 @@ public:
virtual void ShowInfo();
virtual int RenderProperties(CUIRect *pToolbox);
static int RenderCommonProperties(CEditor *pEditor, CUIRect *pToolbox, array<CLayerTiles *> &pLayers);
struct SCommonPropState {
bool Modified = false;
int Width = -1;
int Height = -1;
int Color = 0;
};
static int RenderCommonProperties(SCommonPropState &State, CEditor *pEditor, CUIRect *pToolbox, array<CLayerTiles *> &pLayers);
virtual void ModifyImageIndex(INDEX_MODIFY_FUNC pfnFunc);
virtual void ModifyEnvelopeIndex(INDEX_MODIFY_FUNC pfnFunc);
@ -948,28 +954,34 @@ public:
void RenderGrid(CLayerGroup *pGroup);
void UiInvokePopupMenu(void *pID, int Flags, float X, float Y, float W, float H, int (*pfnFunc)(CEditor *pEditor, CUIRect Rect), void *pExtra=0);
void UiInvokePopupMenu(void *pID, int Flags, float X, float Y, float W, float H, int (*pfnFunc)(CEditor *pEditor, CUIRect Rect, void *pContext), void *pExtra=0);
void UiDoPopupMenu();
int UiDoValueSelector(void *pID, CUIRect *pRect, const char *pLabel, int Current, int Min, int Max, int Step, float Scale, const char *pToolTip, bool IsDegree=false, bool IsHex=false, int corners=CUI::CORNER_ALL, ColorRGBA* Color=0);
static int PopupGroup(CEditor *pEditor, CUIRect View);
static int PopupLayer(CEditor *pEditor, CUIRect View);
static int PopupQuad(CEditor *pEditor, CUIRect View);
static int PopupPoint(CEditor *pEditor, CUIRect View);
static int PopupNewFolder(CEditor *pEditor, CUIRect View);
static int PopupMapInfo(CEditor *pEditor, CUIRect View);
static int PopupEvent(CEditor *pEditor, CUIRect View);
static int PopupSelectImage(CEditor *pEditor, CUIRect View);
static int PopupSelectSound(CEditor *pEditor, CUIRect View);
static int PopupSelectGametileOp(CEditor *pEditor, CUIRect View);
static int PopupImage(CEditor *pEditor, CUIRect View);
static int PopupMenuFile(CEditor *pEditor, CUIRect View);
static int PopupSelectConfigAutoMap(CEditor *pEditor, CUIRect View);
static int PopupSound(CEditor *pEditor, CUIRect View);
static int PopupSource(CEditor *pEditor, CUIRect View);
static int PopupColorPicker(CEditor *pEditor, CUIRect View);
static int PopupEntities(CEditor *pEditor, CUIRect View);
static int PopupGroup(CEditor *pEditor, CUIRect View, void *pContext);
struct CLayerPopupContext
{
array<CLayerTiles *> m_aLayers;
CLayerTiles::SCommonPropState m_CommonPropState;
};
static int PopupLayer(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupQuad(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupPoint(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupNewFolder(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupMapInfo(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupEvent(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupSelectImage(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupSelectSound(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupSelectGametileOp(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupImage(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupMenuFile(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupSelectConfigAutoMap(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupSound(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupSource(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupColorPicker(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupEntities(CEditor *pEditor, CUIRect View, void *pContext);
static void CallbackOpenMap(const char *pFileName, int StorageType, void *pUser);
static void CallbackAppendMap(const char *pFileName, int StorageType, void *pUser);
@ -1039,10 +1051,10 @@ public:
IGraphics::CTextureHandle m_SpeedupTexture;
IGraphics::CTextureHandle m_SwitchTexture;
IGraphics::CTextureHandle m_TuneTexture;
static int PopupTele(CEditor *pEditor, CUIRect View);
static int PopupSpeedup(CEditor *pEditor, CUIRect View);
static int PopupSwitch(CEditor *pEditor, CUIRect View);
static int PopupTune(CEditor *pEditor, CUIRect View);
static int PopupTele(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupSpeedup(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupSwitch(CEditor *pEditor, CUIRect View, void *pContext);
static int PopupTune(CEditor *pEditor, CUIRect View, void *pContext);
unsigned char m_TeleNumber;
unsigned char m_TuningNum;

View file

@ -961,8 +961,40 @@ int CLayerTiles::RenderProperties(CUIRect *pToolBox)
return 0;
}
int CLayerTiles::RenderCommonProperties(CEditor *pEditor, CUIRect *pToolbox, array<CLayerTiles *> &pLayers)
int CLayerTiles::RenderCommonProperties(SCommonPropState &State, CEditor *pEditor, CUIRect *pToolbox, array<CLayerTiles *> &pLayers)
{
if(State.Modified)
{
CUIRect Commit;
pToolbox->HSplitBottom(20.0f, pToolbox, &Commit);
static int s_CommitButton = 0;
if(pEditor->DoButton_Editor(&s_CommitButton, "Commit", 0, &Commit, 0, "Applies the changes"))
{
dbg_msg("editor", "applying changes");
for_each(pLayers.all(), [&State](CLayerTiles *pLayer){
pLayer->Resize(State.Width, State.Height);
pLayer->m_Color.r = (State.Color>>24)&0xff;
pLayer->m_Color.g = (State.Color>>16)&0xff;
pLayer->m_Color.b = (State.Color>>8)&0xff;
pLayer->m_Color.a = State.Color&0xff;
pLayer->FlagModified(0, 0, pLayer->m_Width, pLayer->m_Height);
});
State.Modified = false;
}
}
else
{
for_each(pLayers.all(), [&State](CLayerTiles *pLayer){
if(pLayer->m_Width > State.Width)
State.Width = pLayer->m_Width;
if(pLayer->m_Height > State.Height)
State.Height = pLayer->m_Height;
});
}
{
CUIRect Warning;
pToolbox->HSplitTop(13.0f, &Warning, pToolbox);
@ -984,22 +1016,12 @@ int CLayerTiles::RenderCommonProperties(CEditor *pEditor, CUIRect *pToolbox, arr
NUM_PROPS,
};
int Width = 1;
int Height = 1;
for_each(pLayers.all(), [&Width, &Height](CLayerTiles *pLayer){
if(pLayer->m_Width > Width)
Width = pLayer->m_Width;
if(pLayer->m_Height > Height)
Height = pLayer->m_Height;
});
int Color = 0;
CProperty aProps[] = {
{"Width", Width, PROPTYPE_INT_SCROLL, 1, 100000},
{"Height", Height, PROPTYPE_INT_SCROLL, 1, 100000},
{"Width", State.Width, PROPTYPE_INT_SCROLL, 1, 100000},
{"Height", State.Height, PROPTYPE_INT_SCROLL, 1, 100000},
{"Shift", 0, PROPTYPE_SHIFT, 0, 0},
{"Shift by", pEditor->m_ShiftBy, PROPTYPE_INT_SCROLL, 1, 100000},
{"Color", Color, PROPTYPE_COLOR, 0, 0},
{"Color", State.Color, PROPTYPE_COLOR, 0, 0},
{0},
};
@ -1015,9 +1037,7 @@ int CLayerTiles::RenderCommonProperties(CEditor *pEditor, CUIRect *pToolbox, arr
pEditor->m_PopupEventActivated = true;
pEditor->m_LargeLayerWasWarned = true;
}
for_each(pLayers.all(), [NewVal](CLayerTiles *pLayer){
pLayer->Resize(NewVal, pLayer->m_Height);
});
State.Width = NewVal;
}
else if(Prop == PROP_HEIGHT && NewVal > 1)
{
@ -1027,10 +1047,7 @@ int CLayerTiles::RenderCommonProperties(CEditor *pEditor, CUIRect *pToolbox, arr
pEditor->m_PopupEventActivated = true;
pEditor->m_LargeLayerWasWarned = true;
}
for_each(pLayers.all(), [NewVal](CLayerTiles *pLayer){
pLayer->Resize(pLayer->m_Width, NewVal);
});
State.Height = NewVal;
}
else if(Prop == PROP_SHIFT)
{
@ -1042,19 +1059,12 @@ int CLayerTiles::RenderCommonProperties(CEditor *pEditor, CUIRect *pToolbox, arr
pEditor->m_ShiftBy = NewVal;
else if(Prop == PROP_COLOR)
{
for_each(pLayers.all(), [NewVal](CLayerTiles *pLayer){
pLayer->m_Color.r = (NewVal>>24)&0xff;
pLayer->m_Color.g = (NewVal>>16)&0xff;
pLayer->m_Color.b = (NewVal>>8)&0xff;
pLayer->m_Color.a = NewVal&0xff;
});
State.Color = NewVal;
}
if(Prop != -1)
if(Prop != -1 && Prop != PROP_SHIFT)
{
for_each(pLayers.all(), [](CLayerTiles *pLayer){
pLayer->FlagModified(0, 0, pLayer->m_Width, pLayer->m_Height);
});
State.Modified = true;
}
return 0;

View file

@ -18,14 +18,14 @@ static struct
{
CUIRect m_Rect;
void *m_pId;
int (*m_pfnFunc)(CEditor *pEditor, CUIRect Rect);
int (*m_pfnFunc)(CEditor *pEditor, CUIRect Rect, void *pContext);
int m_IsMenu;
void *m_pExtra;
void *m_pContext;
} s_UiPopups[8];
static int g_UiNumPopups = 0;
void CEditor::UiInvokePopupMenu(void *pID, int Flags, float x, float y, float Width, float Height, int (*pfnFunc)(CEditor *pEditor, CUIRect Rect), void *pExtra)
void CEditor::UiInvokePopupMenu(void *pID, int Flags, float x, float y, float Width, float Height, int (*pfnFunc)(CEditor *pEditor, CUIRect Rect, void *pContext), void *pContext)
{
if(g_UiNumPopups > 7)
return;
@ -41,7 +41,7 @@ void CEditor::UiInvokePopupMenu(void *pID, int Flags, float x, float y, float Wi
s_UiPopups[g_UiNumPopups].m_Rect.w = Width;
s_UiPopups[g_UiNumPopups].m_Rect.h = Height;
s_UiPopups[g_UiNumPopups].m_pfnFunc = pfnFunc;
s_UiPopups[g_UiNumPopups].m_pExtra = pExtra;
s_UiPopups[g_UiNumPopups].m_pContext = pContext;
g_UiNumPopups++;
}
@ -80,7 +80,7 @@ void CEditor::UiDoPopupMenu()
RenderTools()->DrawUIRect(&r, ColorRGBA(0,0,0,0.75f), Corners, 3.0f);
r.Margin(4.0f, &r);
if(s_UiPopups[i].m_pfnFunc(this, r))
if(s_UiPopups[i].m_pfnFunc(this, r, s_UiPopups[i].m_pContext))
{
m_LockMouse = false;
UI()->SetActiveItem(0);
@ -99,7 +99,7 @@ void CEditor::UiDoPopupMenu()
}
int CEditor::PopupGroup(CEditor *pEditor, CUIRect View)
int CEditor::PopupGroup(CEditor *pEditor, CUIRect View, void *pContext)
{
// remove group button
CUIRect Button;
@ -357,30 +357,18 @@ int CEditor::PopupGroup(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupLayer(CEditor *pEditor, CUIRect View)
int CEditor::PopupLayer(CEditor *pEditor, CUIRect View, void *pContext)
{
CLayerPopupContext *pPopup = (CLayerPopupContext *)pContext;
// remove layer button
CUIRect Button;
View.HSplitBottom(12.0f, &View, &Button);
static int s_DeleteButton = 0;
if(pEditor->m_lSelectedLayers.size() > 1)
if(pPopup->m_aLayers.size() > 1)
{
array<CLayerTiles *> apLayers;
bool AllTile = true;
for(int i = 0; AllTile && i < pEditor->m_lSelectedLayers.size(); i++)
{
if(pEditor->m_Map.m_lGroups[pEditor->m_SelectedGroup]->m_lLayers[i]->m_Type == LAYERTYPE_TILES)
apLayers.add((CLayerTiles *)pEditor->m_Map.m_lGroups[pEditor->m_SelectedGroup]->m_lLayers[i]);
else
AllTile = false;
}
// Don't allow editing if all selected layers are tile layers
if(!AllTile)
return 1;
return CLayerTiles::RenderCommonProperties(pEditor, &View, apLayers);
return CLayerTiles::RenderCommonProperties(pPopup->m_CommonPropState, pEditor, &View, pPopup->m_aLayers);
}
// don't allow deletion of game layer
@ -471,7 +459,7 @@ int CEditor::PopupLayer(CEditor *pEditor, CUIRect View)
return pCurrentLayer->RenderProperties(&View);
}
int CEditor::PopupQuad(CEditor *pEditor, CUIRect View)
int CEditor::PopupQuad(CEditor *pEditor, CUIRect View, void *pContext)
{
array<CQuad *> lQuads = pEditor->GetSelectedQuads();
CQuad *pCurrentQuad = lQuads[pEditor->m_SelectedQuadIndex];
@ -653,7 +641,7 @@ int CEditor::PopupQuad(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupSource(CEditor *pEditor, CUIRect View)
int CEditor::PopupSource(CEditor *pEditor, CUIRect View, void *pContext)
{
CSoundSource *pSource = pEditor->GetSelectedSource();
@ -847,7 +835,7 @@ int CEditor::PopupSource(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupPoint(CEditor *pEditor, CUIRect View)
int CEditor::PopupPoint(CEditor *pEditor, CUIRect View, void *pContext)
{
array<CQuad *> lQuads = pEditor->GetSelectedQuads();
CQuad *pCurrentQuad = lQuads[pEditor->m_SelectedQuadIndex];
@ -937,7 +925,7 @@ int CEditor::PopupPoint(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupNewFolder(CEditor *pEditor, CUIRect View)
int CEditor::PopupNewFolder(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect Label, ButtonBar;
@ -1006,7 +994,7 @@ int CEditor::PopupNewFolder(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupMapInfo(CEditor *pEditor, CUIRect View)
int CEditor::PopupMapInfo(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect Label, ButtonBar, Button;
@ -1074,7 +1062,7 @@ int CEditor::PopupMapInfo(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupEvent(CEditor *pEditor, CUIRect View)
int CEditor::PopupEvent(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect Label, ButtonBar;
@ -1156,7 +1144,7 @@ int CEditor::PopupEvent(CEditor *pEditor, CUIRect View)
static int g_SelectImageSelected = -100;
static int g_SelectImageCurrent = -100;
int CEditor::PopupSelectImage(CEditor *pEditor, CUIRect View)
int CEditor::PopupSelectImage(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect ButtonBar, ImageView;
View.VSplitLeft(80.0f, &ButtonBar, &View);
@ -1268,7 +1256,7 @@ int CEditor::PopupSelectImageResult()
static int g_SelectSoundSelected = -100;
static int g_SelectSoundCurrent = -100;
int CEditor::PopupSelectSound(CEditor *pEditor, CUIRect View)
int CEditor::PopupSelectSound(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect ButtonBar, SoundView;
View.VSplitLeft(80.0f, &ButtonBar, &View);
@ -1359,7 +1347,7 @@ int CEditor::PopupSelectSoundResult()
static int s_GametileOpSelected = -1;
int CEditor::PopupSelectGametileOp(CEditor *pEditor, CUIRect View)
int CEditor::PopupSelectGametileOp(CEditor *pEditor, CUIRect View, void *pContext)
{
static const char *s_pButtonNames[] = { "Air", "Hookable", "Death", "Unhookable", "Hookthrough", "Freeze", "Unfreeze", "Deep Freeze", "Deep Unfreeze", "Blue Check-Tele", "Red Check-Tele" };
static unsigned s_NumButtons = sizeof(s_pButtonNames) / sizeof(char*);
@ -1396,7 +1384,7 @@ int CEditor::PopupSelectGameTileOpResult()
static int s_AutoMapConfigSelected = -100;
static int s_AutoMapConfigCurrent = -100;
int CEditor::PopupSelectConfigAutoMap(CEditor *pEditor, CUIRect View)
int CEditor::PopupSelectConfigAutoMap(CEditor *pEditor, CUIRect View, void *pContext)
{
CLayerTiles *pLayer = static_cast<CLayerTiles*>(pEditor->GetSelectedLayer(0));
CUIRect Button;
@ -1435,7 +1423,7 @@ int CEditor::PopupSelectConfigAutoMapResult()
// DDRace
int CEditor::PopupTele(CEditor *pEditor, CUIRect View)
int CEditor::PopupTele(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect Button;
View.HSplitBottom(12.0f, &View, &Button);
@ -1483,7 +1471,7 @@ int CEditor::PopupTele(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupSpeedup(CEditor *pEditor, CUIRect View)
int CEditor::PopupSpeedup(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect Button;
View.HSplitBottom(12.0f, &View, &Button);
@ -1517,7 +1505,7 @@ int CEditor::PopupSpeedup(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupSwitch(CEditor *pEditor, CUIRect View)
int CEditor::PopupSwitch(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect Button;
View.HSplitBottom(12.0f, &View, &Button);
@ -1568,7 +1556,7 @@ int CEditor::PopupSwitch(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupTune(CEditor *pEditor, CUIRect View)
int CEditor::PopupTune(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect Button;
View.HSplitBottom(12.0f, &View, &Button);
@ -1594,7 +1582,7 @@ int CEditor::PopupTune(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupColorPicker(CEditor *pEditor, CUIRect View)
int CEditor::PopupColorPicker(CEditor *pEditor, CUIRect View, void *pContext)
{
CUIRect SVPicker, HuePicker;
View.VSplitRight(20.0f, &SVPicker, &HuePicker);
@ -1696,7 +1684,7 @@ int CEditor::PopupColorPicker(CEditor *pEditor, CUIRect View)
return 0;
}
int CEditor::PopupEntities(CEditor *pEditor, CUIRect View)
int CEditor::PopupEntities(CEditor *pEditor, CUIRect View, void *pContext)
{
for(int i = 0; i < (int)pEditor->m_SelectEntitiesFiles.size(); i++)
{