16
0
mirror of https://github.com/MaSzyna-EU07/maszyna.git synced 2026-07-22 11:39:19 +02:00

map improvements

This commit is contained in:
milek7
2019-02-18 17:46:31 +01:00
parent 52ff1ecb98
commit 89cf20a251
16 changed files with 240 additions and 180 deletions

View File

@@ -6296,7 +6296,7 @@ std::string TController::Relation() const
return TrainParams->ShowRelation(); return TrainParams->ShowRelation();
}; };
std::string TController::TrainName() const const std::string& TController::TrainName() const
{ // zwraca numer pociągu { // zwraca numer pociągu
return TrainParams->TrainName; return TrainParams->TrainName;
}; };

View File

@@ -380,9 +380,9 @@ private:
// timetable // timetable
// methods // methods
public: public:
std::string TrainName() const; const std::string &TrainName() const;
private: private:
std::string Relation() const; std::string Relation() const;
Mtable::TTrainParameters const * TrainTimetable() const; Mtable::TTrainParameters const * TrainTimetable() const;
int StationIndex() const; int StationIndex() const;
int StationCount() const; int StationCount() const;

View File

@@ -159,7 +159,7 @@ struct material_data {
class TDynamicObject { // klasa pojazdu class TDynamicObject { // klasa pojazdu
friend opengl_renderer; friend opengl_renderer;
public: public:
static bool bDynamicRemove; // moved from ground static bool bDynamicRemove; // moved from ground
@@ -185,7 +185,7 @@ public:
// parametry położenia pojazdu dostępne publicznie // parametry położenia pojazdu dostępne publicznie
std::string asTrack; // nazwa toru początkowego; wywalić? std::string asTrack; // nazwa toru początkowego; wywalić?
std::string asDestination; // dokąd pojazd ma być kierowany "(stacja):(tor)" std::string asDestination; // dokąd pojazd ma być kierowany "(stacja):(tor)"
Math3D::matrix4x4 mMatrix; // macierz przekształcenia do renderowania modeli Math3D::matrix4x4 mMatrix; // macierz przekształcenia do renderowania modeli
TMoverParameters *MoverParameters; // parametry fizyki ruchu oraz przeliczanie TMoverParameters *MoverParameters; // parametry fizyki ruchu oraz przeliczanie
TDynamicObject *NextConnected; // pojazd podłączony od strony sprzęgu 1 (kabina -1) TDynamicObject *NextConnected; // pojazd podłączony od strony sprzęgu 1 (kabina -1)
TDynamicObject *PrevConnected; // pojazd podłączony od strony sprzęgu 0 (kabina 1) TDynamicObject *PrevConnected; // pojazd podłączony od strony sprzęgu 0 (kabina 1)
@@ -362,7 +362,7 @@ private:
sound_source rsEngageSlippery { sound_placement::engine }; // moved from cab sound_source rsEngageSlippery { sound_placement::engine }; // moved from cab
void position( glm::vec3 const Location ); void position( glm::vec3 const Location );
void render( TMoverParameters const &Vehicle, double const Deltatime ); void render( TMoverParameters const &Vehicle, double const Deltatime );
}; };
// methods // methods
@@ -450,10 +450,10 @@ private:
exchange_data m_exchange; // state of active load exchange procedure, if any exchange_data m_exchange; // state of active load exchange procedure, if any
exchange_sounds m_exchangesounds; // sounds associated with the load exchange exchange_sounds m_exchangesounds; // sounds associated with the load exchange
bool renderme; // yB - czy renderowac bool renderme; // yB - czy renderowac
float ModCamRot; float ModCamRot;
int iInventory[ 2 ] { 0, 0 }; // flagi bitowe posiadanych submodeli (np. świateł) int iInventory[ 2 ] { 0, 0 }; // flagi bitowe posiadanych submodeli (np. świateł)
bool btnOn; // ABu: czy byly uzywane buttony, jesli tak, to po renderingu wylacz bool btnOn; // ABu: czy byly uzywane buttony, jesli tak, to po renderingu wylacz
// bo ten sam model moze byc jeszcze wykorzystany przez inny obiekt! // bo ten sam model moze byc jeszcze wykorzystany przez inny obiekt!
public: public:

View File

@@ -2230,3 +2230,15 @@ event_manager::export_as_text( std::ostream &Output ) const {
} }
} }
} }
std::vector<TEventLauncher*> event_manager::find_eventlaunchers(glm::vec2 center, float radius) const {
std::vector<TEventLauncher *> results;
for (auto &launcher : m_launchers.sequence()) {
glm::dvec3 location = launcher->location();
if (glm::distance2(glm::vec2(location.x, location.z), center) < radius)
results.push_back(launcher);
}
return results;
}

View File

@@ -615,6 +615,9 @@ public:
// sends basic content of the class in legacy (text) format to provided stream // sends basic content of the class in legacy (text) format to provided stream
void void
export_as_text( std::ostream &Output ) const; export_as_text( std::ostream &Output ) const;
// returns all eventlaunchers in radius ignoring height
std::vector<TEventLauncher *>
find_eventlaunchers(glm::vec2 center, float radius) const;
private: private:
// types // types

View File

