merge IFormSource and TextDest into FormIO

master
darkrose 2014-10-30 23:00:42 +10:00
parent c48399628e
commit 9078f10541
8 changed files with 149 additions and 181 deletions

View File

@ -1569,7 +1569,7 @@ void Client::clickActiveObject(u8 button, u16 id, u16 item_i)
}
void Client::sendNodemetaFields(v3s16 p, const std::string &formname,
const std::map<std::string, std::string> &fields)
const std::map<std::string, std::wstring> &fields)
{
std::ostringstream os(std::ios_base::binary);
u8 buf[12];
@ -1587,11 +1587,11 @@ void Client::sendNodemetaFields(v3s16 p, const std::string &formname,
// Write number of fields
writeU16(buf, fields.size());
os.write((char*)buf, 2);
for (std::map<std::string, std::string>::const_iterator i = fields.begin(); i != fields.end(); i++) {
for (std::map<std::string, std::wstring>::const_iterator i = fields.begin(); i != fields.end(); i++) {
const std::string &name = i->first;
const std::string &value = i->second;
const std::wstring &value = i->second;
os<<serializeString(name);
os<<serializeLongString(value);
os<<serializeLongWideString(value);
}
// Make data buffer

View File

@ -204,7 +204,7 @@ public:
void clickActiveObject(u8 button, u16 id, u16 item_i);
void sendNodemetaFields(v3s16 p, const std::string &formname,
const std::map<std::string, std::string> &fields);
const std::map<std::string, std::wstring> &fields);
void sendInventoryAction(InventoryAction *a);
void sendChatMessage(const std::wstring &message);
void sendChangePassword(const std::wstring oldpassword,

View File

@ -103,58 +103,34 @@ u16 g_selected_item = 0;
Text input system
*/
struct TextDestChat : public TextDest
class ChatFormIO : public FormIO
{
TextDestChat(Client *client)
public:
ChatFormIO(Client *client)
{
m_client = client;
}
void gotText(std::wstring text)
void gotText(std::map<std::string, std::wstring> fields)
{
// Discard empty line
if(text == L"")
if (fields["text"] == L"")
return;
// Send to others
m_client->sendChatMessage(text);
m_client->sendChatMessage(fields["text"]);
// Show locally
m_client->addChatMessage(text);
m_client->addChatMessage(fields["text"]);
}
void gotText(std::map<std::string, std::string> fields)
std::string getForm()
{
gotText(narrow_to_wide(fields["text"]));
return "";
}
Client *m_client;
};
struct TextDestNodeMetadata : public TextDest
{
TextDestNodeMetadata(v3s16 p, Client *client)
{
m_p = p;
m_client = client;
}
// This is deprecated I guess? -celeron55
void gotText(std::wstring text)
{
std::string ntext = wide_to_narrow(text);
infostream<<"Submitting 'text' field of node at ("<<m_p.X<<","
<<m_p.Y<<","<<m_p.Z<<"): "<<ntext<<std::endl;
std::map<std::string, std::string> fields;
fields["text"] = ntext;
m_client->sendNodemetaFields(m_p, "", fields);
}
void gotText(std::map<std::string, std::string> fields)
{
m_client->sendNodemetaFields(m_p, "", fields);
}
v3s16 m_p;
Client *m_client;
};
/* Respawn menu callback */
class MainRespawnInitiator: public IRespawnInitiator
@ -177,18 +153,18 @@ private:
/* Form update callback */
class NodeMetadataFormSource: public IFormSource
class NodeMetadataFormIO: public FormIO
{
public:
NodeMetadataFormSource(ClientMap *map, v3s16 p):
m_map(map),
NodeMetadataFormIO(v3s16 p, Client *client):
m_client(client),
m_p(p)
{
}
std::string getForm()
{
NodeMetadata *meta = m_map->getNodeMetadata(m_p);
NodeMetadata *meta = m_client->getEnv().getMap().getNodeMetadata(m_p);
if (!meta)
return "";
return meta->getDrawSpecString();
@ -196,18 +172,24 @@ public:
NodeMetadata *getMeta()
{
return m_map->getNodeMetadata(m_p);
return m_client->getEnv().getMap().getNodeMetadata(m_p);
}
ClientMap *m_map;
void gotText(std::map<std::string, std::wstring> fields)
{
m_client->sendNodemetaFields(m_p, "", fields);
}
Client *m_client;
v3s16 m_p;
};
class PlayerInventoryFormSource: public IFormSource
class PlayerInventoryFormIO: public FormIO
{
public:
PlayerInventoryFormSource(Client *client):
m_client(client)
PlayerInventoryFormIO(Client *client):
m_show_appearance(false),
m_client(client)
{
}
std::string getForm()
@ -226,6 +208,16 @@ public:
"list[current_player;craftresult;7,2;1,1;]";
}
void gotText(std::map<std::string, std::wstring> fields)
{
if (fields["show_appearance"] != L"") {
m_show_appearance = true;
}else{
m_show_appearance = false;
}
}
bool m_show_appearance;
Client *m_client;
};
@ -1280,10 +1272,10 @@ void the_game(
InventoryLocation inventoryloc;
inventoryloc.setCurrentPlayer();
PlayerInventoryFormSource *src = new PlayerInventoryFormSource(&client);
assert(src);
menu->setFormSpec(src->getForm(), inventoryloc);
menu->setFormSource(src);
PlayerInventoryFormIO *fio = new PlayerInventoryFormIO(&client);
assert(fio);
menu->setFormSpec(fio->getForm(), inventoryloc);
menu->setFormIO(fio);
menu->drop();
}
else if(input->wasKeyDown(EscapeKey))
@ -1299,19 +1291,15 @@ void the_game(
}
else if(input->wasKeyDown(getKeySetting("keymap_chat")))
{
TextDest *dest = new TextDestChat(&client);
FormIO *fio = new ChatFormIO(&client);
(new GUITextInputMenu(guienv, guiroot, -1,
&g_menumgr, dest,
L""))->drop();
(new GUITextInputMenu(guienv, guiroot, -1, &g_menumgr, fio, L""))->drop();
}
else if(input->wasKeyDown(getKeySetting("keymap_cmd")))
{
TextDest *dest = new TextDestChat(&client);
FormIO *fio = new ChatFormIO(&client);
(new GUITextInputMenu(guienv, guiroot, -1,
&g_menumgr, dest,
L"/"))->drop();
(new GUITextInputMenu(guienv, guiroot, -1, &g_menumgr, fio, L"/"))->drop();
}
else if(input->wasKeyDown(getKeySetting("keymap_freemove"))) {
if (g_settings->getBool("free_move")) {
@ -1871,13 +1859,11 @@ void the_game(
}
if(input->getRightClicked())
{
if (input->getRightClicked()) {
infostream<<"Ground right-clicked"<<std::endl;
// If metadata provides an inventory view, activate it
if(meta && meta->getDrawSpecString() != "" && !random_input)
{
if (meta && meta->getDrawSpecString() != "" && !random_input) {
infostream<<"Launching custom inventory view"<<std::endl;
InventoryLocation inventoryloc;
@ -1885,19 +1871,12 @@ void the_game(
/* Create menu */
GUIFormSpecMenu *menu =
new GUIFormSpecMenu(guienv, guiroot, -1,
&g_menumgr,
&client);
GUIFormSpecMenu *menu = new GUIFormSpecMenu(guienv, guiroot, -1, &g_menumgr, &client);
menu->setFormSpec(meta->getDrawSpecString(), inventoryloc);
menu->setFormSource(new NodeMetadataFormSource(
&client.getEnv().getClientMap(), nodepos));
menu->setTextDest(new TextDestNodeMetadata(nodepos, &client));
menu->setFormIO(new NodeMetadataFormIO(nodepos, &client));
menu->drop();
}
else
{
}else{
client.groundAction(1, nodepos, neighbourpos, g_selected_item);
camera.setDigging(1); // right click animation
}
@ -1908,22 +1887,18 @@ void the_game(
} // selected_object == NULL
if(left_punch || (input->getLeftClicked() && !left_punch_muted))
{
if (left_punch || (input->getLeftClicked() && !left_punch_muted))
camera.setDigging(0); // left click animation
}
input->resetLeftClicked();
input->resetRightClicked();
if(input->getLeftReleased())
{
if (input->getLeftReleased()) {
infostream<<"Left button released (stopped digging)"
<<std::endl;
client.groundAction(2, v3s16(0,0,0), v3s16(0,0,0), 0);
}
if(input->getRightReleased())
{
if (input->getRightReleased()) {
// Nothing here
}
@ -1947,33 +1922,29 @@ void the_game(
/*
Update skybox
*/
if(fabs(brightness - old_brightness) > 0.01)
if (fabs(brightness - old_brightness) > 0.01)
update_skybox(driver, smgr, skybox, brightness);
/*
Update clouds
*/
if(clouds)
{
if (clouds) {
clouds->step(dtime);
clouds->update(v2f(player_position.X, player_position.Z),
0.05+brightness*0.95);
clouds->update(v2f(player_position.X, player_position.Z), 0.05+brightness*0.95);
}
/*
Update farmesh
*/
if(farmesh)
{
if (farmesh) {
farmesh_range = draw_control.wanted_range * 10;
if(draw_control.range_all && farmesh_range < 500)
if (draw_control.range_all && farmesh_range < 500)
farmesh_range = 500;
if(farmesh_range > 1000)
if (farmesh_range > 1000)
farmesh_range = 1000;
farmesh->step(dtime);
farmesh->update(v2f(player_position.X, player_position.Z),
0.05+brightness*0.95, farmesh_range);
farmesh->update(v2f(player_position.X, player_position.Z), 0.05+brightness*0.95, farmesh_range);
}
/*

View File

@ -97,8 +97,7 @@ GUIFormSpecMenu::GUIFormSpecMenu(gui::IGUIEnvironment* env,
):
GUIModalMenu(env, parent, id, menumgr),
m_invmgr(invmgr),
m_form_src(NULL),
m_text_dst(NULL),
m_form_io(NULL),
m_selected_item(NULL),
m_selected_amount(0),
m_selected_dragging(false),
@ -111,8 +110,7 @@ GUIFormSpecMenu::~GUIFormSpecMenu()
removeChildren();
delete m_selected_item;
delete m_form_src;
delete m_text_dst;
delete m_form_io;
}
void GUIFormSpecMenu::removeChildren()
@ -297,10 +295,11 @@ void GUIFormSpecMenu::regenerateGui(v2u32 screensize)
// fdefault may contain a variable reference, which
// needs to be resolved from the node metadata
if(m_form_src)
fdefault = m_form_src->resolveText(odefault);
else
if (m_form_io) {
fdefault = m_form_io->resolveText(odefault);
}else{
fdefault = odefault;
}
FieldSpec spec = FieldSpec(
narrow_to_wide(fname.c_str()),
@ -579,8 +578,8 @@ void GUIFormSpecMenu::drawList(const ListDrawSpec &s, int phase)
void GUIFormSpecMenu::drawMenu()
{
if (m_form_src) {
std::string newform = m_form_src->getForm();
if (m_form_io) {
std::string newform = m_form_io->getForm();
if (newform != m_formspec_string) {
m_formspec_string = newform;
regenerateGui(m_screensize_old);
@ -632,30 +631,22 @@ void GUIFormSpecMenu::drawMenu()
void GUIFormSpecMenu::acceptInput()
{
if(m_text_dst)
{
std::map<std::string, std::string> fields;
if (m_form_io) {
std::map<std::string, std::wstring> fields;
gui::IGUIElement *e;
for(u32 i=0; i<m_fields.size(); i++)
{
for (u32 i=0; i<m_fields.size(); i++) {
const FieldSpec &s = m_fields[i];
if(s.send)
{
if(s.is_button)
{
fields[wide_to_narrow(s.fname.c_str())] = wide_to_narrow(s.flabel.c_str());
}
else
{
if (s.send) {
if (s.is_button) {
fields[wide_to_narrow(s.fname.c_str())] = s.flabel.c_str();
}else{
e = getElementFromId(s.fid);
if(e != NULL)
{
fields[wide_to_narrow(s.fname.c_str())] = wide_to_narrow(e->getText());
}
if (e != NULL)
fields[wide_to_narrow(s.fname.c_str())] = e->getText();
}
}
}
m_text_dst->gotText(fields);
m_form_io->gotText(fields);
}
}

View File

@ -30,21 +30,13 @@ with this program; if not, write to the Free Software Foundation, Inc.,
class InventoryManager;
struct TextDest
{
virtual ~TextDest() {};
// This is deprecated I guess? -celeron55
virtual void gotText(std::wstring text) = 0;
virtual void gotText(std::map<std::string, std::string> fields) = 0;
};
class IFormSource
class FormIO
{
public:
virtual ~IFormSource(){}
virtual ~FormIO(){}
virtual std::string getForm() = 0;
// Fill in variables in field text
virtual std::string resolveText(std::string str){ return str; }
virtual void gotText(std::map<std::string, std::wstring> fields) = 0;
};
void drawInventoryItem(video::IVideoDriver *driver,
@ -158,15 +150,9 @@ public:
}
// form_src is deleted by this GUIFormSpecMenu
void setFormSource(IFormSource *form_src)
void setFormIO(FormIO *form_io)
{
m_form_src = form_src;
}
// text_dst is deleted by this GUIFormSpecMenu
void setTextDest(TextDest *text_dst)
{
m_text_dst = text_dst;
m_form_io = form_io;
}
void removeChildren();
@ -196,8 +182,7 @@ protected:
std::string m_formspec_string;
InventoryLocation m_current_inventory_location;
IFormSource *m_form_src;
TextDest *m_text_dst;
FormIO *m_form_io;
core::array<ListDrawSpec> m_inventorylists;
core::array<ImageDrawSpec> m_images;

View File

@ -33,32 +33,32 @@ with this program; if not, write to the Free Software Foundation, Inc.,
GUITextInputMenu::GUITextInputMenu(gui::IGUIEnvironment* env,
gui::IGUIElement* parent, s32 id,
IMenuManager *menumgr,
TextDest *dest,
FormIO *io,
std::wstring initial_text
):
GUIModalMenu(env, parent, id, menumgr),
m_dest(dest),
m_io(io),
m_initial_text(initial_text)
{
}
GUITextInputMenu::~GUITextInputMenu()
{
if (m_io)
delete m_io;
removeChildren();
if(m_dest)
delete m_dest;
}
void GUITextInputMenu::removeChildren()
{
{
gui::IGUIElement *e = getElementFromId(256);
if(e != NULL)
if (e != NULL)
e->remove();
}
{
gui::IGUIElement *e = getElementFromId(257);
if(e != NULL)
if (e != NULL)
e->remove();
}
}
@ -69,12 +69,9 @@ void GUITextInputMenu::regenerateGui(v2u32 screensize)
{
gui::IGUIElement *e = getElementFromId(256);
if(e != NULL)
{
if (e != NULL) {
text = e->getText();
}
else
{
}else{
text = m_initial_text;
m_initial_text = L"";
}
@ -148,51 +145,42 @@ void GUITextInputMenu::drawMenu()
void GUITextInputMenu::acceptInput()
{
if(m_dest)
{
if (m_io) {
gui::IGUIElement *e = getElementFromId(256);
if(e != NULL)
{
m_dest->gotText(e->getText());
if (e != NULL) {
std::map<std::string,std::wstring> fields;
fields["text"] = e->getText();
m_io->gotText(fields);
}
delete m_dest;
m_dest = NULL;
delete m_io;
m_io = NULL;
}
}
bool GUITextInputMenu::OnEvent(const SEvent& event)
{
if(event.EventType==EET_KEY_INPUT_EVENT)
{
if(event.KeyInput.Key==KEY_ESCAPE && event.KeyInput.PressedDown)
{
if (event.EventType==EET_KEY_INPUT_EVENT) {
if (event.KeyInput.Key==KEY_ESCAPE && event.KeyInput.PressedDown) {
quitMenu();
return true;
}
if(event.KeyInput.Key==KEY_RETURN && event.KeyInput.PressedDown)
{
if (event.KeyInput.Key==KEY_RETURN && event.KeyInput.PressedDown) {
acceptInput();
quitMenu();
return true;
}
}
if(event.EventType==EET_GUI_EVENT)
{
if(event.GUIEvent.EventType==gui::EGET_ELEMENT_FOCUS_LOST
&& isVisible())
{
if(!canTakeFocus(event.GUIEvent.Element))
{
if (event.EventType==EET_GUI_EVENT) {
if (event.GUIEvent.EventType==gui::EGET_ELEMENT_FOCUS_LOST && isVisible()) {
if (!canTakeFocus(event.GUIEvent.Element)) {
dstream<<"GUITextInputMenu: Not allowing focus change."
<<std::endl;
// Returning true disables focus change
return true;
}
}
if(event.GUIEvent.EventType==gui::EGET_BUTTON_CLICKED)
{
switch(event.GUIEvent.Caller->getID())
{
if (event.GUIEvent.EventType==gui::EGET_BUTTON_CLICKED) {
switch (event.GUIEvent.Caller->getID()) {
case 257:
acceptInput();
quitMenu();
@ -200,10 +188,8 @@ bool GUITextInputMenu::OnEvent(const SEvent& event)
return true;
}
}
if(event.GUIEvent.EventType==gui::EGET_EDITBOX_ENTER)
{
switch(event.GUIEvent.Caller->getID())
{
if (event.GUIEvent.EventType==gui::EGET_EDITBOX_ENTER) {
switch (event.GUIEvent.Caller->getID()) {
case 256:
acceptInput();
quitMenu();

View File

@ -32,7 +32,7 @@ public:
GUITextInputMenu(gui::IGUIEnvironment* env,
gui::IGUIElement* parent, s32 id,
IMenuManager *menumgr,
TextDest *dest,
FormIO *io,
std::wstring initial_text);
~GUITextInputMenu();
@ -49,7 +49,7 @@ public:
bool OnEvent(const SEvent& event);
private:
TextDest *m_dest;
FormIO *m_io;
std::wstring m_initial_text;
};

View File

@ -1643,6 +1643,41 @@ inline std::string deSerializeLongString(std::istream &is)
return s;
}
// Creates a string with the length as the first four bytes
inline std::string serializeLongWideString(const std::wstring &plain)
{
//assert(plain.size() <= 65535);
char buf[4];
writeU32((u8*)buf, plain.size());
std::string s;
s.append(buf, 4);
for (u32 i=0; i<plain.size(); i++) {
writeU16((u8*)buf, plain[i]);
s.append(buf, 2);
}
return s;
}
// Reads a string with the length as the first four bytes
inline std::wstring deSerializeLongWideString(std::istream &is)
{
char buf[4];
is.read(buf, 4);
if(is.gcount() != 4)
throw SerializationError("deSerializeLongWideString: size not read");
u16 s_size = readU32((u8*)buf);
if(s_size == 0)
return L"";
std::wstring s;
s.reserve(s_size);
for (u32 i=0; i<s_size; i++) {
is.read(&buf[0], 2);
wchar_t c16 = readU16((u8*)buf);
s.append(&c16, 1);
}
return s;
}
//
inline u32 time_to_daynight_ratio(u32 time_of_day)