mirror of
https://github.com/MaSzyna-EU07/maszyna.git
synced 2026-10-17 03:59:19 +02:00
feat(editor): add orthographic top view toggle
This commit is contained in:
@@ -1431,9 +1431,8 @@ void editor_mode::draw_orthophoto()
|
|||||||
Camera.SetMatrix(viewmatrix);
|
Camera.SetMatrix(viewmatrix);
|
||||||
glm::mat4 const view = glm::mat4(glm::mat3(viewmatrix));
|
glm::mat4 const view = glm::mat4(glm::mat3(viewmatrix));
|
||||||
ImGuiIO const &io = ImGui::GetIO();
|
ImGuiIO const &io = ImGui::GetIO();
|
||||||
float const fovy = glm::radians(Global.FieldOfView / Global.ZoomFactor);
|
|
||||||
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
||||||
m_orthophoto.draw(glm::perspective(fovy, aspect, 0.1f, 10000.0f) * view, Camera.Pos, io.DisplaySize.x, io.DisplaySize.y);
|
m_orthophoto.draw(editor_mode::projection_matrix(aspect) * view, Camera.Pos, io.DisplaySize.x, io.DisplaySize.y);
|
||||||
}
|
}
|
||||||
|
|
||||||
editor_terrain *editor_mode::terrain_at(double X, double Z)
|
editor_terrain *editor_mode::terrain_at(double X, double Z)
|
||||||
@@ -2107,9 +2106,8 @@ void editor_mode::draw_area_fill_outline() const
|
|||||||
ImGuiIO const &io = ImGui::GetIO();
|
ImGuiIO const &io = ImGui::GetIO();
|
||||||
glm::mat4 const view = GfxRenderer->Camera_View_Matrix();
|
glm::mat4 const view = GfxRenderer->Camera_View_Matrix();
|
||||||
glm::dvec3 const camerapos = GfxRenderer->Camera_Position();
|
glm::dvec3 const camerapos = GfxRenderer->Camera_Position();
|
||||||
float const fovy = glm::radians(Global.FieldOfView / Global.ZoomFactor);
|
|
||||||
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
||||||
glm::mat4 const viewprojection = glm::perspective(fovy, aspect, 0.1f, 10000.0f) * view;
|
glm::mat4 const viewprojection = editor_mode::projection_matrix(aspect) * view;
|
||||||
|
|
||||||
auto const to_clip = [&](glm::dvec3 const &Point) { return viewprojection * glm::vec4(glm::vec3(Point - camerapos), 1.0f); };
|
auto const to_clip = [&](glm::dvec3 const &Point) { return viewprojection * glm::vec4(glm::vec3(Point - camerapos), 1.0f); };
|
||||||
auto const to_screen = [&](glm::vec4 const &Clip) {
|
auto const to_screen = [&](glm::vec4 const &Clip) {
|
||||||
@@ -2198,6 +2196,14 @@ void editor_mode::render_area_fill()
|
|||||||
|
|
||||||
void editor_mode::render_gizmo_options()
|
void editor_mode::render_gizmo_options()
|
||||||
{
|
{
|
||||||
|
if (ImGui::Button(Global.EditorOrtho ? "3D view (O)" : "Top view, orthographic (O)"))
|
||||||
|
toggle_ortho();
|
||||||
|
if (Global.EditorOrtho)
|
||||||
|
{
|
||||||
|
ImGui::SameLine();
|
||||||
|
ImGui::SetNextItemWidth(120.0f);
|
||||||
|
ImGui::SliderFloat("Extent (m), wheel", &Global.EditorOrthoExtent, 5.0f, 5000.0f, "%.0f", 3.0f);
|
||||||
|
}
|
||||||
ImGui::Checkbox("Enabled", &m_gizmo_enabled);
|
ImGui::Checkbox("Enabled", &m_gizmo_enabled);
|
||||||
if (!m_gizmo_enabled)
|
if (!m_gizmo_enabled)
|
||||||
return;
|
return;
|
||||||
@@ -2265,7 +2271,7 @@ void editor_mode::render_gizmo()
|
|||||||
}
|
}
|
||||||
|
|
||||||
ImGuizmo::BeginFrame();
|
ImGuizmo::BeginFrame();
|
||||||
ImGuizmo::SetOrthographic(false);
|
ImGuizmo::SetOrthographic(Global.EditorOrtho);
|
||||||
|
|
||||||
ImGuiIO const &io = ImGui::GetIO();
|
ImGuiIO const &io = ImGui::GetIO();
|
||||||
ImGuizmo::SetRect(0.0f, 0.0f, io.DisplaySize.x, io.DisplaySize.y);
|
ImGuizmo::SetRect(0.0f, 0.0f, io.DisplaySize.x, io.DisplaySize.y);
|
||||||
@@ -2278,9 +2284,8 @@ void editor_mode::render_gizmo()
|
|||||||
// the engine's own projection bakes in reverse-Z (and screen orientation), which ImGuizmo
|
// the engine's own projection bakes in reverse-Z (and screen orientation), which ImGuizmo
|
||||||
// doesn't expect; rebuild a clean, standard perspective that matches the rendered view.
|
// doesn't expect; rebuild a clean, standard perspective that matches the rendered view.
|
||||||
// for the main viewport the engine uses a symmetric frustum with this exact fov/aspect.
|
// for the main viewport the engine uses a symmetric frustum with this exact fov/aspect.
|
||||||
float const fovy = glm::radians(Global.FieldOfView / Global.ZoomFactor);
|
|
||||||
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
||||||
glm::mat4 const projection = glm::perspective(fovy, aspect, 0.1f, 10000.0f);
|
glm::mat4 const projection = editor_mode::projection_matrix(aspect);
|
||||||
|
|
||||||
if (!m_node)
|
if (!m_node)
|
||||||
{
|
{
|
||||||
@@ -2462,9 +2467,46 @@ void editor_mode::render_include_gizmo(glm::mat4 const &View, glm::mat4 const &P
|
|||||||
apply_include();
|
apply_include();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
glm::mat4 editor_mode::projection_matrix(float const Aspect)
|
||||||
|
{
|
||||||
|
if (Global.EditorOrtho)
|
||||||
|
{
|
||||||
|
auto const height{Global.EditorOrthoExtent};
|
||||||
|
return glm::ortho(-height * Aspect, height * Aspect, -height, height, -10000.0f, 10000.0f);
|
||||||
|
}
|
||||||
|
return glm::perspective(glm::radians(Global.FieldOfView / Global.ZoomFactor), Aspect, 0.1f, 10000.0f);
|
||||||
|
}
|
||||||
|
|
||||||
|
void editor_mode::toggle_ortho()
|
||||||
|
{
|
||||||
|
Global.EditorOrtho = !Global.EditorOrtho;
|
||||||
|
if (Global.EditorOrtho)
|
||||||
|
{
|
||||||
|
m_ortho_pitch = Camera.Angle.x;
|
||||||
|
Camera.Angle.x = -M_PI_2;
|
||||||
|
Camera.Angle.z = 0.0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Camera.Angle.x = m_ortho_pitch;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void editor_mode::on_scroll(double const Xoffset, double const Yoffset)
|
||||||
|
{
|
||||||
|
if (false == Global.EditorOrtho || ImGui::GetIO().WantCaptureMouse)
|
||||||
|
return;
|
||||||
|
Global.EditorOrthoExtent = std::clamp(Global.EditorOrthoExtent * static_cast<float>(std::pow(0.85, Yoffset)), 5.0f, 5000.0f);
|
||||||
|
}
|
||||||
|
|
||||||
void editor_mode::update_camera(double const Deltatime)
|
void editor_mode::update_camera(double const Deltatime)
|
||||||
{
|
{
|
||||||
Camera.Update();
|
Camera.Update();
|
||||||
|
if (Global.EditorOrtho)
|
||||||
|
{
|
||||||
|
Camera.Angle.x = -M_PI_2;
|
||||||
|
Camera.Angle.z = 0.0;
|
||||||
|
}
|
||||||
|
|
||||||
// focus animation runs after Camera.Update() so it overrides any residual velocity/rotation;
|
// focus animation runs after Camera.Update() so it overrides any residual velocity/rotation;
|
||||||
// it smoothly drives both position and orientation toward the framed object
|
// it smoothly drives both position and orientation toward the framed object
|
||||||
@@ -2544,6 +2586,8 @@ void editor_mode::exit()
|
|||||||
m_track_point = {};
|
m_track_point = {};
|
||||||
m_route = {};
|
m_route = {};
|
||||||
m_route_gizmo_using = false;
|
m_route_gizmo_using = false;
|
||||||
|
if (Global.EditorOrtho)
|
||||||
|
toggle_ortho();
|
||||||
|
|
||||||
g_redo.clear();
|
g_redo.clear();
|
||||||
m_history.clear();
|
m_history.clear();
|
||||||
@@ -2588,6 +2632,7 @@ void editor_mode::on_key(int const Key, int const Scancode, int const Action, in
|
|||||||
bool handled = true;
|
bool handled = true;
|
||||||
switch (Key)
|
switch (Key)
|
||||||
{
|
{
|
||||||
|
case GLFW_KEY_O: toggle_ortho(); break;
|
||||||
case GLFW_KEY_Q: m_gizmo_op = gizmo_operation::translate; break;
|
case GLFW_KEY_Q: m_gizmo_op = gizmo_operation::translate; break;
|
||||||
case GLFW_KEY_W: m_gizmo_op = gizmo_operation::rotate; break;
|
case GLFW_KEY_W: m_gizmo_op = gizmo_operation::rotate; break;
|
||||||
case GLFW_KEY_E: m_gizmo_op = gizmo_operation::scale; break;
|
case GLFW_KEY_E: m_gizmo_op = gizmo_operation::scale; break;
|
||||||
|
|||||||
@@ -50,10 +50,7 @@ class editor_mode : public application_mode
|
|||||||
void on_key(int Key, int Scancode, int Action, int Mods) override;
|
void on_key(int Key, int Scancode, int Action, int Mods) override;
|
||||||
void on_cursor_pos(double Horizontal, double Vertical) override;
|
void on_cursor_pos(double Horizontal, double Vertical) override;
|
||||||
void on_mouse_button(int Button, int Action, int Mods) override;
|
void on_mouse_button(int Button, int Action, int Mods) override;
|
||||||
void on_scroll(double const Xoffset, double const Yoffset) override
|
void on_scroll(double const Xoffset, double const Yoffset) override;
|
||||||
{
|
|
||||||
;
|
|
||||||
}
|
|
||||||
void on_window_resize(int w, int h) override
|
void on_window_resize(int w, int h) override
|
||||||
{
|
{
|
||||||
;
|
;
|
||||||
@@ -64,6 +61,8 @@ class editor_mode : public application_mode
|
|||||||
static bool focus_active();
|
static bool focus_active();
|
||||||
static void set_focus_active(bool isActive);
|
static void set_focus_active(bool isActive);
|
||||||
static TCamera& get_camera() { return Camera; }
|
static TCamera& get_camera() { return Camera; }
|
||||||
|
static glm::mat4 projection_matrix(float const Aspect);
|
||||||
|
void toggle_ortho();
|
||||||
static bool change_history() { return m_change_history; }
|
static bool change_history() { return m_change_history; }
|
||||||
static void set_change_history(bool enabled) { m_change_history = enabled; }
|
static void set_change_history(bool enabled) { m_change_history = enabled; }
|
||||||
static bool settings_open() { return m_settings_open; }
|
static bool settings_open() { return m_settings_open; }
|
||||||
@@ -148,6 +147,7 @@ class editor_mode : public application_mode
|
|||||||
static bool m_change_history;
|
static bool m_change_history;
|
||||||
static bool m_settings_open;
|
static bool m_settings_open;
|
||||||
|
|
||||||
|
double m_ortho_pitch{0.0};
|
||||||
// camera fly-mode (right mouse button held); used to flush motion when it's released
|
// camera fly-mode (right mouse button held); used to flush motion when it's released
|
||||||
command_relay m_camera_relay;
|
command_relay m_camera_relay;
|
||||||
bool m_camera_flying{false};
|
bool m_camera_flying{false};
|
||||||
|
|||||||
@@ -36,9 +36,8 @@ class screen_projection
|
|||||||
ImGuiIO const &io = ImGui::GetIO();
|
ImGuiIO const &io = ImGui::GetIO();
|
||||||
m_size = io.DisplaySize;
|
m_size = io.DisplaySize;
|
||||||
m_camera = GfxRenderer->Camera_Position();
|
m_camera = GfxRenderer->Camera_Position();
|
||||||
float const fovy = glm::radians(Global.FieldOfView / Global.ZoomFactor);
|
|
||||||
float const aspect = m_size.y > 0.0f ? m_size.x / m_size.y : 1.0f;
|
float const aspect = m_size.y > 0.0f ? m_size.x / m_size.y : 1.0f;
|
||||||
m_viewprojection = glm::perspective(fovy, aspect, 0.1f, 10000.0f) * GfxRenderer->Camera_View_Matrix();
|
m_viewprojection = editor_mode::projection_matrix(aspect) * GfxRenderer->Camera_View_Matrix();
|
||||||
}
|
}
|
||||||
|
|
||||||
glm::vec4 clip(glm::dvec3 const &Point) const
|
glm::vec4 clip(glm::dvec3 const &Point) const
|
||||||
@@ -244,15 +243,14 @@ void editor_mode::render_track_gizmo()
|
|||||||
bool const pointmode = ui()->mode() == nodebank_panel::TRACK && m_track_point.valid() && m_track_point.path < static_cast<int>(track->m_paths.size());
|
bool const pointmode = ui()->mode() == nodebank_panel::TRACK && m_track_point.valid() && m_track_point.path < static_cast<int>(track->m_paths.size());
|
||||||
|
|
||||||
ImGuizmo::BeginFrame();
|
ImGuizmo::BeginFrame();
|
||||||
ImGuizmo::SetOrthographic(false);
|
ImGuizmo::SetOrthographic(Global.EditorOrtho);
|
||||||
ImGuiIO const &io = ImGui::GetIO();
|
ImGuiIO const &io = ImGui::GetIO();
|
||||||
ImGuizmo::SetRect(0.0f, 0.0f, io.DisplaySize.x, io.DisplaySize.y);
|
ImGuizmo::SetRect(0.0f, 0.0f, io.DisplaySize.x, io.DisplaySize.y);
|
||||||
|
|
||||||
glm::mat4 const view = GfxRenderer->Camera_View_Matrix();
|
glm::mat4 const view = GfxRenderer->Camera_View_Matrix();
|
||||||
glm::dvec3 const camerapos = GfxRenderer->Camera_Position();
|
glm::dvec3 const camerapos = GfxRenderer->Camera_Position();
|
||||||
float const fovy = glm::radians(Global.FieldOfView / Global.ZoomFactor);
|
|
||||||
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
||||||
glm::mat4 const projection = glm::perspective(fovy, aspect, 0.1f, 10000.0f);
|
glm::mat4 const projection = editor_mode::projection_matrix(aspect);
|
||||||
|
|
||||||
ImGuizmo::OPERATION const operation = (false == pointmode && m_gizmo_op == gizmo_operation::rotate) ? ImGuizmo::ROTATE_Y : ImGuizmo::TRANSLATE;
|
ImGuizmo::OPERATION const operation = (false == pointmode && m_gizmo_op == gizmo_operation::rotate) ? ImGuizmo::ROTATE_Y : ImGuizmo::TRANSLATE;
|
||||||
|
|
||||||
@@ -869,14 +867,13 @@ void editor_mode::render_route_gizmo()
|
|||||||
}
|
}
|
||||||
|
|
||||||
ImGuizmo::BeginFrame();
|
ImGuizmo::BeginFrame();
|
||||||
ImGuizmo::SetOrthographic(false);
|
ImGuizmo::SetOrthographic(Global.EditorOrtho);
|
||||||
ImGuiIO const &io = ImGui::GetIO();
|
ImGuiIO const &io = ImGui::GetIO();
|
||||||
ImGuizmo::SetRect(0.0f, 0.0f, io.DisplaySize.x, io.DisplaySize.y);
|
ImGuizmo::SetRect(0.0f, 0.0f, io.DisplaySize.x, io.DisplaySize.y);
|
||||||
glm::mat4 const view = GfxRenderer->Camera_View_Matrix();
|
glm::mat4 const view = GfxRenderer->Camera_View_Matrix();
|
||||||
glm::dvec3 const camerapos = GfxRenderer->Camera_Position();
|
glm::dvec3 const camerapos = GfxRenderer->Camera_Position();
|
||||||
float const fovy = glm::radians(Global.FieldOfView / Global.ZoomFactor);
|
|
||||||
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
float const aspect = io.DisplaySize.y > 0.0f ? io.DisplaySize.x / io.DisplaySize.y : 1.0f;
|
||||||
glm::mat4 const projection = glm::perspective(fovy, aspect, 0.1f, 10000.0f);
|
glm::mat4 const projection = editor_mode::projection_matrix(aspect);
|
||||||
|
|
||||||
auto const position{route_vertex_position(route.vertex)};
|
auto const position{route_vertex_position(route.vertex)};
|
||||||
if (false == m_route_gizmo_using)
|
if (false == m_route_gizmo_using)
|
||||||
|
|||||||
@@ -1593,6 +1593,13 @@ void opengl33_renderer::setup_pass(viewport_config &Viewport, renderpass_config
|
|||||||
auto const znear = ( Znear > 1.f ? Znear : Znear > 0.f ? Znear * zfar : 0.1f * Global.ZoomFactor);
|
auto const znear = ( Znear > 1.f ? Znear : Znear > 0.f ? Znear * zfar : 0.1f * Global.ZoomFactor);
|
||||||
|
|
||||||
camera.projection() = perspective_projection(Viewport.projection, znear, zfar, frustumtest_proj);
|
camera.projection() = perspective_projection(Viewport.projection, znear, zfar, frustumtest_proj);
|
||||||
|
if (EditorModeFlag && Global.EditorOrtho && Viewport.main)
|
||||||
|
{
|
||||||
|
auto const height{Global.EditorOrthoExtent};
|
||||||
|
auto const width{height * Global.window_size.x / std::max(1.f, static_cast<float>(Global.window_size.y))};
|
||||||
|
camera.projection() = ortho_projection(-width, width, -height, height, -zfar, zfar);
|
||||||
|
frustumtest_proj = ortho_frustumtest_projection(-width, width, -height, height, -zfar, zfar);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case rendermode::shadows:
|
case rendermode::shadows:
|
||||||
@@ -1692,6 +1699,13 @@ void opengl33_renderer::setup_pass(viewport_config &Viewport, renderpass_config
|
|||||||
}
|
}
|
||||||
|
|
||||||
camera.projection() = perspective_projection(proj, znear, zfar, frustumtest_proj);
|
camera.projection() = perspective_projection(proj, znear, zfar, frustumtest_proj);
|
||||||
|
if (EditorModeFlag && Global.EditorOrtho && Viewport.main)
|
||||||
|
{
|
||||||
|
auto const height{Global.EditorOrthoExtent};
|
||||||
|
auto const width{height * Global.window_size.x / std::max(1.f, static_cast<float>(Global.window_size.y))};
|
||||||
|
camera.projection() = ortho_projection(-width, width, -height, height, -zfar, zfar);
|
||||||
|
frustumtest_proj = ortho_frustumtest_projection(-width, width, -height, height, -zfar, zfar);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
case rendermode::reflections:
|
case rendermode::reflections:
|
||||||
|
|||||||
@@ -168,6 +168,8 @@ struct global_settings {
|
|||||||
bool bUseVBO{ true }; // czy jest VBO w karcie graficznej (czy użyć)
|
bool bUseVBO{ true }; // czy jest VBO w karcie graficznej (czy użyć)
|
||||||
float AnisotropicFiltering{ 8.f }; // requested level of anisotropic filtering. TODO: move it to renderer object
|
float AnisotropicFiltering{ 8.f }; // requested level of anisotropic filtering. TODO: move it to renderer object
|
||||||
float FieldOfView{ 45.f }; // vertical field of view for the camera. TODO: move it to the renderer
|
float FieldOfView{ 45.f }; // vertical field of view for the camera. TODO: move it to the renderer
|
||||||
|
bool EditorOrtho{ false };
|
||||||
|
float EditorOrthoExtent{ 150.f };
|
||||||
GLint iMaxTextureSize{ 4096 }; // maksymalny rozmiar tekstury
|
GLint iMaxTextureSize{ 4096 }; // maksymalny rozmiar tekstury
|
||||||
GLint iMaxCabTextureSize{ 4096 }; // largest allowed texture in vehicle cab
|
GLint iMaxCabTextureSize{ 4096 }; // largest allowed texture in vehicle cab
|
||||||
int iMultisampling{ 2 }; // tryb antyaliasingu: 0=brak,1=2px,2=4px,3=8px,4=16px
|
int iMultisampling{ 2 }; // tryb antyaliasingu: 0=brak,1=2px,2=4px,3=8px,4=16px
|
||||||
|
|||||||
Reference in New Issue
Block a user