@@ -44,7 +44,7 @@ driver_ui::driver_ui() {
} }
void driver_ui::render_menu_contents() { void driver_ui::render_menu_contents() {
ui_layer::render_menu_contents(); ui_layer::render_menu_contents();
if (ImGui::BeginMenu(locale::strings[locale::string::ui_mode_windows].c_str())) if (ImGui::BeginMenu(locale::strings[locale::string::ui_mode_windows].c_str()))
{ {

View File

@@ -175,7 +175,7 @@ timetable_panel::update() {
auto *vehicle { ( auto *vehicle { (
false == FreeFlyModeFlag ? controlled : false == FreeFlyModeFlag ? controlled :
camera.m_owner != nullptr ? camera.m_owner : camera.m_owner != nullptr ? camera.m_owner :
std::get<TDynamicObject *>( simulation::Region->find_vehicle( camera.Pos, 20, false, false ) ) ) }; // w trybie latania lokalizujemy wg mapy std::get<TDynamicObject *>( simulation::Region->find_vehicle( camera.Pos, 20, false, false ) ) ) }; // w trybie latania lokalizujemy wg mapy
if( vehicle == nullptr ) { return; } if( vehicle == nullptr ) { return; }
// if the nearest located vehicle doesn't have a direct driver, try to query its owner // if the nearest located vehicle doesn't have a direct driver, try to query its owner
@@ -313,7 +313,7 @@ debug_panel::update() {
m_scenariolines.clear(); m_scenariolines.clear();
m_eventqueuelines.clear(); m_eventqueuelines.clear();
m_cameralines.clear(); m_cameralines.clear();
m_rendererlines.clear(); m_rendererlines.clear();
update_section_vehicle( m_vehiclelines ); update_section_vehicle( m_vehiclelines );
update_section_engine( m_enginelines ); update_section_engine( m_enginelines );
@@ -322,7 +322,7 @@ debug_panel::update() {
update_section_scenario( m_scenariolines ); update_section_scenario( m_scenariolines );
update_section_eventqueue( m_eventqueuelines ); update_section_eventqueue( m_eventqueuelines );
update_section_camera( m_cameralines ); update_section_camera( m_cameralines );
update_section_renderer( m_rendererlines ); update_section_renderer( m_rendererlines );
} }
void void
@@ -348,17 +348,17 @@ debug_panel::render() {
} }
// sections // sections
ImGui::Separator(); ImGui::Separator();
render_section( "Vehicle", m_vehiclelines ); render_section( "Vehicle", m_vehiclelines );
render_section( "Vehicle Engine", m_enginelines ); render_section( "Vehicle Engine", m_enginelines );
render_section( "Vehicle AI", m_ailines ); render_section( "Vehicle AI", m_ailines );
render_section( "Vehicle Scan Table", m_scantablelines ); render_section( "Vehicle Scan Table", m_scantablelines );
render_section( "Scenario", m_scenariolines ); render_section( "Scenario", m_scenariolines );
if( true == render_section( "Scenario Event Queue", m_eventqueuelines ) ) { if( true == render_section( "Scenario Event Queue", m_eventqueuelines ) ) {
// event queue filter // event queue filter
ImGui::Checkbox( "By This Vehicle Only", &m_eventqueueactivevehicleonly ); ImGui::Checkbox( "By This Vehicle Only", &m_eventqueueactivevehicleonly );
} }
render_section( "Camera", m_cameralines ); render_section( "Camera", m_cameralines );
render_section( "Gfx Renderer", m_rendererlines ); render_section( "Gfx Renderer", m_rendererlines );
// toggles // toggles
ImGui::Separator(); ImGui::Separator();
ImGui::Checkbox( "Debug Mode", &DebugModeFlag ); ImGui::Checkbox( "Debug Mode", &DebugModeFlag );
@@ -367,7 +367,7 @@ debug_panel::render() {
ImGui::Indent(); ImGui::Indent();
ImGui::Checkbox( ImGui::Checkbox(
"Draw normal traction", "Draw normal traction",
&GfxRenderer.settings.force_normal_traction_render ); &GfxRenderer.settings.force_normal_traction_render );
ImGui::Unindent(); ImGui::Unindent();
} }
} }
@@ -839,7 +839,7 @@ debug_panel::update_section_camera( std::vector<text_line> &Output ) {
void void
debug_panel::update_section_renderer( std::vector<text_line> &Output ) { debug_panel::update_section_renderer( std::vector<text_line> &Output ) {
// gfx renderer data // gfx renderer data
auto textline = auto textline =
"FoV: " + to_string( Global.FieldOfView / Global.ZoomFactor, 1 ) "FoV: " + to_string( Global.FieldOfView / Global.ZoomFactor, 1 )
+ ", Draw range x " + to_string( Global.fDistanceFactor, 1 ) + ", Draw range x " + to_string( Global.fDistanceFactor, 1 )
@@ -861,7 +861,7 @@ debug_panel::update_section_renderer( std::vector<text_line> &Output ) {
Output.emplace_back( textline, Global.UITextColor ); Output.emplace_back( textline, Global.UITextColor );
// renderer stats // renderer stats
Output.emplace_back( GfxRenderer.info_times(), Global.UITextColor ); Output.emplace_back( GfxRenderer.info_times(), Global.UITextColor );
Output.emplace_back( GfxRenderer.info_stats(), Global.UITextColor ); Output.emplace_back( GfxRenderer.info_stats(), Global.UITextColor );
} }

View File

@@ -46,7 +46,7 @@ public:
: ui_panel( Name, Isopen ) {} : ui_panel( Name, Isopen ) {}
void update() override; void update() override;
void render() override; void render() override;
private: private:
// types // types
@@ -98,5 +98,5 @@ public:
: ui_panel( Name, Isopen ) {} : ui_panel( Name, Isopen ) {}
void update() override; void update() override;
void render() override; void render() override;
}; };

View File

@@ -262,7 +262,7 @@ itemproperties_panel::render() {
ImGui::TextColored( ImVec4( line.color.r, line.color.g, line.color.b, line.color.a ), line.data.c_str() ); ImGui::TextColored( ImVec4( line.color.r, line.color.g, line.color.b, line.color.a ), line.data.c_str() );
} }
// group section // group section
render_group(); render_group();
} }
ImGui::End(); ImGui::End();
} }

View File

@@ -20,12 +20,12 @@ public:
{} {}
void update( scene::basic_node const *Node ); void update( scene::basic_node const *Node );
void render() override; void render() override;
private: private:
// methods // methods
void update_group(); void update_group();
bool render_group(); bool render_group();
// members // members
scene::basic_node const *m_node { nullptr }; // scene node bound to the panel scene::basic_node const *m_node { nullptr }; // scene node bound to the panel

View File

