settings page completely moved to xml
This commit is contained in:
parent
9cdf3ff016
commit
b9ea88b988
@ -1,6 +1,7 @@
|
||||
<panel size='400' color='0' interval='1' context='menu'>
|
||||
<panel id='settings_panel' color='0'>
|
||||
</panel>
|
||||
<button onclick='menu.page="languages"' id='langs_btn'>-</button>
|
||||
<button onclick='menu.page="settings_audio"'>@Audio</button>
|
||||
<button onclick='menu.page="controls"'>@Controls</button>
|
||||
<button onclick='menu:back()'>@Back</button>
|
||||
|
||||
@ -23,9 +23,23 @@ function update_setting(x, id, name, postfix)
|
||||
)
|
||||
end
|
||||
|
||||
function create_checkbox(id, name)
|
||||
document.settings_panel:add(string.format(
|
||||
"<checkbox consumer='function(x) core.set_setting(\"%s\", x) end' checked='%s'>%s</checkbox>",
|
||||
id, core.str_setting(id), gui.str(name, "settings")
|
||||
))
|
||||
end
|
||||
|
||||
function on_open()
|
||||
create_setting("chunks.load-distance", "Load Distance", 1, 3)
|
||||
create_setting("chunks.load-speed", "Load Speed", 1, 1)
|
||||
create_setting("graphics.fog-curve", "Fog Curve", 0.1, 2)
|
||||
create_setting("camera.fov", "FOV", 1, 4, "°")
|
||||
create_checkbox("display.vsync", "V-Sync")
|
||||
create_checkbox("graphics.backlight", "Backlight")
|
||||
create_checkbox("camera.shaking", "Camera Shaking")
|
||||
document.langs_btn.text = string.format(
|
||||
"%s: %s", gui.str("Language", "settings"),
|
||||
gui.get_locales_info()[gui.get_locale()].name
|
||||
)
|
||||
end
|
||||
|
||||
@ -23,3 +23,12 @@ std::string IntegerSetting::toString() const {
|
||||
return "invalid format";
|
||||
}
|
||||
}
|
||||
|
||||
std::string FlagSetting::toString() const {
|
||||
switch (getFormat()) {
|
||||
case setting_format::simple:
|
||||
return value ? "true" : "false";
|
||||
default:
|
||||
return "invalid format";
|
||||
}
|
||||
}
|
||||
|
||||
@ -156,4 +156,47 @@ public:
|
||||
virtual std::string toString() const override;
|
||||
};
|
||||
|
||||
class FlagSetting : public Setting {
|
||||
protected:
|
||||
bool initial;
|
||||
bool value;
|
||||
std::vector<consumer<bool>> consumers;
|
||||
public:
|
||||
FlagSetting(
|
||||
bool value,
|
||||
setting_format format=setting_format::simple
|
||||
) : Setting(format),
|
||||
initial(value),
|
||||
value(value)
|
||||
{}
|
||||
|
||||
bool& operator*() {
|
||||
return value;
|
||||
}
|
||||
|
||||
bool get() const {
|
||||
return value;
|
||||
}
|
||||
|
||||
void set(bool value) {
|
||||
if (value == this->value) {
|
||||
return;
|
||||
}
|
||||
this->value = value;
|
||||
for (auto& callback : consumers) {
|
||||
callback(value);
|
||||
}
|
||||
}
|
||||
|
||||
void observe(consumer<bool> callback) {
|
||||
consumers.push_back(callback);
|
||||
}
|
||||
|
||||
virtual void resetToDefault() override {
|
||||
value = initial;
|
||||
}
|
||||
|
||||
virtual std::string toString() const override;
|
||||
};
|
||||
|
||||
#endif // DATA_SETTING_H_
|
||||
|
||||
@ -149,7 +149,7 @@ void Engine::mainloop() {
|
||||
if (!Window::isIconified()) {
|
||||
renderFrame(batch);
|
||||
}
|
||||
Window::swapInterval(Window::isIconified() ? 1 : settings.display.swapInterval);
|
||||
Window::swapInterval(Window::isIconified() ? 1 : settings.display.vsync.get());
|
||||
|
||||
processPostRunnables();
|
||||
|
||||
|
||||
@ -17,13 +17,17 @@ SettingsHandler::SettingsHandler(EngineSettings& settings) {
|
||||
map.emplace("audio.volume-ambient", &settings.audio.volumeAmbient);
|
||||
map.emplace("audio.volume-music", &settings.audio.volumeMusic);
|
||||
|
||||
map.emplace("display.vsync", &settings.display.vsync);
|
||||
|
||||
map.emplace("camera.sensitivity", &settings.camera.sensitivity);
|
||||
map.emplace("camera.fov", &settings.camera.fov);
|
||||
map.emplace("camera.shaking", &settings.camera.shaking);
|
||||
|
||||
map.emplace("chunks.load-distance", &settings.chunks.loadDistance);
|
||||
map.emplace("chunks.load-speed", &settings.chunks.loadSpeed);
|
||||
|
||||
map.emplace("graphics.fog-curve", &settings.graphics.fogCurve);
|
||||
map.emplace("graphics.backlight", &settings.graphics.backlight);
|
||||
}
|
||||
|
||||
dynamic::Value SettingsHandler::getValue(const std::string& name) const {
|
||||
@ -36,6 +40,8 @@ dynamic::Value SettingsHandler::getValue(const std::string& name) const {
|
||||
return dynamic::Value::of((number_t)number->get());
|
||||
} else if (auto integer = dynamic_cast<IntegerSetting*>(setting)) {
|
||||
return dynamic::Value::of((integer_t)integer->get());
|
||||
} else if (auto flag = dynamic_cast<FlagSetting*>(setting)) {
|
||||
return dynamic::Value::boolean(flag->get());
|
||||
} else {
|
||||
throw std::runtime_error("type is not implemented for '"+name+"'");
|
||||
}
|
||||
@ -58,6 +64,23 @@ Setting* SettingsHandler::getSetting(const std::string& name) const {
|
||||
return found->second;
|
||||
}
|
||||
|
||||
template<class T>
|
||||
static void set_numeric_value(T* setting, dynamic::Value& value) {
|
||||
switch (value.type) {
|
||||
case dynamic::valtype::integer:
|
||||
setting->set(std::get<integer_t>(value.value));
|
||||
break;
|
||||
case dynamic::valtype::number:
|
||||
setting->set(std::get<number_t>(value.value));
|
||||
break;
|
||||
case dynamic::valtype::boolean:
|
||||
setting->set(std::get<bool>(value.value));
|
||||
break;
|
||||
default:
|
||||
throw std::runtime_error("type error, numeric value expected");
|
||||
}
|
||||
}
|
||||
|
||||
void SettingsHandler::setValue(const std::string& name, dynamic::Value value) {
|
||||
auto found = map.find(name);
|
||||
if (found == map.end()) {
|
||||
@ -65,27 +88,11 @@ void SettingsHandler::setValue(const std::string& name, dynamic::Value value) {
|
||||
}
|
||||
auto setting = found->second;
|
||||
if (auto number = dynamic_cast<NumberSetting*>(setting)) {
|
||||
switch (value.type) {
|
||||
case dynamic::valtype::integer:
|
||||
number->set(std::get<integer_t>(value.value));
|
||||
break;
|
||||
case dynamic::valtype::number:
|
||||
number->set(std::get<number_t>(value.value));
|
||||
break;
|
||||
default:
|
||||
throw std::runtime_error("type error, numeric value expected");
|
||||
}
|
||||
set_numeric_value(number, value);
|
||||
} else if (auto integer = dynamic_cast<IntegerSetting*>(setting)) {
|
||||
switch (value.type) {
|
||||
case dynamic::valtype::integer:
|
||||
integer->set(std::get<integer_t>(value.value));
|
||||
break;
|
||||
case dynamic::valtype::number:
|
||||
integer->set(std::get<number_t>(value.value));
|
||||
break;
|
||||
default:
|
||||
throw std::runtime_error("type error, numeric value expected");
|
||||
}
|
||||
set_numeric_value(number, value);
|
||||
} else if (auto flag = dynamic_cast<FlagSetting*>(setting)) {
|
||||
set_numeric_value(flag, value);
|
||||
} else {
|
||||
throw std::runtime_error("type is not implement - setting '"+name+"'");
|
||||
}
|
||||
@ -107,7 +114,7 @@ toml::Wrapper* create_wrapper(EngineSettings& settings) {
|
||||
display.add("width", &settings.display.width);
|
||||
display.add("height", &settings.display.height);
|
||||
display.add("samples", &settings.display.samples);
|
||||
display.add("swap-interval", &settings.display.swapInterval);
|
||||
display.add("vsync", &*settings.display.vsync);
|
||||
|
||||
toml::Section& chunks = wrapper->add("chunks");
|
||||
chunks.add("load-distance", &*settings.chunks.loadDistance);
|
||||
@ -117,13 +124,13 @@ toml::Wrapper* create_wrapper(EngineSettings& settings) {
|
||||
toml::Section& camera = wrapper->add("camera");
|
||||
camera.add("fov-effects", &settings.camera.fovEvents);
|
||||
camera.add("fov", &*settings.camera.fov);
|
||||
camera.add("shaking", &settings.camera.shaking);
|
||||
camera.add("shaking", &*settings.camera.shaking);
|
||||
camera.add("sensitivity", &*settings.camera.sensitivity);
|
||||
|
||||
toml::Section& graphics = wrapper->add("graphics");
|
||||
graphics.add("gamma", &settings.graphics.gamma);
|
||||
graphics.add("fog-curve", &*settings.graphics.fogCurve);
|
||||
graphics.add("backlight", &settings.graphics.backlight);
|
||||
graphics.add("backlight", &*settings.graphics.backlight);
|
||||
graphics.add("frustum-culling", &settings.graphics.frustumCulling);
|
||||
graphics.add("skybox-resolution", &settings.graphics.skyboxResolution);
|
||||
|
||||
|
||||
@ -17,9 +17,6 @@ class LevelController;
|
||||
using packconsumer = std::function<void(const ContentPack& pack)>;
|
||||
|
||||
namespace menus {
|
||||
// implemented in menu_settings.cpp
|
||||
extern void create_settings_panel(Engine* engine);
|
||||
|
||||
extern std::shared_ptr<gui::Panel> create_packs_panel(
|
||||
const std::vector<ContentPack>& packs,
|
||||
Engine* engine,
|
||||
|
||||
@ -1,67 +0,0 @@
|
||||
#include "menu.h"
|
||||
#include "menu_commons.h"
|
||||
|
||||
#include "../locale/langs.h"
|
||||
#include "../../graphics/ui/GUI.h"
|
||||
#include "../../graphics/ui/gui_util.h"
|
||||
#include "../../engine.h"
|
||||
#include "../../util/stringutil.h"
|
||||
#include "../../window/Events.h"
|
||||
|
||||
#include <glm/glm.hpp>
|
||||
|
||||
using namespace gui;
|
||||
|
||||
void menus::create_settings_panel(Engine* engine) {
|
||||
auto menu = engine->getGUI()->getMenu();
|
||||
auto panel = menus::create_page(engine, "settings", 400, 0.0f, 1);
|
||||
|
||||
/* V-Sync checkbox */{
|
||||
auto checkbox = std::make_shared<FullCheckBox>(
|
||||
langs::get(L"V-Sync", L"settings"), glm::vec2(400, 32)
|
||||
);
|
||||
checkbox->setSupplier([=]() {
|
||||
return engine->getSettings().display.swapInterval != 0;
|
||||
});
|
||||
checkbox->setConsumer([=](bool checked) {
|
||||
engine->getSettings().display.swapInterval = checked;
|
||||
});
|
||||
panel->add(checkbox);
|
||||
}
|
||||
|
||||
/* Backlight checkbox */{
|
||||
auto checkbox = std::make_shared<FullCheckBox>(
|
||||
langs::get(L"Backlight", L"settings"), glm::vec2(400, 32)
|
||||
);
|
||||
checkbox->setSupplier([=]() {
|
||||
return engine->getSettings().graphics.backlight;
|
||||
});
|
||||
checkbox->setConsumer([=](bool checked) {
|
||||
engine->getSettings().graphics.backlight = checked;
|
||||
});
|
||||
panel->add(checkbox);
|
||||
}
|
||||
|
||||
/* Camera shaking checkbox */ {
|
||||
auto checkbox = std::make_shared<FullCheckBox>(
|
||||
langs::get(L"Camera Shaking", L"settings"), glm::vec2(400, 32)
|
||||
);
|
||||
checkbox->setSupplier([=]() {
|
||||
return engine->getSettings().camera.shaking;
|
||||
});
|
||||
checkbox->setConsumer([=](bool checked) {
|
||||
engine->getSettings().camera.shaking = checked;
|
||||
});
|
||||
panel->add(checkbox);
|
||||
}
|
||||
|
||||
std::string langName = langs::locales_info.at(langs::current->getId()).name;
|
||||
panel->add(guiutil::gotoButton(
|
||||
langs::get(L"Language", L"settings")+L": "+
|
||||
util::str2wstr_utf8(langName),
|
||||
"languages", menu));
|
||||
|
||||
panel->add(guiutil::gotoButton(L"Audio", "settings_audio", menu));
|
||||
panel->add(guiutil::gotoButton(L"Controls", "controls", menu));
|
||||
panel->add(guiutil::backButton(menu));
|
||||
}
|
||||
@ -102,7 +102,7 @@ LevelScreen::LevelScreen(Engine* engine, Level* level) : Screen(engine) {
|
||||
hud = std::make_unique<Hud>(engine, frontend.get(), controller->getPlayer());
|
||||
|
||||
|
||||
backlight = settings.graphics.backlight;
|
||||
backlight = settings.graphics.backlight.get();
|
||||
|
||||
animator = std::make_unique<TextureAnimator>();
|
||||
animator->addAnimations(assets->getAnimations());
|
||||
@ -167,9 +167,9 @@ void LevelScreen::update(float delta) {
|
||||
// TODO: subscribe for setting change
|
||||
EngineSettings& settings = engine->getSettings();
|
||||
controller->getPlayer()->camera->setFov(glm::radians(settings.camera.fov.get()));
|
||||
if (settings.graphics.backlight != backlight) {
|
||||
if (settings.graphics.backlight.get() != backlight) {
|
||||
controller->getLevel()->chunks->saveAndClear();
|
||||
backlight = settings.graphics.backlight;
|
||||
backlight = settings.graphics.backlight.get();
|
||||
}
|
||||
|
||||
if (!hud->isPause()) {
|
||||
|
||||
@ -449,7 +449,7 @@ void BlocksRenderer::render(const voxel* voxels) {
|
||||
void BlocksRenderer::build(const Chunk* chunk, const ChunksStorage* chunks) {
|
||||
this->chunk = chunk;
|
||||
voxelsBuffer->setPosition(chunk->x * CHUNK_W - 1, 0, chunk->z * CHUNK_D - 1);
|
||||
chunks->getVoxels(voxelsBuffer, settings.graphics.backlight);
|
||||
chunks->getVoxels(voxelsBuffer, settings.graphics.backlight.get());
|
||||
overflow = false;
|
||||
vertexOffset = 0;
|
||||
indexOffset = indexSize = 0;
|
||||
|
||||
@ -254,7 +254,7 @@ static std::shared_ptr<UINode> readButton(UiXmlReader& reader, xml::xmlelement e
|
||||
static std::shared_ptr<UINode> readCheckBox(UiXmlReader& reader, xml::xmlelement element) {
|
||||
auto text = readAndProcessInnerText(element, reader.getContext());
|
||||
bool checked = element->attr("checked", "false").asBool();
|
||||
auto checkbox = std::make_shared<FullCheckBox>(text, glm::vec2(), checked);
|
||||
auto checkbox = std::make_shared<FullCheckBox>(text, glm::vec2(32), checked);
|
||||
_readPanel(reader, element, *checkbox);
|
||||
|
||||
if (element->has("consumer")) {
|
||||
|
||||
@ -139,7 +139,7 @@ void CameraControl::switchCamera() {
|
||||
void CameraControl::update(PlayerInput& input, float delta, Chunks* chunks) {
|
||||
offset = glm::vec3(0.0f, 0.7f, 0.0f);
|
||||
|
||||
if (settings.shaking && !input.cheat) {
|
||||
if (settings.shaking.get() && !input.cheat) {
|
||||
offset += updateCameraShaking(delta);
|
||||
}
|
||||
if (settings.fovEvents){
|
||||
|
||||
@ -133,8 +133,8 @@ static int l_str_setting(lua_State* L) {
|
||||
static int l_get_setting_info(lua_State* L) {
|
||||
auto name = lua_tostring(L, 1);
|
||||
auto setting = scripting::engine->getSettingsHandler().getSetting(name);
|
||||
lua_createtable(L, 0, 1);
|
||||
if (auto number = dynamic_cast<NumberSetting*>(setting)) {
|
||||
lua_createtable(L, 0, 1);
|
||||
lua_pushnumber(L, number->getMin());
|
||||
lua_setfield(L, -2, "min");
|
||||
lua_pushnumber(L, number->getMax());
|
||||
@ -142,13 +142,13 @@ static int l_get_setting_info(lua_State* L) {
|
||||
return 1;
|
||||
}
|
||||
if (auto integer = dynamic_cast<IntegerSetting*>(setting)) {
|
||||
lua_createtable(L, 0, 1);
|
||||
lua_pushinteger(L, integer->getMin());
|
||||
lua_setfield(L, -2, "min");
|
||||
lua_pushinteger(L, integer->getMax());
|
||||
lua_setfield(L, -2, "max");
|
||||
return 1;
|
||||
}
|
||||
lua_pop(L, 1);
|
||||
luaL_error(L, "unsupported setting type");
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -28,8 +28,8 @@ struct DisplaySettings {
|
||||
int height = 720;
|
||||
/// @brief Anti-aliasing samples
|
||||
int samples = 0;
|
||||
/// @brief GLFW swap interval value, 0 - unlimited fps, 1 - vsync
|
||||
int swapInterval = 1;
|
||||
/// @brief VSync on
|
||||
FlagSetting vsync = {true};
|
||||
/// @brief Window title */
|
||||
std::string title = "VoxelEngine-Cpp v" +
|
||||
std::to_string(ENGINE_VERSION_MAJOR) + "." +
|
||||
@ -49,7 +49,7 @@ struct CameraSettings {
|
||||
/// @brief Camera dynamic field of view effects
|
||||
bool fovEvents = true;
|
||||
/// @brief Camera movement shake
|
||||
bool shaking = true;
|
||||
FlagSetting shaking = {true};
|
||||
/// @brief Camera field of view
|
||||
NumberSetting fov {90.0f, 10, 120};
|
||||
/// @brief Camera sensitivity
|
||||
@ -62,7 +62,7 @@ struct GraphicsSettings {
|
||||
NumberSetting fogCurve {1.6f, 1.0f, 6.0f};
|
||||
float gamma = 1.0f;
|
||||
/// @brief Enable blocks backlight to prevent complete darkness
|
||||
bool backlight = true;
|
||||
FlagSetting backlight = {true};
|
||||
/// @brief Enable chunks frustum culling
|
||||
bool frustumCulling = true;
|
||||
int skyboxResolution = 64 + 32;
|
||||
|
||||
@ -164,7 +164,7 @@ int Window::initialize(DisplaySettings& settings){
|
||||
const GLFWvidmode* mode = glfwGetVideoMode(monitor);
|
||||
glfwSetWindowMonitor(window, monitor, 0, 0, mode->width, mode->height, GLFW_DONT_CARE);
|
||||
}
|
||||
glfwSwapInterval(settings.swapInterval);
|
||||
glfwSwapInterval(settings.vsync.get());
|
||||
const GLubyte* vendor = glGetString(GL_VENDOR);
|
||||
const GLubyte* renderer = glGetString(GL_RENDERER);
|
||||
logger.info() << "GL Vendor: " << (char*)vendor;
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user