Skip to content

Commit

Permalink
Formspecs: Close on metadata removal (#8348)
Browse files Browse the repository at this point in the history
Formspecs will now close as soon the formspec string in the node metadata turns invalid.
  • Loading branch information
SmallJoker committed Jun 10, 2019
1 parent e40be61 commit e2f8f4d
Show file tree
Hide file tree
Showing 4 changed files with 85 additions and 39 deletions.
91 changes: 52 additions & 39 deletions src/client/game.cpp
Expand Up @@ -827,10 +827,6 @@ class Game {

ChatBackend *chat_backend = nullptr;

GUIFormSpecMenu *current_formspec = nullptr;
//default: "". If other than "", empty show_formspec packets will only close the formspec when the formname matches
std::string cur_formname;

EventManager *eventmgr = nullptr;
QuicktuneShortcutter *quicktune = nullptr;
bool registration_confirmation_shown = false;
Expand Down Expand Up @@ -1143,8 +1139,9 @@ void Game::shutdown()
driver->setRenderTarget(irr::video::ERT_STEREO_BOTH_BUFFERS);
}
#endif
if (current_formspec)
current_formspec->quitMenu();
auto formspec = m_game_ui->getFormspecGUI();
if (formspec)
formspec->quitMenu();

showOverlayMessage(N_("Shutting down..."), 0, 0, false);

Expand All @@ -1163,10 +1160,7 @@ void Game::shutdown()
g_menumgr.deletingMenu(g_menumgr.m_stack.front());
}

if (current_formspec) {
current_formspec->drop();
current_formspec = NULL;
}
m_game_ui->deleteFormspec();

chat_backend->addMessage(L"", L"# Disconnected.");
chat_backend->addMessage(L"", L"");
Expand Down Expand Up @@ -1853,8 +1847,9 @@ void Game::processUserInput(f32 dtime)
input->step(dtime);

#ifdef __ANDROID__
if (current_formspec != NULL)
current_formspec->getAndroidUIInput();
auto formspec = m_game_ui->getFormspecGUI();
if (formspec)
formspec->getAndroidUIInput();
else
handleAndroidChatInput();
#endif
Expand Down Expand Up @@ -2050,10 +2045,11 @@ void Game::openInventory()
if (!client->moddingEnabled()
|| !client->getScript()->on_inventory_open(fs_src->m_client->getInventory(inventoryloc))) {
TextDest *txt_dst = new TextDestPlayerInventory(client);
GUIFormSpecMenu::create(current_formspec, client, &input->joystick, fs_src,
auto *&formspec = m_game_ui->updateFormspec("");
GUIFormSpecMenu::create(formspec, client, &input->joystick, fs_src,
txt_dst, client->getFormspecPrepend());
cur_formname = "";
current_formspec->setFormSpec(fs_src->getForm(), inventoryloc);

formspec->setFormSpec(fs_src->getForm(), inventoryloc);
}
}

