vertex_engine/src/glfw/glfw.cpp
2024-05-15 10:57:21 +03:00

229 lines
6.0 KiB
C++
Executable File
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#include "glfw.hpp"
// #include "renderer/renderer.hpp"
// #include "event/system_event/category/key_event.hpp"
// #include "event/system_event/category/window_event.hpp"
namespace VE
{
glfw::glfw()
{
if (!glfwInit())
{
hack::error()("Not glfw window init");
std::terminate();
}
}
glfw::~glfw()
{
hack::warn(": ")("Destroy glfw window", m_win_data.m_name);
glfwDestroyWindow(m_win);
glfwTerminate();
}
void glfw::init(std::string win_name)
{
m_win_data.m_name = win_name;
set_hint();
set_window();
set_graphic_context();
set_pointer();
set_key_callback();
set_mouse_callback();
set_window_callback();
set_opengl();
}
void glfw::set_hint()
{
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 4);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 5);
glfwWindowHint(GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
glfwWindowHint(GLFW_SAMPLES, 4);
hack::log()("Set glfw window hint");
}
void glfw::set_window()
{
// два полследних nullptr
// первый - устанавливает монитор на ктором будетоткрытие(основной, дополнительнй)
// второй - делиться ли ресурсами с кем-то
m_win = glfwCreateWindow(
glfwGetVideoMode(glfwGetPrimaryMonitor())->width,
glfwGetVideoMode(glfwGetPrimaryMonitor())->height,
m_win_data.m_name.c_str(),
nullptr, nullptr
);
if(m_win == NULL)
{
hack::error()("Failed to create GLFW window");
glfwTerminate();
std::terminate();
}
glfwGetWindowSize(m_win, &m_win_data.m_width, &m_win_data.m_height);
hack::log(": ")("Created glfw window", m_win_data.m_name);
hack::log(" = ")(" width", m_win_data.m_width);
hack::log(" = ")(" height", m_win_data.m_height);
}
void glfw::set_graphic_context()
{
m_context = std::make_unique<context>(m_win);
hack::log()("Set context");
}
void glfw::set_pointer()
{
glfwSetWindowUserPointer(m_win, &m_win_data);
}
GLFWwindow* glfw::get_win() const
{
return m_win;
}
int glfw::width() const
{
return m_win_data.m_width;
}
int glfw::height() const
{
return m_win_data.m_height;
}
void glfw::update()
{
glfwPollEvents();
m_context->swap_buffers();
}
void glfw::clear() const
{
glClearColor(m_bgcolor.r, m_bgcolor.g, m_bgcolor.b, m_bgcolor.a);
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
}
void glfw::set_event_fn(const event_fn<event>& fn)
{
m_win_data.execute = fn;
}
void glfw::set_key_callback()
{
glfwSetKeyCallback(m_win, [](GLFWwindow* w, int key, int scancode, int action, int mods)
{
auto d = static_cast<win_data*>(glfwGetWindowUserPointer(w));
event e{ action, key };
// HERE
// тут одноврекменно срабатывает только один сигнал
// т.е. если нажада клавиша и удерживается сигнал о повторе идет
// но если нажать одновременно еще, то сигнал о той нажатой пропадает
// нужносамому реализовывать функцию повтора а не полагаться на внутреннюю
// реализацию glfw
switch (action)
{
case GLFW_PRESS:
{
e.m_type = event_type::KEY_PRESSED;
break;
}
case GLFW_RELEASE:
{
e.m_type = event_type::KEY_RELEASED;
break;
}
case GLFW_REPEAT:
{
e.m_type = event_type::KEY_REPEATE;
break;
}
}
d->execute(e);
});
}
void glfw::set_mouse_callback()
{
glfwSetMouseButtonCallback(m_win, [](GLFWwindow* w, int button, int action, int mods)
{
auto d = static_cast<win_data*>(glfwGetWindowUserPointer(w));
event e{ action, button };
switch (action)
{
case GLFW_PRESS:
{
e.m_type = event_type::MOUSE_BUTTON_PRESSED;
break;
}
case GLFW_RELEASE:
{
e.m_type = event_type::MOUSE_BUTTON_RELEASED;
break;
}
}
d->execute(e);
});
glfwSetScrollCallback(m_win, [](GLFWwindow* w, double xOffset, double yOffset)
{
auto d = static_cast<win_data*>(glfwGetWindowUserPointer(w));
event e{ event_type::MOUSE_SCROLL, std::pair<float, float>{ static_cast<float>(xOffset), static_cast<float>(yOffset) } };
d->execute(e);
});
glfwSetCursorPosCallback(m_win, [](GLFWwindow* w, double xPos, double yPos)
{
auto d = static_cast<win_data*>(glfwGetWindowUserPointer(w));
event e{ event_type::MOUSE_CURSOR_POSITION, std::pair<float, float>{ static_cast<float>(xPos), static_cast<float>(yPos) } };
d->execute(e);
});
}
void glfw::set_window_callback()
{
glfwSetWindowSizeLimits(m_win, m_win_data.m_width, m_win_data.m_height, GLFW_DONT_CARE, GLFW_DONT_CARE);
glfwSetWindowSizeCallback(m_win, [](GLFWwindow* w, int width, int height)
{
auto d = static_cast<win_data*>(glfwGetWindowUserPointer(w));
d->m_width = width;
d->m_height = height;
event e{ event_type::WINDOW_RESIZE, std::pair<float, float>{ static_cast<float>(width), static_cast<float>(height) } };
d->execute(e);
});
glfwSetWindowCloseCallback(m_win, [](GLFWwindow* w)
{
auto d = static_cast<win_data*>(glfwGetWindowUserPointer(w));
event e{ event_type::WINDOW_CLOSE, nullptr };
d->execute(e);
});
glfwSetWindowFocusCallback(m_win, [](GLFWwindow* w, int focused)
{
auto d = static_cast<win_data*>(glfwGetWindowUserPointer(w));
event e{ event_type::WINDOW_FOCUS, focused };
d->execute(e);
});
}
void glfw::set_opengl()
{
glEnable(GL_DEPTH_TEST);
glClearColor(0.07f, 0.13f, 0.17f, 1.0f);
glViewport(0, 0, m_win_data.m_width, m_win_data.m_height);
}
}