@@ -209,7 +209,7 @@ CODE
// At this point you've got the texture data and you need to upload that your your graphic system: // At this point you've got the texture data and you need to upload that your your graphic system:
// After we have created the texture, store its pointer/identifier (_in whichever format your engine uses_) in 'io.Fonts->TexID'. // After we have created the texture, store its pointer/identifier (_in whichever format your engine uses_) in 'io.Fonts->TexID'.
// This will be passed back to your via the renderer. Basically ImTextureID == void*. Read FAQ below for details about ImTextureID. // This will be passed back to your via the renderer. Basically ImTextureID == void*. Read FAQ below for details about ImTextureID.
MyTexture* texture = MyEngine::CreateTextureFromMemoryPixels(pixels, width, height, TEXTURE_TYPE_RGBA32) MyTexture* texture = MyEngine::CreateTextureFromMemoryPixels(pixels, width, height, TEXTURE_TYPE_RGBA32)
io.Fonts->TexID = (void*)texture; io.Fonts->TexID = (void*)texture;
@@ -235,7 +235,7 @@ CODE
MyGameRender(); // may use any ImGui functions as well! MyGameRender(); // may use any ImGui functions as well!
// Render imgui, swap buffers // Render imgui, swap buffers
// (You want to try calling EndFrame/Render as late as you can, to be able to use imgui in your own game rendering code) // (You want to try calling EndFrame/Render as late as you can, to be able to use imgui in your own game rendering code)
ImGui::EndFrame(); ImGui::EndFrame();
ImGui::Render(); ImGui::Render();
ImDrawData* draw_data = ImGui::GetDrawData(); ImDrawData* draw_data = ImGui::GetDrawData();
@@ -250,7 +250,7 @@ CODE
void void MyImGuiRenderFunction(ImDrawData* draw_data) void void MyImGuiRenderFunction(ImDrawData* draw_data)
{ {
// TODO: Setup render state: alpha-blending enabled, no face culling, no depth testing, scissor enabled // TODO: Setup render state: alpha-blending enabled, no face culling, no depth testing, scissor enabled
// TODO: Setup viewport using draw_data->DisplaySize // TODO: Setup viewport using draw_data->DisplaySize
// TODO: Setup orthographic projection matrix cover draw_data->DisplayPos to draw_data->DisplayPos + draw_data->DisplaySize // TODO: Setup orthographic projection matrix cover draw_data->DisplayPos to draw_data->DisplayPos + draw_data->DisplaySize
// TODO: Setup shader: vertex { float2 pos, float2 uv, u32 color }, fragment shader sample color from 1 texture, multiply by vertex color. // TODO: Setup shader: vertex { float2 pos, float2 uv, u32 color }, fragment shader sample color from 1 texture, multiply by vertex color.
@@ -453,9 +453,9 @@ CODE
- 2015/08/05 (1.44) - split imgui.cpp into extra files: imgui_demo.cpp imgui_draw.cpp imgui_internal.h that you need to add to your project. - 2015/08/05 (1.44) - split imgui.cpp into extra files: imgui_demo.cpp imgui_draw.cpp imgui_internal.h that you need to add to your project.
- 2015/07/18 (1.44) - fixed angles in ImDrawList::PathArcTo(), PathArcToFast() (introduced in 1.43) being off by an extra PI for no justifiable reason - 2015/07/18 (1.44) - fixed angles in ImDrawList::PathArcTo(), PathArcToFast() (introduced in 1.43) being off by an extra PI for no justifiable reason
- 2015/07/14 (1.43) - add new ImFontAtlas::AddFont() API. For the old AddFont***, moved the 'font_no' parameter of ImFontAtlas::AddFont** functions to the ImFontConfig structure. - 2015/07/14 (1.43) - add new ImFontAtlas::AddFont() API. For the old AddFont***, moved the 'font_no' parameter of ImFontAtlas::AddFont** functions to the ImFontConfig structure.
you need to render your textured triangles with bilinear filtering to benefit from sub-pixel positioning of text. you need to render your textured triangles with bilinear filtering to benefit from sub-pixel positioning of text.
- 2015/07/08 (1.43) - switched rendering data to use indexed rendering. this is saving a fair amount of CPU/GPU and enables us to get anti-aliasing for a marginal cost. - 2015/07/08 (1.43) - switched rendering data to use indexed rendering. this is saving a fair amount of CPU/GPU and enables us to get anti-aliasing for a marginal cost.
this necessary change will break your rendering function! the fix should be very easy. sorry for that :( this necessary change will break your rendering function! the fix should be very easy. sorry for that :(
- if you are using a vanilla copy of one of the imgui_impl_XXXX.cpp provided in the example, you just need to update your copy and you can ignore the rest. - if you are using a vanilla copy of one of the imgui_impl_XXXX.cpp provided in the example, you just need to update your copy and you can ignore the rest.
- the signature of the io.RenderDrawListsFn handler has changed! - the signature of the io.RenderDrawListsFn handler has changed!
old: ImGui_XXXX_RenderDrawLists(ImDrawList** const cmd_lists, int cmd_lists_count) old: ImGui_XXXX_RenderDrawLists(ImDrawList** const cmd_lists, int cmd_lists_count)
@@ -463,8 +463,8 @@ CODE
argument: 'cmd_lists' becomes 'draw_data->CmdLists', 'cmd_lists_count' becomes 'draw_data->CmdListsCount' argument: 'cmd_lists' becomes 'draw_data->CmdLists', 'cmd_lists_count' becomes 'draw_data->CmdListsCount'
ImDrawList: 'commands' becomes 'CmdBuffer', 'vtx_buffer' becomes 'VtxBuffer', 'IdxBuffer' is new. ImDrawList: 'commands' becomes 'CmdBuffer', 'vtx_buffer' becomes 'VtxBuffer', 'IdxBuffer' is new.
ImDrawCmd: 'vtx_count' becomes 'ElemCount', 'clip_rect' becomes 'ClipRect', 'user_callback' becomes 'UserCallback', 'texture_id' becomes 'TextureId'. ImDrawCmd: 'vtx_count' becomes 'ElemCount', 'clip_rect' becomes 'ClipRect', 'user_callback' becomes 'UserCallback', 'texture_id' becomes 'TextureId'.
- each ImDrawList now contains both a vertex buffer and an index buffer. For each command, render ElemCount/3 triangles using indices from the index buffer. - each ImDrawList now contains both a vertex buffer and an index buffer. For each command, render ElemCount/3 triangles using indices from the index buffer.
- if you REALLY cannot render indexed primitives, you can call the draw_data->DeIndexAllBuffers() method to de-index the buffers. This is slow and a waste of CPU/GPU. Prefer using indexed rendering! - if you REALLY cannot render indexed primitives, you can call the draw_data->DeIndexAllBuffers() method to de-index the buffers. This is slow and a waste of CPU/GPU. Prefer using indexed rendering!
- refer to code in the examples/ folder or ask on the GitHub if you are unsure of how to upgrade. please upgrade! - refer to code in the examples/ folder or ask on the GitHub if you are unsure of how to upgrade. please upgrade!
- 2015/07/10 (1.43) - changed SameLine() parameters from int to float. - 2015/07/10 (1.43) - changed SameLine() parameters from int to float.
- 2015/07/02 (1.42) - renamed SetScrollPosHere() to SetScrollFromCursorPos(). Kept inline redirection function (will obsolete). - 2015/07/02 (1.42) - renamed SetScrollPosHere() to SetScrollFromCursorPos(). Kept inline redirection function (will obsolete).
@@ -497,7 +497,7 @@ CODE
became: unsigned char* pixels; int width, height; io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); <..Upload texture to GPU>; io.Fonts->TexId = YourTextureIdentifier; became: unsigned char* pixels; int width, height; io.Fonts->GetTexDataAsRGBA32(&pixels, &width, &height); <..Upload texture to GPU>; io.Fonts->TexId = YourTextureIdentifier;
you now more flexibility to load multiple TTF fonts and manage the texture buffer for internal needs. you now more flexibility to load multiple TTF fonts and manage the texture buffer for internal needs.
it is now recommended that you sample the font texture with bilinear interpolation. it is now recommended that you sample the font texture with bilinear interpolation.
(1.30) - added texture identifier in ImDrawCmd passed to your render function (we can now render images). make sure to set io.Fonts->TexID. (1.30) - added texture identifier in ImDrawCmd passed to your render function (we can now render images). make sure to set io.Fonts->TexID.
(1.30) - removed IO.PixelCenterOffset (unnecessary, can be handled in user projection matrix) (1.30) - removed IO.PixelCenterOffset (unnecessary, can be handled in user projection matrix)
(1.30) - removed ImGui::IsItemFocused() in favor of ImGui::IsItemActive() which handles all widgets (1.30) - removed ImGui::IsItemFocused() in favor of ImGui::IsItemActive() which handles all widgets
- 2014/12/10 (1.18) - removed SetNewWindowDefaultPos() in favor of new generic API SetNextWindowPos(pos, ImGuiSetCondition_FirstUseEver) - 2014/12/10 (1.18) - removed SetNewWindowDefaultPos() in favor of new generic API SetNextWindowPos(pos, ImGuiSetCondition_FirstUseEver)
@@ -539,15 +539,15 @@ CODE
Please read documentations or tutorials on your graphics API to understand how to display textures on the screen before moving onward. Please read documentations or tutorials on your graphics API to understand how to display textures on the screen before moving onward.
Long explanation: Long explanation:
- Dear ImGui's job is to create "meshes", defined in a renderer-agnostic format made of draw commands and vertices. - Dear ImGui's job is to create "meshes", defined in a renderer-agnostic format made of draw commands and vertices.
At the end of the frame those meshes (ImDrawList) will be displayed by your rendering function. They are made up of textured polygons and the code At the end of the frame those meshes (ImDrawList) will be displayed by your rendering function. They are made up of textured polygons and the code
to render them is generally fairly short (a few dozen lines). In the examples/ folder we provide functions for popular graphics API (OpenGL, DirectX, etc.). to render them is generally fairly short (a few dozen lines). In the examples/ folder we provide functions for popular graphics API (OpenGL, DirectX, etc.).
- Each rendering function decides on a data type to represent "textures". The concept of what is a "texture" is entirely tied to your underlying engine/graphics API. - Each rendering function decides on a data type to represent "textures". The concept of what is a "texture" is entirely tied to your underlying engine/graphics API.
We carry the information to identify a "texture" in the ImTextureID type. We carry the information to identify a "texture" in the ImTextureID type.
ImTextureID is nothing more that a void*, aka 4/8 bytes worth of data: just enough to store 1 pointer or 1 integer of your choice. ImTextureID is nothing more that a void*, aka 4/8 bytes worth of data: just enough to store 1 pointer or 1 integer of your choice.
Dear ImGui doesn't know or understand what you are storing in ImTextureID, it merely pass ImTextureID values until they reach your rendering function. Dear ImGui doesn't know or understand what you are storing in ImTextureID, it merely pass ImTextureID values until they reach your rendering function.
- In the examples/ bindings, for each graphics API binding we decided on a type that is likely to be a good representation for specifying - In the examples/ bindings, for each graphics API binding we decided on a type that is likely to be a good representation for specifying
an image from the end-user perspective. This is what the _examples_ rendering functions are using: an image from the end-user perspective. This is what the _examples_ rendering functions are using:
OpenGL: ImTextureID = GLuint (see ImGui_ImplGlfwGL3_RenderDrawData() function in imgui_impl_glfw_gl3.cpp) OpenGL: ImTextureID = GLuint (see ImGui_ImplGlfwGL3_RenderDrawData() function in imgui_impl_glfw_gl3.cpp)
DirectX9: ImTextureID = LPDIRECT3DTEXTURE9 (see ImGui_ImplDX9_RenderDrawData() function in imgui_impl_dx9.cpp) DirectX9: ImTextureID = LPDIRECT3DTEXTURE9 (see ImGui_ImplDX9_RenderDrawData() function in imgui_impl_dx9.cpp)
@@ -560,9 +560,9 @@ CODE
- If you have a custom engine built over e.g. OpenGL, instead of passing GLuint around you may decide to use a high-level data type to carry information about - If you have a custom engine built over e.g. OpenGL, instead of passing GLuint around you may decide to use a high-level data type to carry information about
the texture as well as how to display it (shaders, etc.). The decision of what to use as ImTextureID can always be made better knowing how your codebase the texture as well as how to display it (shaders, etc.). The decision of what to use as ImTextureID can always be made better knowing how your codebase
is designed. If your engine has high-level data types for "textures" and "material" then you may want to use them. is designed. If your engine has high-level data types for "textures" and "material" then you may want to use them.
If you are starting with OpenGL or DirectX or Vulkan and haven't built much of a rendering engine over them, keeping the default ImTextureID If you are starting with OpenGL or DirectX or Vulkan and haven't built much of a rendering engine over them, keeping the default ImTextureID
representation suggested by the example bindings is probably the best choice. representation suggested by the example bindings is probably the best choice.
(Advanced users may also decide to keep a low-level type in ImTextureID, and use ImDrawList callback and pass information to their renderer) (Advanced users may also decide to keep a low-level type in ImTextureID, and use ImDrawList callback and pass information to their renderer)
User code may do: User code may do:
@@ -570,7 +570,7 @@ CODE
MyTexture* texture = g_CoffeeTableTexture; MyTexture* texture = g_CoffeeTableTexture;
ImGui::Image((void*)texture, ImVec2(texture->Width, texture->Height)); ImGui::Image((void*)texture, ImVec2(texture->Width, texture->Height));
The renderer function called after ImGui::Render() will receive that same value that the user code passed: The renderer function called after ImGui::Render() will receive that same value that the user code passed:
// Cast ImTextureID / void* stored in the draw command as our texture type // Cast ImTextureID / void* stored in the draw command as our texture type
MyTexture* texture = (MyTexture*)pcmd->TextureId; MyTexture* texture = (MyTexture*)pcmd->TextureId;
@@ -596,11 +596,11 @@ CODE
glPixelStorei(GL_UNPACK_ROW_LENGTH, 0); glPixelStorei(GL_UNPACK_ROW_LENGTH, 0);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, image_width, image_height, 0, GL_RGBA, GL_UNSIGNED_BYTE, image_data); glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, image_width, image_height, 0, GL_RGBA, GL_UNSIGNED_BYTE, image_data);
// Now that we have an OpenGL texture, assuming our imgui rendering function (imgui_impl_xxx.cpp file) takes GLuint as ImTextureID, we can display it: // Now that we have an OpenGL texture, assuming our imgui rendering function (imgui_impl_xxx.cpp file) takes GLuint as ImTextureID, we can display it:
ImGui::Image((void*)(intptr_t)my_opengl_texture, ImVec2(my_image_width, my_image_height)); ImGui::Image((void*)(intptr_t)my_opengl_texture, ImVec2(my_image_width, my_image_height));
C/C++ tip: a void* is pointer-sized storage. You may safely store any pointer or integer into it by casting your value to ImTexture / void*, and vice-versa. C/C++ tip: a void* is pointer-sized storage. You may safely store any pointer or integer into it by casting your value to ImTexture / void*, and vice-versa.
Because both end-points (user code and rendering function) are under your control, you know exactly what is stored inside the ImTexture / void*. Because both end-points (user code and rendering function) are under your control, you know exactly what is stored inside the ImTexture / void*.
Examples: Examples:
GLuint my_tex = XXX; GLuint my_tex = XXX;
@@ -736,7 +736,7 @@ CODE
ImGuiIO& io = ImGui::GetIO(); ImGuiIO& io = ImGui::GetIO();
io.Fonts->AddFontFromFileTTF("myfontfile.ttf", size_in_pixels); io.Fonts->AddFontFromFileTTF("myfontfile.ttf", size_in_pixels);
io.Fonts->GetTexDataAsRGBA32() or GetTexDataAsAlpha8() io.Fonts->GetTexDataAsRGBA32() or GetTexDataAsAlpha8()
(default is ProggyClean.ttf, rendered at size 13, embedded in dear imgui's source code) (default is ProggyClean.ttf, rendered at size 13, embedded in dear imgui's source code)
New programmers: remember that in C/C++ and most programming languages if you want to use a New programmers: remember that in C/C++ and most programming languages if you want to use a
backslash \ within a string literal, you need to write it double backslash "\\": backslash \ within a string literal, you need to write it double backslash "\\":
@@ -1002,7 +1002,7 @@ ImGuiStyle::ImGuiStyle()
ButtonTextAlign = ImVec2(0.5f,0.5f);// Alignment of button text when button is larger than text. ButtonTextAlign = ImVec2(0.5f,0.5f);// Alignment of button text when button is larger than text.
DisplayWindowPadding = ImVec2(20,20); // Window position are clamped to be visible within the display area by at least this amount. Only applies to regular windows. DisplayWindowPadding = ImVec2(20,20); // Window position are clamped to be visible within the display area by at least this amount. Only applies to regular windows.
DisplaySafeAreaPadding = ImVec2(3,3); // If you cannot see the edge of your screen (e.g. on a TV) increase the safe area padding. Covers popups/tooltips as well regular windows. DisplaySafeAreaPadding = ImVec2(3,3); // If you cannot see the edge of your screen (e.g. on a TV) increase the safe area padding. Covers popups/tooltips as well regular windows.
MouseCursorScale = 1.0f; // Scale software rendered mouse cursor (when io.MouseDrawCursor is enabled). May be removed later. MouseCursorScale = 1.0f; // Scale software rendered mouse cursor (when io.MouseDrawCursor is enabled). May be removed later.
AntiAliasedLines = true; // Enable anti-aliasing on lines/borders. Disable if you are really short on CPU/GPU. AntiAliasedLines = true; // Enable anti-aliasing on lines/borders. Disable if you are really short on CPU/GPU.
AntiAliasedFill = true; // Enable anti-aliasing on filled shapes (rounded rectangles, circles, etc.) AntiAliasedFill = true; // Enable anti-aliasing on filled shapes (rounded rectangles, circles, etc.)
CurveTessellationTol = 1.25f; // Tessellation tolerance when using PathBezierCurveTo() without a specific number of segments. Decrease for highly tessellated curves (higher quality, more polygons), increase to reduce quality. CurveTessellationTol = 1.25f; // Tessellation tolerance when using PathBezierCurveTo() without a specific number of segments. Decrease for highly tessellated curves (higher quality, more polygons), increase to reduce quality.
@@ -2154,7 +2154,7 @@ void ImGui::RenderTextClipped(const ImVec2& pos_min, const ImVec2& pos_max, cons
if (clip_rect) // If we had no explicit clipping rectangle then pos==clip_min if (clip_rect) // If we had no explicit clipping rectangle then pos==clip_min
need_clipping |= (pos.x < clip_min->x) || (pos.y < clip_min->y); need_clipping |= (pos.x < clip_min->x) || (pos.y < clip_min->y);
// Align whole block. We should defer that to the better rendering function when we'll have support for individual line alignment. // Align whole block. We should defer that to the better rendering function when we'll have support for individual line alignment.
if (align.x > 0.0f) pos.x = ImMax(pos.x, pos.x + (pos_max.x - pos.x - text_size.x) * align.x); if (align.x > 0.0f) pos.x = ImMax(pos.x, pos.x + (pos_max.x - pos.x - text_size.x) * align.x);
if (align.y > 0.0f) pos.y = ImMax(pos.y, pos.y + (pos_max.y - pos.y - text_size.y) * align.y); if (align.y > 0.0f) pos.y = ImMax(pos.y, pos.y + (pos_max.y - pos.y - text_size.y) * align.y);
@@ -3145,7 +3145,7 @@ void ImGui::NewFrame()
g.OverlayDrawList.PushClipRectFullScreen(); g.OverlayDrawList.PushClipRectFullScreen();
g.OverlayDrawList.Flags = (g.Style.AntiAliasedLines ? ImDrawListFlags_AntiAliasedLines : 0) | (g.Style.AntiAliasedFill ? ImDrawListFlags_AntiAliasedFill : 0); g.OverlayDrawList.Flags = (g.Style.AntiAliasedLines ? ImDrawListFlags_AntiAliasedLines : 0) | (g.Style.AntiAliasedFill ? ImDrawListFlags_AntiAliasedFill : 0);
// Mark rendering data as invalid to prevent user who may have a handle on it to use it // Mark rendering data as invalid to prevent user who may have a handle on it to use it
g.DrawData.Clear(); g.DrawData.Clear();
// Drag and drop keep the source ID alive so even if the source disappear our state is consistent // Drag and drop keep the source ID alive so even if the source disappear our state is consistent
@@ -3243,7 +3243,7 @@ void ImGui::NewFrame()
g.CurrentPopupStack.resize(0); g.CurrentPopupStack.resize(0);
ClosePopupsOverWindow(g.NavWindow); ClosePopupsOverWindow(g.NavWindow);
// Create implicit window - we will only render it if the user has added something to it. // Create implicit window - we will only render it if the user has added something to it.
// We don't use "Debug" to avoid colliding with user trying to create a "Debug" window with custom flags. // We don't use "Debug" to avoid colliding with user trying to create a "Debug" window with custom flags.
SetNextWindowSize(ImVec2(400,400), ImGuiCond_FirstUseEver); SetNextWindowSize(ImVec2(400,400), ImGuiCond_FirstUseEver);
Begin("Debug##Default"); Begin("Debug##Default");
@@ -3375,9 +3375,9 @@ static void AddDrawListToDrawData(ImVector<ImDrawList*>* out_list, ImDrawList* d
// If this assert triggers because you are drawing lots of stuff manually: // If this assert triggers because you are drawing lots of stuff manually:
// A) Make sure you are coarse clipping, because ImDrawList let all your vertices pass. You can use the Metrics window to inspect draw list contents. // A) Make sure you are coarse clipping, because ImDrawList let all your vertices pass. You can use the Metrics window to inspect draw list contents.
// B) If you need/want meshes with more than 64K vertices, uncomment the '#define ImDrawIdx unsigned int' line in imconfig.h to set the index size to 4 bytes. // B) If you need/want meshes with more than 64K vertices, uncomment the '#define ImDrawIdx unsigned int' line in imconfig.h to set the index size to 4 bytes.
// You'll need to handle the 4-bytes indices to your renderer. For example, the OpenGL example code detect index size at compile-time by doing: // You'll need to handle the 4-bytes indices to your renderer. For example, the OpenGL example code detect index size at compile-time by doing:
// glDrawElements(GL_TRIANGLES, (GLsizei)pcmd->ElemCount, sizeof(ImDrawIdx) == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, idx_buffer_offset); // glDrawElements(GL_TRIANGLES, (GLsizei)pcmd->ElemCount, sizeof(ImDrawIdx) == 2 ? GL_UNSIGNED_SHORT : GL_UNSIGNED_INT, idx_buffer_offset);
// Your own engine or render API may use different parameters or function calls to specify index sizes. 2 and 4 bytes indices are generally supported by most API. // Your own engine or render API may use different parameters or function calls to specify index sizes. 2 and 4 bytes indices are generally supported by most API.
// C) If for some reason you cannot use 4 bytes indices or don't want to, a workaround is to call BeginChild()/EndChild() before reaching the 64K limit to split your draw commands in multiple draw lists. // C) If for some reason you cannot use 4 bytes indices or don't want to, a workaround is to call BeginChild()/EndChild() before reaching the 64K limit to split your draw commands in multiple draw lists.
if (sizeof(ImDrawIdx) == 2) if (sizeof(ImDrawIdx) == 2)
IM_ASSERT(draw_list->_VtxCurrentIdx < (1 << 16) && "Too many vertices in ImDrawList using 16-bit indices. Read comment above"); IM_ASSERT(draw_list->_VtxCurrentIdx < (1 << 16) && "Too many vertices in ImDrawList using 16-bit indices. Read comment above");
@@ -3389,12 +3389,12 @@ static void AddWindowToDrawData(ImVector<ImDrawList*>* out_render_list, ImGuiWin
{ {
ImGuiContext& g = *GImGui; ImGuiContext& g = *GImGui;
g.IO.MetricsRenderWindows++; g.IO.MetricsRenderWindows++;
AddDrawListToDrawData(out_render_list, window->DrawList); AddDrawListToDrawData(out_render_list, window->DrawList);
for (int i = 0; i < window->DC.ChildWindows.Size; i++) for (int i = 0; i < window->DC.ChildWindows.Size; i++)
{ {
ImGuiWindow* child = window->DC.ChildWindows[i]; ImGuiWindow* child = window->DC.ChildWindows[i];
if (IsWindowActiveAndVisible(child)) // clipped children may have been marked not active if (IsWindowActiveAndVisible(child)) // clipped children may have been marked not active
AddWindowToDrawData(out_render_list, child); AddWindowToDrawData(out_render_list, child);
} }
} }
@@ -3573,21 +3573,21 @@ void ImGui::Render()
ImGui::EndFrame(); ImGui::EndFrame();
g.FrameCountRendered = g.FrameCount; g.FrameCountRendered = g.FrameCount;
// Gather ImDrawList to render (for each active window) // Gather ImDrawList to render (for each active window)
g.IO.MetricsRenderVertices = g.IO.MetricsRenderIndices = g.IO.MetricsRenderWindows = 0; g.IO.MetricsRenderVertices = g.IO.MetricsRenderIndices = g.IO.MetricsRenderWindows = 0;
g.DrawDataBuilder.Clear(); g.DrawDataBuilder.Clear();
ImGuiWindow* windows_to_render_front_most[2]; ImGuiWindow* windows_to_render_front_most[2];
windows_to_render_front_most[0] = (g.NavWindowingTarget && !(g.NavWindowingTarget->Flags & ImGuiWindowFlags_NoBringToFrontOnFocus)) ? g.NavWindowingTarget->RootWindow : NULL; windows_to_render_front_most[0] = (g.NavWindowingTarget && !(g.NavWindowingTarget->Flags & ImGuiWindowFlags_NoBringToFrontOnFocus)) ? g.NavWindowingTarget->RootWindow : NULL;
windows_to_render_front_most[1] = g.NavWindowingTarget ? g.NavWindowingList : NULL; windows_to_render_front_most[1] = g.NavWindowingTarget ? g.NavWindowingList : NULL;
for (int n = 0; n != g.Windows.Size; n++) for (int n = 0; n != g.Windows.Size; n++)
{ {
ImGuiWindow* window = g.Windows[n]; ImGuiWindow* window = g.Windows[n];
if (IsWindowActiveAndVisible(window) && (window->Flags & ImGuiWindowFlags_ChildWindow) == 0 && window != windows_to_render_front_most[0] && window != windows_to_render_front_most[1]) if (IsWindowActiveAndVisible(window) && (window->Flags & ImGuiWindowFlags_ChildWindow) == 0 && window != windows_to_render_front_most[0] && window != windows_to_render_front_most[1])
AddWindowToDrawDataSelectLayer(window); AddWindowToDrawDataSelectLayer(window);
} }
for (int n = 0; n < IM_ARRAYSIZE(windows_to_render_front_most); n++) for (int n = 0; n < IM_ARRAYSIZE(windows_to_render_front_most); n++)
if (windows_to_render_front_most[n] && IsWindowActiveAndVisible(windows_to_render_front_most[n])) // NavWindowingTarget is always temporarily displayed as the front-most window if (windows_to_render_front_most[n] && IsWindowActiveAndVisible(windows_to_render_front_most[n])) // NavWindowingTarget is always temporarily displayed as the front-most window
AddWindowToDrawDataSelectLayer(windows_to_render_front_most[n]); AddWindowToDrawDataSelectLayer(windows_to_render_front_most[n]);
g.DrawDataBuilder.FlattenIntoSingleLayer(); g.DrawDataBuilder.FlattenIntoSingleLayer();
// Draw software mouse cursor if requested // Draw software mouse cursor if requested
@@ -5034,7 +5034,7 @@ bool ImGui::Begin(const char* name, bool* p_open, ImGuiWindowFlags flags)
//window->DrawList->AddRect(window->InnerRect.Min, window->InnerRect.Max, IM_COL32_WHITE); //window->DrawList->AddRect(window->InnerRect.Min, window->InnerRect.Max, IM_COL32_WHITE);
// Inner clipping rectangle // Inner clipping rectangle
// Force round operator last to ensure that e.g. (int)(max.x-min.x) in user's render code produce correct result. // Force round operator last to ensure that e.g. (int)(max.x-min.x) in user's render code produce correct result.
window->InnerClipRect.Min.x = ImFloor(0.5f + window->InnerMainRect.Min.x + ImMax(0.0f, ImFloor(window->WindowPadding.x*0.5f - window->WindowBorderSize))); window->InnerClipRect.Min.x = ImFloor(0.5f + window->InnerMainRect.Min.x + ImMax(0.0f, ImFloor(window->WindowPadding.x*0.5f - window->WindowBorderSize)));
window->InnerClipRect.Min.y = ImFloor(0.5f + window->InnerMainRect.Min.y); window->InnerClipRect.Min.y = ImFloor(0.5f + window->InnerMainRect.Min.y);
window->InnerClipRect.Max.x = ImFloor(0.5f + window->InnerMainRect.Max.x - ImMax(0.0f, ImFloor(window->WindowPadding.x*0.5f - window->WindowBorderSize))); window->InnerClipRect.Max.x = ImFloor(0.5f + window->InnerMainRect.Max.x - ImMax(0.0f, ImFloor(window->WindowPadding.x*0.5f - window->WindowBorderSize)));
@@ -5070,7 +5070,7 @@ bool ImGui::Begin(const char* name, bool* p_open, ImGuiWindowFlags flags)
window->HiddenFramesRegular = 1; window->HiddenFramesRegular = 1;
} }
// Don't render if style alpha is 0.0 at the time of Begin(). This is arbitrary and inconsistent but has been there for a long while (may remove at some point) // Don't render if style alpha is 0.0 at the time of Begin(). This is arbitrary and inconsistent but has been there for a long while (may remove at some point)
if (style.Alpha <= 0.0f) if (style.Alpha <= 0.0f)
window->HiddenFramesRegular = 1; window->HiddenFramesRegular = 1;
@@ -7514,7 +7514,7 @@ static void ImGui::NavUpdateWindowing()
g.NavWindowingHighlightAlpha = 1.0f; g.NavWindowingHighlightAlpha = 1.0f;
} }
// Single press toggles NavLayer, long press with L/R apply actual focus on release (until then the window was merely rendered front-most) // Single press toggles NavLayer, long press with L/R apply actual focus on release (until then the window was merely rendered front-most)
if (!IsNavInputDown(ImGuiNavInput_Menu)) if (!IsNavInputDown(ImGuiNavInput_Menu))
{ {
g.NavWindowingToggleLayer &= (g.NavWindowingHighlightAlpha < 1.0f); // Once button was held long enough we don't consider it a tap-to-toggle-layer press anymore. g.NavWindowingToggleLayer &= (g.NavWindowingHighlightAlpha < 1.0f); // Once button was held long enough we don't consider it a tap-to-toggle-layer press anymore.
@@ -7924,7 +7924,7 @@ void ImGui::EndColumns()
window->DrawList->AddLine(ImVec2(xi, ImMax(y1 + 1.0f, window->ClipRect.Min.y)), ImVec2(xi, ImMin(y2, window->ClipRect.Max.y)), col); window->DrawList->AddLine(ImVec2(xi, ImMax(y1 + 1.0f, window->ClipRect.Min.y)), ImVec2(xi, ImMin(y2, window->ClipRect.Max.y)), col);
} }
// Apply dragging after drawing the column lines, so our rendered lines are in sync with how items were displayed during the frame. // Apply dragging after drawing the column lines, so our rendered lines are in sync with how items were displayed during the frame.
if (dragging_column != -1) if (dragging_column != -1)
{ {
if (!columns->IsBeingResized) if (!columns->IsBeingResized)

14
scene.h
View File

@@ -63,7 +63,7 @@ struct scratch_data {
// TBD, TODO: replace with quadtree scheme? // TBD, TODO: replace with quadtree scheme?
class basic_cell { class basic_cell {
friend opengl_renderer; friend opengl_renderer;
public: public:
// constructors // constructors
@@ -150,7 +150,7 @@ public:
// sets center point of the cell // sets center point of the cell
void void
center( glm::dvec3 Center ); center( glm::dvec3 Center );
// generates renderable version of held non-instanced geometry in specified geometry bank // generates renderable version of held non-instanced geometry in specified geometry bank
void void
create_geometry( gfx::geometrybank_handle const &Bank ); create_geometry( gfx::geometrybank_handle const &Bank );
void create_map_geometry(std::vector<gfx::basic_vertex> &Bank); void create_map_geometry(std::vector<gfx::basic_vertex> &Bank);
@@ -193,7 +193,7 @@ private:
} m_directories; } m_directories;
// animation of owned items (legacy code, clean up along with track refactoring) // animation of owned items (legacy code, clean up along with track refactoring)
bool m_geometrycreated { false }; bool m_geometrycreated { false };
unsigned int m_framestamp { 0 }; // id of last rendered gfx frame unsigned int m_framestamp { 0 }; // id of last rendered gfx frame
TTrack *tTrackAnim = nullptr; // obiekty do przeliczenia animacji TTrack *tTrackAnim = nullptr; // obiekty do przeliczenia animacji
command_relay m_relay; command_relay m_relay;
}; };
@@ -201,7 +201,7 @@ private:
// basic scene partitioning structure, holds terrain geometry and collection of cells // basic scene partitioning structure, holds terrain geometry and collection of cells
class basic_section { class basic_section {
friend opengl_renderer; friend opengl_renderer;
public: public:
// constructors // constructors
@@ -274,7 +274,7 @@ public:
// sets center point of the section // sets center point of the section
void void
center( glm::dvec3 Center ); center( glm::dvec3 Center );
// generates renderable version of held non-instanced geometry // generates renderable version of held non-instanced geometry
void void
create_geometry(); create_geometry();
void create_map_geometry(const gfx::geometrybank_handle handle); void create_map_geometry(const gfx::geometrybank_handle handle);
@@ -303,7 +303,7 @@ private:
cell_array m_cells; // partitioning scheme cell_array m_cells; // partitioning scheme
shapenode_sequence m_shapes; // large pieces of opaque geometry and (legacy) terrain shapenode_sequence m_shapes; // large pieces of opaque geometry and (legacy) terrain
// TODO: implement dedicated, higher fidelity, fixed resolution terrain mesh item // TODO: implement dedicated, higher fidelity, fixed resolution terrain mesh item
// gfx renderer data // gfx renderer data
gfx::geometrybank_handle m_geometrybank; gfx::geometrybank_handle m_geometrybank;
bool m_geometrycreated { false }; bool m_geometrycreated { false };
@@ -313,7 +313,7 @@ private:
// top-level of scene spatial structure, holds collection of sections // top-level of scene spatial structure, holds collection of sections
class basic_region { class basic_region {
friend opengl_renderer; friend opengl_renderer;
public: public:
// constructors // constructors

View File

@@ -314,7 +314,7 @@ void ui_layer::render_panels()
{ {
for (auto *panel : m_panels) for (auto *panel : m_panels)
{ {
panel->render(); panel->render();
} }
} }

View File

@@ -24,8 +24,8 @@ public:
ui_panel( std::string const &Identifier, bool const Isopen ); ui_panel( std::string const &Identifier, bool const Isopen );
// methods // methods
virtual void update() {}; virtual void update() {};
virtual void render(); virtual void render();
virtual void render_contents(); virtual void render_contents();
// temporary access // temporary access
// types // types
struct text_line { struct text_line {
@@ -47,7 +47,7 @@ public:
std::deque<text_line> text_lines; std::deque<text_line> text_lines;
int window_flags = -1; int window_flags = -1;
std::string get_name() { return name; } const std::string& get_name() { return name; }
protected: protected:
// members // members
@@ -60,13 +60,13 @@ public:
bool is_expanded { false }; bool is_expanded { false };
void render_contents() override; void render_contents() override;
}; };
class ui_log_panel : public ui_panel { class ui_log_panel : public ui_panel {
using ui_panel::ui_panel; using ui_panel::ui_panel;
void render_contents() override; void render_contents() override;
}; };
class ui_layer { class ui_layer {
@@ -107,7 +107,7 @@ public:
update(); update();
// draws requested UI elements // draws requested UI elements
void void
render(); render();
// //
static static
void void
@@ -146,19 +146,19 @@ protected:
private: private:
// methods // methods
// render() subclass details // render() subclass details
virtual virtual
void void
render_() {}; render_() {};
// draws background quad with specified earlier texture // draws background quad with specified earlier texture
void void
render_background(); render_background();
// draws a progress bar in defined earlier state // draws a progress bar in defined earlier state
void void
render_progress(); render_progress();
void void
render_tooltip(); render_tooltip();
void render_panels(); void render_panels();
void render_menu(); void render_menu();

View File

@@ -58,74 +58,12 @@ float ui::map_panel::get_vehicle_rotation()
{ {
const TDynamicObject *vehicle = simulation::Train->Dynamic(); const TDynamicObject *vehicle = simulation::Train->Dynamic();
glm::vec3 front = glm::dvec3(vehicle->VectorFront()) * (vehicle->DirectionGet() > 0 ? 1.0 : -1.0); glm::vec3 front = glm::dvec3(vehicle->VectorFront()) * (vehicle->DirectionGet() > 0 ? 1.0 : -1.0);
glm::vec2 f2(front.x, front.z);
glm::vec2 north_ptr(0.0f, 1.0f); glm::vec2 north_ptr(0.0f, 1.0f);
return glm::atan(f2.y, f2.x) - glm::atan(north_ptr.y, north_ptr.x); return glm::atan(front.z, front.x) - glm::atan(north_ptr.y, north_ptr.x);
} }
void ui::map_panel::render_contents() void ui::map_panel::render_map_texture(glm::mat4 transform, glm::vec2 surface_size) {
{ cFrustum frustum;
if (!init_done)
return;
scene::basic_region *Region = simulation::Region;
float prevzoom = zoom;
if (ImGui::Button("-"))
zoom /= 2;
ImGui::SameLine();
if (ImGui::Button("+"))
zoom *= 2;
ImGui::SameLine();
float x = zoom / prevzoom;
translate *= x;
glm::mat4 transform;
transform[0][0] = -1.0f;
static int mode = 0;
ImGui::RadioButton("manual", &mode, 0); ImGui::SameLine();
ImGui::RadioButton("cam", &mode, 1); ImGui::SameLine();
ImGui::RadioButton("vehicle", &mode, 2);
ImVec2 size = ImGui::GetContentRegionAvail();
float aspectx = size.y / size.x;
float aspectz = size.x / size.y;
if (aspectx > aspectz)
transform = glm::scale(transform, glm::vec3(aspectx, 1.0f, 1.0f));
else
transform = glm::scale(transform, glm::vec3(1.0f, 1.0f, aspectz));
if (mode == 2 && simulation::Train && simulation::Train->Dynamic())
{
float rot = get_vehicle_rotation();
transform = glm::rotate(transform, rot, glm::vec3(0.0f, 1.0f, 0.0f));
glm::dvec3 vpos = simulation::Train->Dynamic()->GetPosition();
translate = glm::vec2(vpos.x, vpos.z) * -zoom;
}
else if (mode == 1)
{
float rot;
if (FreeFlyModeFlag)
rot = glm::pi<float>() - Global.pCamera.Angle.y;
else
rot = get_vehicle_rotation() - Global.pCamera.Angle.y;
transform = glm::rotate(transform, rot, glm::vec3(0.0f, 1.0f, 0.0f));
glm::dvec3 vpos = Global.pCamera.Pos;
translate = glm::vec2(vpos.x, vpos.z) * -zoom;
}
transform = glm::translate(transform, glm::vec3(translate.x, 0.0f, translate.y));
transform = glm::scale(transform, glm::vec3(zoom));
frustum.calculate(transform, glm::mat4()); frustum.calculate(transform, glm::mat4());
m_section_handles.clear(); m_section_handles.clear();
@@ -134,10 +72,10 @@ void ui::map_panel::render_contents()
{ {
for (int column = 0; column < scene::EU07_REGIONSIDESECTIONCOUNT; column++) for (int column = 0; column < scene::EU07_REGIONSIDESECTIONCOUNT; column++)
{ {
scene::basic_section *s = Region->get_section(row * scene::EU07_REGIONSIDESECTIONCOUNT + column); scene::basic_section *section = simulation::Region->get_section(row * scene::EU07_REGIONSIDESECTIONCOUNT + column);
if (s && frustum.sphere_inside(s->area().center, s->area().radius) > 0.f) if (section && frustum.sphere_inside(section->area().center, section->area().radius) > 0.f)
{ {
const gfx::geometrybank_handle handle = s->get_map_geometry(); const gfx::geometrybank_handle handle = section->get_map_geometry();
if (handle != null_handle) if (handle != null_handle)
m_section_handles.push_back(handle); m_section_handles.push_back(handle);
} }
@@ -162,46 +100,152 @@ void ui::map_panel::render_contents()
m_shader->bind(); m_shader->bind();
glLineWidth(1.5f); glLineWidth(1.5f);
glViewport(0, 0, size.x, size.y); glViewport(0, 0, surface_size.x, surface_size.y);
GfxRenderer.Draw_Geometry(m_section_handles.begin(), m_section_handles.end()); GfxRenderer.Draw_Geometry(m_section_handles.begin(), m_section_handles.end());
if (Global.iMultisampling) if (Global.iMultisampling)
m_fb->blit_from(m_msaa_fb.get(), size.x, size.y, GL_COLOR_BUFFER_BIT, GL_COLOR_ATTACHMENT0); m_fb->blit_from(m_msaa_fb.get(), surface_size.x, surface_size.y, GL_COLOR_BUFFER_BIT, GL_COLOR_ATTACHMENT0);
gl::framebuffer::unbind(); gl::framebuffer::unbind();
m_shader->unbind(); m_shader->unbind();
}
ImVec2 origin = ImGui::GetCursorPos(); void ui::map_panel::render_labels(glm::mat4 transform, ImVec2 origin, glm::vec2 surface_size)
ImGui::ImageButton(reinterpret_cast<void*>(m_tex->id), size, ImVec2(0, size.y / fb_size), ImVec2(size.x / fb_size, 0), 0); {
if (mode == 0 && ImGui::IsItemHovered() && ImGui::IsMouseDragging())
{
ImVec2 ivdelta = ImGui::GetMouseDragDelta();
ImGui::ResetMouseDragDelta();
glm::vec2 delta(ivdelta.x, ivdelta.y);
delta.x /= size.x;
delta.y /= size.y;
translate -= delta * 2.0f;
}
ImGui::PushStyleColor(ImGuiCol_Text, ImVec4(0.7f, 1.0f, 0.7f, 1.0f)); ImGui::PushStyleColor(ImGuiCol_Text, ImVec4(0.7f, 1.0f, 0.7f, 1.0f));
for (TDynamicObject *vehicle : simulation::Vehicles.sequence()) { for (TDynamicObject *vehicle : simulation::Vehicles.sequence()) {
if (vehicle->Prev()) if (vehicle->Prev() || !vehicle->Mechanik)
continue;
if (vehicle->Mechanik->TrainName().empty())
continue; continue;
glm::vec4 pos = transform * glm::vec4(glm::vec3(vehicle->GetPosition()), 1.0f); glm::vec4 ndc_pos = transform * glm::vec4(glm::vec3(vehicle->GetPosition()), 1.0f);
if (glm::abs(pos.x) > 1.0f || glm::abs(pos.z) > 1.0f) if (glm::abs(ndc_pos.x) > 1.0f || glm::abs(ndc_pos.z) > 1.0f)
continue; continue;
glm::vec2 textpos = (glm::vec2(pos.x, -pos.z) / 2.0f + 0.5f) * glm::vec2(size.x, size.y); glm::vec2 gui_pos = (glm::vec2(ndc_pos.x, -ndc_pos.z) / 2.0f + 0.5f) * glm::vec2(surface_size.x, surface_size.y);
TDynamicObject *veh = vehicle;
const char *desc = vehicle->Mechanik->TrainName().c_str(); const char *desc = vehicle->Mechanik->TrainName().c_str();
ImVec2 textsize = ImGui::CalcTextSize(desc); ImVec2 textsize = ImGui::CalcTextSize(desc);
ImGui::SetCursorPos(ImVec2(origin.x + textpos.x - textsize.x / 2.0f, ImGui::SetCursorPos(ImVec2(origin.x + gui_pos.x - textsize.x / 2.0f,
origin.y + textpos.y - textsize.y / 2.0f)); origin.y + gui_pos.y - textsize.y / 2.0f));
ImGui::TextUnformatted(desc); ImGui::TextUnformatted(desc);
} }
ImGui::PopStyleColor(); ImGui::PopStyleColor();
} }
void ui::map_panel::render_contents()
{
if (!init_done)
return;
float prev_zoom = zoom;
if (ImGui::Button("-"))
zoom /= 2;
ImGui::SameLine();
if (ImGui::Button("+"))
zoom *= 2;
ImGui::SameLine();
float x = zoom / prev_zoom;
translate *= x;
glm::mat4 transform;
transform[0][0] = -1.0f;
static enum {
MODE_MANUAL = 0,
MODE_CAMERA,
MODE_VEHICLE
} mode = MODE_MANUAL;
ImGui::RadioButton("manual", (int*)&mode, 0); ImGui::SameLine();
ImGui::RadioButton("cam", (int*)&mode, 1); ImGui::SameLine();
ImGui::RadioButton("vehicle", (int*)&mode, 2);
ImVec2 surface_size_im = ImGui::GetContentRegionAvail();
glm::vec2 surface_size(surface_size_im.x, surface_size_im.y);
float aspect = surface_size.y / surface_size.x;
if (aspect > 1.0f / aspect)
transform = glm::scale(transform, glm::vec3(aspect, 1.0f, 1.0f));
else
transform = glm::scale(transform, glm::vec3(1.0f, 1.0f, 1.0f / aspect));
if (mode == MODE_VEHICLE && simulation::Train)
{
float rotation = get_vehicle_rotation();
transform = glm::rotate(transform, rotation, glm::vec3(0.0f, 1.0f, 0.0f));
glm::dvec3 position = simulation::Train->Dynamic()->GetPosition();
translate = glm::vec2(position.x, position.z) * -zoom;
}
if (mode == MODE_CAMERA)
{
float initial_rotation;
if (!FreeFlyModeFlag)
initial_rotation = get_vehicle_rotation();
else
initial_rotation = glm::pi<float>();
float rotation = initial_rotation - Global.pCamera.Angle.y;
transform = glm::rotate(transform, rotation, glm::vec3(0.0f, 1.0f, 0.0f));
glm::dvec3 position = Global.pCamera.Pos;
translate = glm::vec2(position.x, position.z) * -zoom;
}
transform = glm::translate(transform, glm::vec3(translate.x, 0.0f, translate.y));
transform = glm::scale(transform, glm::vec3(zoom));
render_map_texture(transform, surface_size);
ImVec2 window_origin = ImGui::GetCursorPos();
ImVec2 screen_origin = ImGui::GetCursorScreenPos();
ImGui::ImageButton(reinterpret_cast<void*>(m_tex->id), surface_size_im, ImVec2(0, surface_size.y / fb_size), ImVec2(surface_size.x / fb_size, 0), 0);
if (ImGui::IsItemHovered())
{
if (mode == 0 && ImGui::IsMouseDragging(0)) {
WriteLog("drag");
ImVec2 delta_im = ImGui::GetMouseDragDelta();
ImGui::ResetMouseDragDelta();
glm::vec2 delta(delta_im.x, delta_im.y);
delta.x /= surface_size.x;
delta.y /= surface_size.y;
translate -= delta * 2.0f;
}
if (ImGui::IsMouseClicked(1)) {
WriteLog("click");
ImVec2 screen_pos = ImGui::GetMousePos();
glm::vec2 surface_pos(screen_pos.x - screen_origin.x, screen_pos.y - screen_origin.y);
glm::vec2 ndc_pos = surface_pos / surface_size * 2.0f - 1.0f;
glm::vec3 world_pos = glm::inverse(transform) * glm::vec4(ndc_pos.x, 0.0f, -ndc_pos.y, 1.0f);
std::vector<TEventLauncher *> launchers = simulation::Events.find_eventlaunchers(glm::vec2(world_pos.x, world_pos.z), 10.0f);
for (auto launcher : launchers) {
command_relay relay;
if (!Global.shiftState && launcher->Event1)
relay.post(user_command::queueevent, (double)simulation::Events.GetEventId(launcher->Event1), 0.0, GLFW_PRESS, 0);
else if (launcher->Event2)
relay.post(user_command::queueevent, (double)simulation::Events.GetEventId(launcher->Event2), 0.0, GLFW_PRESS, 0);
}
WriteLog(std::to_string(world_pos.x) + "," + std::to_string(world_pos.z));
}
}
render_labels(transform, window_origin, surface_size);
}

View File

@@ -10,7 +10,7 @@ namespace ui {
class map_panel : public ui_panel { class map_panel : public ui_panel {
std::unique_ptr<gl::program> m_shader; std::unique_ptr<gl::program> m_shader;
std::unique_ptr<gl::framebuffer> m_msaa_fb; std::unique_ptr<gl::framebuffer> m_msaa_fb;
std::unique_ptr<gl::renderbuffer> m_msaa_rb; std::unique_ptr<gl::renderbuffer> m_msaa_rb;
std::unique_ptr<gl::framebuffer> m_fb; std::unique_ptr<gl::framebuffer> m_fb;
std::unique_ptr<opengl_texture> m_tex; std::unique_ptr<opengl_texture> m_tex;
@@ -25,7 +25,8 @@ class map_panel : public ui_panel {
glm::vec2 translate; glm::vec2 translate;
float zoom = 1.0f / 1000.0f; float zoom = 1.0f / 1000.0f;
float get_vehicle_rotation(); float get_vehicle_rotation();
cFrustum frustum; void render_map_texture(glm::mat4 transform, glm::vec2 surface_size);
void render_labels(glm::mat4 transform, ImVec2 origin, glm::vec2 surface_size);
bool init_done = false; bool init_done = false;