Expand Down Expand Up @@ -2581,19 +2577,20 @@ void Game::handleClientEvent_Deathscreen(ClientEvent *event, CameraOrientation *
void Game::handleClientEvent_ShowFormSpec(ClientEvent *event, CameraOrientation *cam)
{
if (event->show_formspec.formspec->empty()) {
if (current_formspec && (event->show_formspec.formname->empty()
|| *(event->show_formspec.formname) == cur_formname)) {
current_formspec->quitMenu();
auto formspec = m_game_ui->getFormspecGUI();
if (formspec && (event->show_formspec.formname->empty()
|| *(event->show_formspec.formname) == m_game_ui->getFormspecName())) {
formspec->quitMenu();
}
} else {
FormspecFormSource *fs_src =
new FormspecFormSource(*(event->show_formspec.formspec));
TextDestPlayerInventory *txt_dst =
new TextDestPlayerInventory(client, *(event->show_formspec.formname));

GUIFormSpecMenu::create(current_formspec, client, &input->joystick,
auto *&formspec = m_game_ui->updateFormspec(*(event->show_formspec.formname));
GUIFormSpecMenu::create(formspec, client, &input->joystick,
fs_src, txt_dst, client->getFormspecPrepend());
cur_formname = *(event->show_formspec.formname);
}

delete event->show_formspec.formspec;
Expand All @@ -2605,7 +2602,7 @@ void Game::handleClientEvent_ShowLocalFormSpec(ClientEvent *event, CameraOrienta
FormspecFormSource *fs_src = new FormspecFormSource(*event->show_formspec.formspec);
LocalFormspecHandler *txt_dst =
new LocalFormspecHandler(*event->show_formspec.formname, client);
GUIFormSpecMenu::create(current_formspec, client, &input->joystick,
GUIFormSpecMenu::create(m_game_ui->getFormspecGUI(), client, &input->joystick,
fs_src, txt_dst, client->getFormspecPrepend());

delete event->show_formspec.formspec;
Expand Down Expand Up @@ -3272,11 +3269,11 @@ void Game::handlePointingAtNode(const PointedThing &pointed,
&client->getEnv().getClientMap(), nodepos);
TextDest *txt_dst = new TextDestNodeMetadata(nodepos, client);

GUIFormSpecMenu::create(current_formspec, client, &input->joystick, fs_src,
auto *&formspec = m_game_ui->updateFormspec("");
GUIFormSpecMenu::create(formspec, client, &input->joystick, fs_src,
txt_dst, client->getFormspecPrepend());
cur_formname.clear();

current_formspec->setFormSpec(meta->getString("formspec"), inventoryloc);
formspec->setFormSpec(meta->getString("formspec"), inventoryloc);
} else {
// Report right click to server

Expand Down Expand Up @@ -3844,14 +3841,28 @@ void Game::updateFrame(ProfilerGraph *graph, RunStats *stats, f32 dtime,
1. Delete formspec menu reference if menu was removed
2. Else, make sure formspec menu is on top
*/
if (current_formspec) {
if (current_formspec->getReferenceCount() == 1) {
current_formspec->drop();
current_formspec = NULL;
} else if (isMenuActive()) {
guiroot->bringToFront(current_formspec);
auto formspec = m_game_ui->getFormspecGUI();
do { // breakable. only runs for one iteration
if (!formspec)
break;

if (formspec->getReferenceCount() == 1) {
m_game_ui->deleteFormspec();
break;
}
}

auto &loc = formspec->getFormspecLocation();
if (loc.type == InventoryLocation::NODEMETA) {
NodeMetadata *meta = client->getEnv().getClientMap().getNodeMetadata(loc.p);
if (!meta || meta->getString("formspec").empty()) {
formspec->quitMenu();
break;
}
}

if (isMenuActive())
guiroot->bringToFront(formspec);
} while (false);

/*
Drawing begins
Expand Down Expand Up @@ -4048,7 +4059,7 @@ void Game::extendedResourceCleanup()

void Game::showDeathFormspec()
{
static std::string formspec =
static std::string formspec_str =
std::string(FORMSPEC_VERSION_STRING) +
SIZE_TAG
"bgcolor[#320000b4;true]"
Expand All @@ -4059,12 +4070,13 @@ void Game::showDeathFormspec()
/* Create menu */
/* Note: FormspecFormSource and LocalFormspecHandler *
* are deleted by guiFormSpecMenu */
FormspecFormSource *fs_src = new FormspecFormSource(formspec);
FormspecFormSource *fs_src = new FormspecFormSource(formspec_str);
LocalFormspecHandler *txt_dst = new LocalFormspecHandler("MT_DEATH_SCREEN", client);

GUIFormSpecMenu::create(current_formspec, client, &input->joystick, fs_src,
txt_dst, client->getFormspecPrepend());
current_formspec->setFocus("btn_respawn");
auto *&formspec = m_game_ui->getFormspecGUI();
GUIFormSpecMenu::create(formspec, client, &input->joystick,
fs_src, txt_dst, client->getFormspecPrepend());
formspec->setFocus("btn_respawn");
}

#define GET_KEY_NAME(KEY) gettext(getKeySetting(#KEY).name())
Expand Down Expand Up @@ -4188,10 +4200,11 @@ void Game::showPauseMenu()
FormspecFormSource *fs_src = new FormspecFormSource(os.str());
LocalFormspecHandler *txt_dst = new LocalFormspecHandler("MT_PAUSE_MENU");

GUIFormSpecMenu::create(current_formspec, client, &input->joystick,
auto *&formspec = m_game_ui->getFormspecGUI();
GUIFormSpecMenu::create(formspec, client, &input->joystick,
fs_src, txt_dst, client->getFormspecPrepend());
current_formspec->setFocus("btn_continue");
current_formspec->doPause = true;
formspec->setFocus("btn_continue");
formspec->doPause = true;
}

/****************************************************************************/
Expand Down
12 changes: 12 additions & 0 deletions src/client/gameui.cpp
Expand Up @@ -302,3 +302,15 @@ void GameUI::toggleProfiler()
showTranslatedStatusText("Profiler hidden");
}
}


void GameUI::deleteFormspec()
{
if (m_formspec)
m_formspec->quitMenu();

delete m_formspec;
m_formspec = nullptr;

m_formname.clear();
}
16 changes: 16 additions & 0 deletions src/client/gameui.h
Expand Up @@ -21,6 +21,7 @@ with this program; if not, write to the Free Software Foundation, Inc.,
#pragma once

#include <IGUIEnvironment.h>
#include "gui/guiFormSpecMenu.h"
#include "util/enriched_string.h"
#include "util/pointedthing.h"
#include "game.h"
Expand Down Expand Up @@ -88,6 +89,16 @@ class GameUI
void toggleHud();
void toggleProfiler();

GUIFormSpecMenu *&updateFormspec(const std::string &formname)
{
m_formname = formname;
return m_formspec;
}

const std::string &getFormspecName() { return m_formname; }
GUIFormSpecMenu *&getFormspecGUI() { return m_formspec; }
void deleteFormspec();

private:
Flags m_flags;

Expand All @@ -107,4 +118,9 @@ class GameUI
gui::IGUIStaticText *m_guitext_profiler = nullptr; // Profiler text
u8 m_profiler_current_page = 0;
const u8 m_profiler_max_page = 3;

// Default: "". If other than "": Empty show_formspec packets will only
// close the formspec when the formname matches
std::string m_formname;
GUIFormSpecMenu *m_formspec = nullptr;
};
5 changes: 5 additions & 0 deletions src/gui/guiFormSpecMenu.h
Expand Up @@ -304,6 +304,11 @@ class GUIFormSpecMenu : public GUIModalMenu
regenerateGui(m_screensize_old);
}

const InventoryLocation &getFormspecLocation()
{
return m_current_inventory_location;
}

void setFormspecPrepend(const std::string &formspecPrepend)
{
m_formspec_prepend = formspecPrepend;
Expand Down

0 comments on commit e2f8f4d

Please sign in to comment.