Skip to content

Commit

Permalink
Add support for gui/load-screen
Browse files Browse the repository at this point in the history
  • Loading branch information
BenLubar committed Feb 14, 2018
1 parent db01238 commit 49b1672
Show file tree
Hide file tree
Showing 2 changed files with 135 additions and 1 deletion.
2 changes: 1 addition & 1 deletion CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ SET_SOURCE_FILES_PROPERTIES( ${PROJECT_HDRS} PROPERTIES HEADER_FILE_ONLY TRUE)

LIST(APPEND PROJECT_SRCS ${PROJECT_HDRS})

LIST(APPEND PROJECT_LIBS jsoncpp ${ZLIB_LIBRARIES} df-ai-biome)
LIST(APPEND PROJECT_LIBS jsoncpp lua ${ZLIB_LIBRARIES} df-ai-biome)

IF(APPLE)
SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -undefined dynamic_lookup")
Expand Down
134 changes: 134 additions & 0 deletions embark.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@
#include "event_manager.h"
#include "hooks.h"

#include "LuaTools.h"

#include "modules/Gui.h"
#include "modules/Screen.h"
#include "modules/Translation.h"
Expand Down Expand Up @@ -42,12 +44,28 @@ static bool viewscreen_is()
return strict_virtual_cast<T>(Gui::getCurViewscreen(false)) != nullptr;
}

static std::function<bool()> viewscreen_is(const std::string & focus)
{
return [focus]() -> bool
{
return Gui::getCurFocus(false) == focus;
};
}

template<typename T>
static bool viewscreen_is_not()
{
return strict_virtual_cast<T>(Gui::getCurViewscreen(false)) == nullptr;
}

static std::function<bool()> viewscreen_is_not(const std::string & focus)
{
return [focus]() -> bool
{
return Gui::getCurFocus(false) != focus;
};
}

void EmbarkExclusive::Run(color_ostream & out)
{
df::viewscreen *curview = Gui::getCurViewscreen(false);
Expand Down Expand Up @@ -230,6 +248,122 @@ void EmbarkExclusive::Run(color_ostream & out)
});
});

If(viewscreen_is("dfhack/lua/load_screen"), [&]()
{
dfhack_viewscreen *view = dfhack_viewscreen::try_cast(curview);
df::viewscreen_loadgamest *parent = view ? strict_virtual_cast<df::viewscreen_loadgamest>(view->parent) : nullptr;
if (!view || view->getFocusString() != "lua/load_screen" || !parent)
{
return;
}

If([&]() -> bool { return config.random_embark_world.empty(); }, [&]()
{
Do([&]()
{
ai->debug(out, "leaving \"Select World\" (no save name)");
});

Key(interface_key::LEAVESCREEN);
}, [&]()
{
std::vector<df::loadgame_save_info *> filtered_saves;
for (auto save : parent->saves)
{
size_t len = save->folder_name.length();
const static std::string tmpl("-#####-##-##");
if (len < tmpl.length())
{
filtered_saves.push_back(save);
}
else
{
for (size_t i = 0; i < tmpl.length(); i++)
{
char expect = tmpl.at(tmpl.length() - i - 1);
char actual = save->folder_name.at(len - i - 1);
if (expect == '#' ? actual < '0' || actual > '9' : actual != expect)
{
filtered_saves.push_back(save);
break;
}
}
}
}

auto save = std::find_if(filtered_saves.begin(), filtered_saves.end(), [](df::loadgame_save_info *s) -> bool
{
return s->folder_name == config.random_embark_world;
});

If([&]() -> bool { return save == filtered_saves.end(); }, [&]()
{
Do([&]()
{
ai->debug(out, "could not find save named " + config.random_embark_world);
config.set(out, config.random_embark_world, std::string());
});

Key(interface_key::LEAVESCREEN);
}, [&]()
{
auto L = Lua::Core::State;
lua_rawgetp(L, LUA_REGISTRYINDEX, view);
lua_getfield(L, -1, "sel_idx");
int32_t sel_idx = static_cast<int32_t>(lua_tointeger(L, -1)) - 1;
lua_pop(L, 2);

Do([&]()
{
ai->debug(out, stl_sprintf("selecting save #%d (%s) (%s)",
(save - filtered_saves.begin()) + 1,
(*save)->world_name.c_str(),
(*save)->fort_name.c_str()));
});

SelectVerticalMenuItem(sel_idx, int32_t(save - filtered_saves.begin()));
});
});
});

If([&]() -> bool
{
df::viewscreen *screen = Gui::getCurViewscreen(false);
df::viewscreen *parent = screen ? screen->parent : nullptr;
// TODO: get a real focus string for the load_screen_options dialog
return Gui::getFocusString(screen) == "dfhack/lua" && Gui::getFocusString(parent) == "dfhack/lua/load_screen";
}, [&]()
{
dfhack_viewscreen *view = dfhack_viewscreen::try_cast(curview);
if (!view)
return;

auto L = Lua::Core::State;
lua_rawgetp(L, LUA_REGISTRYINDEX, view);
lua_getfield(L, -1, "save_mtime");
if (lua_isnoneornil(L, -1))
{
// not on load_screen_options
lua_pop(L, 2);
return;
}
lua_getfield(L, -2, "loading");
bool startedLoading = !!lua_isboolean(L, -1);
bool finishedLoading = startedLoading && !lua_toboolean(L, -1);
lua_pop(L, 3);

If([&]() -> bool { return startedLoading; }, [&]()
{
While([&]() -> bool { return !finishedLoading; }, [&]()
{
Delay();
});
}, [&]()
{
Key(interface_key::SELECT);
});
});

If(viewscreen_is<df::viewscreen_new_regionst>, [&]()
{
df::viewscreen_new_regionst *view = strict_virtual_cast<df::viewscreen_new_regionst>(curview);
Expand Down

0 comments on commit 49b1672

Please sign in to comment.