Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion code/addons/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -14,4 +14,5 @@ add_subdirectory(tinyxml)
add_subdirectory(nsharp)
add_addon(tbui)
add_subdirectory(multiplayer)
add_subdirectory(navigationfeature)
add_subdirectory(navigationfeature)
add_subdirectory(navigationfeaturemodule)
18 changes: 9 additions & 9 deletions code/addons/dynui/console/imguiconsole.cc
Original file line number Diff line number Diff line change
Expand Up @@ -392,16 +392,16 @@ ImguiConsole::RenderContent()
// Unfortunately we can't use ImGui::Clipper here since each entry might have a different height.
// TODO: We could roll our own "clipper".
ImGui::PushTextWrapPos(ImGui::GetWindowContentRegionMax().x);
for (int i = 0; i < consoleBuffer.Size(); i++)
for (int i = 0; i < this->consoleBuffer.Size(); i++)
{
const char* item = consoleBuffer[i].msg.AsCharPtr();
const char* item = this->consoleBuffer[i].msg.AsCharPtr();

//Filter on both time, prefix and entry
if (!filter.PassFilter(item) && !filter.PassFilter(this->LogEntryTypeAsCharPtr(consoleBuffer[i].type)))
if (!filter.PassFilter(item) && !filter.PassFilter(this->LogEntryTypeAsCharPtr(this->consoleBuffer[i].type)))
continue;

ImVec4 col;
switch (consoleBuffer[i].type)
switch (this->consoleBuffer[i].type)
{
case N_MESSAGE:
col = ImVec4(1.0f, 1.0f, 1.0f, 1.0f);
Expand All @@ -428,9 +428,9 @@ ImguiConsole::RenderContent()
ImGui::PushStyleColor(ImGuiCol_Text, col);
ImGui::SameLine();
//Print message prefix
if (consoleBuffer[i].type != N_MESSAGE)
if (this->consoleBuffer[i].type != N_MESSAGE)
{
ImGui::TextUnformatted(this->LogEntryTypeAsCharPtr(consoleBuffer[i].type));
ImGui::TextUnformatted(this->LogEntryTypeAsCharPtr(this->consoleBuffer[i].type));
ImGui::SameLine();
}
//Print log entry
Expand All @@ -441,11 +441,11 @@ ImguiConsole::RenderContent()
ImGui::PopTextWrapPos();

static SizeT lastConsoleBufferSize = 0;
if (this->scrollToBottom && consoleBuffer.Size() != lastConsoleBufferSize)
if (this->scrollToBottom && this->consoleBuffer.Size() != lastConsoleBufferSize)
{
ImGui::SetScrollHereY();
}
lastConsoleBufferSize = consoleBuffer.Size();
lastConsoleBufferSize = this->consoleBuffer.Size();

ImGui::PopStyleVar();
ImGui::EndChild();
Expand Down Expand Up @@ -634,7 +634,7 @@ ImguiConsole::Execute(const Util::String& command)
void
ImguiConsole::AppendToLog(const LogEntry& msg)
{
this->consoleBuffer.Add(msg);
this->consoleBuffer.Add(msg);
}

//------------------------------------------------------------------------------
Expand Down
136 changes: 124 additions & 12 deletions code/addons/dynui/imguicontext.cc
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,8 @@ struct ImguiState
Ptr<ImguiInputHandler> inputHandler;
Ptr<ImguiDisplayEventHandler> displayEventHandler;
bool dockOverViewport;
bool graphicsContextRegistered;
bool renderingEnabled;
} state;

IndexT VertexBufferOffset = 0;
Expand All @@ -78,6 +80,38 @@ SizeT TotalIndicesThisFrame = 0;

static Core::CVar* ui_opacity;

//------------------------------------------------------------------------------
/**
*/
static void
ImguiNoOpPipelineSetup(const CoreGraphics::RenderPassId)
{
// Intentionally empty. Used to clear stale framescript callbacks after reload failures.
}

//------------------------------------------------------------------------------
/**
*/
static void
ImguiNoOpDraw(const CoreGraphics::CmdBufferId, const CoreGraphics::QueueType, const Math::rectangle<int>&, const IndexT, const IndexT)
{
// Intentionally empty. Used to clear stale framescript callbacks after reload failures.
}

//------------------------------------------------------------------------------
/**
*/
static void
DisableImguiFramescriptCallbacks()
{
#if WITH_NEBULA_EDITOR
FrameScript_editorframe::RegisterSubgraphPipelines_ImGUI_Render(ImguiNoOpPipelineSetup);
FrameScript_editorframe::RegisterSubgraph_ImGUI_Render(ImguiNoOpDraw);
#endif
FrameScript_default::RegisterSubgraphPipelines_ImGUI_Render(ImguiNoOpPipelineSetup);
FrameScript_default::RegisterSubgraph_ImGUI_Render(ImguiNoOpDraw);
}

ImFont* ImguiNormalFont;
ImFont* ImguiSmallFont;
ImFont* ImguiBoldFont;
Expand All @@ -90,6 +124,11 @@ ImFont* ImguiItFont;
void
ImguiDrawFunction(const CoreGraphics::CmdBufferId cmdBuf, const Math::rectangle<int>& viewport, ImDrawData* data)
{
if (!state.renderingEnabled)
{
return;
}

// get Imgui context
ImGuiIO& io = ImGui::GetIO();
int fb_width = (int)(viewport.width() * io.DisplayFramebufferScale.x);
Expand All @@ -100,9 +139,20 @@ ImguiDrawFunction(const CoreGraphics::CmdBufferId cmdBuf, const Math::rectangle<
//const Ptr<BufferLock>& vboLock = renderer->GetVertexBufferLock();
//const Ptr<BufferLock>& iboLock = renderer->GetIndexBufferLock();
IndexT currentBuffer = CoreGraphics::GetBufferedFrameIndex();
if (currentBuffer < 0 || currentBuffer >= state.vbos.Size() || currentBuffer >= state.ibos.Size())
{
n_warning("ImguiDrawFunction(): buffer index %d out of bounds (vbos=%d, ibos=%d), skipping UI draw", currentBuffer, state.vbos.Size(), state.ibos.Size());
return;
}
BufferId vbo = state.vbos[currentBuffer];
BufferId ibo = state.ibos[currentBuffer];

if (vbo == CoreGraphics::InvalidBufferId || ibo == CoreGraphics::InvalidBufferId)
{
n_warning("ImguiDrawFunction(): invalid UI buffers for buffered frame %d, skipping UI draw", currentBuffer);
return;
}

N_CMD_SCOPE(cmdBuf, NEBULA_MARKER_GRAPHICS, "ImGUI");

// apply shader
Expand Down Expand Up @@ -418,14 +468,26 @@ ImguiContext::Create()
{
ui_opacity = Core::CVarCreate(Core::CVar_Float, "ui_opacity", "1.0", "Global UI opacity (0..1)");

__bundle.OnViewportResized = ImguiContext::OnViewportResized;
Graphics::GraphicsServer::Instance()->RegisterGraphicsContext(&__bundle, &__state);

state.dockOverViewport = false;
state.graphicsContextRegistered = false;
state.renderingEnabled = false;

// allocate imgui shader
state.uiShader = CoreGraphics::ShaderGet("shd:imgui/shaders/imgui.gplb");
if (state.uiShader == CoreGraphics::InvalidShaderId)
{
DisableImguiFramescriptCallbacks();
n_error("ImguiContext::Create: Failed to load imgui shader 'shd:imgui/shaders/imgui.gplb'\n");
return;
}

state.prog = CoreGraphics::ShaderGetProgram(state.uiShader, CoreGraphics::ShaderFeatureMask("Static"));
if (state.prog == CoreGraphics::InvalidShaderProgramId)
{
DisableImguiFramescriptCallbacks();
n_error("ImguiContext::Create: Failed to get 'Static' program from imgui shader\n");
return;
}

state.resourceTable = CoreGraphics::ShaderCreateResourceTable(state.uiShader, NEBULA_BATCH_GROUP);

Expand All @@ -452,6 +514,9 @@ ImguiContext::Create()
{
FrameScript_editorframe::RegisterSubgraphPipelines_ImGUI_Render([](const CoreGraphics::RenderPassId pass)
{
if (!state.renderingEnabled)
return;

CoreGraphics::InputAssemblyKey inputAssembly{ CoreGraphics::PrimitiveTopology::TriangleList, false };
if (state.editorPipeline != CoreGraphics::InvalidPipelineId)
CoreGraphics::DestroyGraphicsPipeline(state.editorPipeline);
Expand All @@ -460,6 +525,9 @@ ImguiContext::Create()

FrameScript_editorframe::RegisterSubgraph_ImGUI_Render([](const CoreGraphics::CmdBufferId cmdBuf, const CoreGraphics::QueueType queue, const Math::rectangle<int>& viewport, const IndexT frame, const IndexT bufferIndex)
{
if (!state.renderingEnabled)
return;

#ifdef NEBULA_NO_DYNUI_ASSERTS
ImguiContext::RecoverImGuiContextErrors();
#endif
Expand Down Expand Up @@ -497,22 +565,33 @@ ImguiContext::Create()
ImguiDrawFunction(cmdBuf, viewport, ImGui::GetDrawData());
}
IndexT currentBuffer = CoreGraphics::GetBufferedFrameIndex();
CoreGraphics::BufferFlush(state.vbos[currentBuffer]);
CoreGraphics::BufferFlush(state.ibos[currentBuffer]);
if (currentBuffer >= 0 && currentBuffer < state.vbos.Size() && currentBuffer < state.ibos.Size())
{
if (state.vbos[currentBuffer] != CoreGraphics::InvalidBufferId)
CoreGraphics::BufferFlush(state.vbos[currentBuffer]);
if (state.ibos[currentBuffer] != CoreGraphics::InvalidBufferId)
CoreGraphics::BufferFlush(state.ibos[currentBuffer]);
}
});
}
else
#endif
{
FrameScript_default::RegisterSubgraphPipelines_ImGUI_Render([](const CoreGraphics::RenderPassId pass)
{
if (!state.renderingEnabled)
return;

CoreGraphics::InputAssemblyKey inputAssembly{ CoreGraphics::PrimitiveTopology::TriangleList, false };
if (state.pipeline != CoreGraphics::InvalidPipelineId)
CoreGraphics::DestroyGraphicsPipeline(state.pipeline);
state.pipeline = CoreGraphics::CreateGraphicsPipeline({ state.prog, CoreGraphics::InvalidPassId, 0, pass, inputAssembly });
});
FrameScript_default::RegisterSubgraph_ImGUI_Render([](const CoreGraphics::CmdBufferId cmdBuf, const CoreGraphics::QueueType queue, const Math::rectangle<int>& viewport, const IndexT frame, const IndexT bufferIndex)
{
if (!state.renderingEnabled)
return;

#ifdef NEBULA_NO_DYNUI_ASSERTS
ImguiContext::RecoverImGuiContextErrors();
#endif
Expand Down Expand Up @@ -550,8 +629,17 @@ ImguiContext::Create()
ImguiDrawFunction(cmdBuf, viewport, ImGui::GetDrawData());
}
IndexT currentBuffer = CoreGraphics::GetBufferedFrameIndex();
CoreGraphics::BufferFlush(state.vbos[currentBuffer]);
CoreGraphics::BufferFlush(state.ibos[currentBuffer]);
if (currentBuffer >= 0 && currentBuffer < state.vbos.Size() && currentBuffer < state.ibos.Size())
{
if (state.vbos[currentBuffer] != CoreGraphics::InvalidBufferId)
{
CoreGraphics::BufferFlush(state.vbos[currentBuffer]);
}
if (state.ibos[currentBuffer] != CoreGraphics::InvalidBufferId)
{
CoreGraphics::BufferFlush(state.ibos[currentBuffer]);
}
}
});
}

Expand Down Expand Up @@ -873,6 +961,11 @@ ImguiContext::Create()
}
ImGui::LoadIniSettingsFromDisk("imgui.ini");
}

__bundle.OnViewportResized = ImguiContext::OnViewportResized;
Graphics::GraphicsServer::Instance()->RegisterGraphicsContext(&__bundle, &__state);
state.graphicsContextRegistered = true;
state.renderingEnabled = true;
}

//------------------------------------------------------------------------------
Expand All @@ -881,6 +974,9 @@ ImguiContext::Create()
void
ImguiContext::Discard()
{
state.renderingEnabled = false;
DisableImguiFramescriptCallbacks();

IndexT i;
for (i = 0; i < state.vbos.Size(); i++)
{
Expand All @@ -894,13 +990,29 @@ ImguiContext::Discard()
state.indexPtrs[i] = nullptr;
}

Input::InputServer::Instance()->RemoveInputHandler(state.inputHandler.upcast<InputHandler>());
state.inputHandler = nullptr;
if (state.inputHandler != nullptr)
{
Input::InputServer::Instance()->RemoveInputHandler(state.inputHandler.upcast<InputHandler>());
state.inputHandler = nullptr;
}

CoreGraphics::DisplayDevice::Instance()->RemoveEventHandler(state.displayEventHandler.upcast<CoreGraphics::DisplayEventHandler>());
state.displayEventHandler = nullptr;
if (state.displayEventHandler != nullptr)
{
CoreGraphics::DisplayDevice::Instance()->RemoveEventHandler(state.displayEventHandler.upcast<CoreGraphics::DisplayEventHandler>());
state.displayEventHandler = nullptr;
}

CoreGraphics::DestroyTexture((CoreGraphics::TextureId)state.fontTexture.nebulaHandle);
if (state.graphicsContextRegistered)
{
Graphics::GraphicsServer::Instance()->UnregisterGraphicsContext(&__bundle);
state.graphicsContextRegistered = false;
}

if ((CoreGraphics::TextureId)state.fontTexture.nebulaHandle != CoreGraphics::InvalidTextureId)
{
CoreGraphics::DestroyTexture((CoreGraphics::TextureId)state.fontTexture.nebulaHandle);
state.fontTexture.nebulaHandle = CoreGraphics::InvalidTextureId;
}

#ifdef IMGUI_HAS_VIEWPORT
/// The main window is handled by nebula
Expand Down
9 changes: 9 additions & 0 deletions code/addons/memdb/attributeregistry.cc
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,15 @@ AttributeRegistry::Instance()

//------------------------------------------------------------------------------
/**
*/
bool
AttributeRegistry::HasInstance()
{
return Singleton != nullptr;
}

//------------------------------------------------------------------------------
/**
This static method is used to destroy the registry object and should be
called right before the main function exits. It will make sure that
no accidential memory leaks are reported by the debug heap.
Expand Down
Loading
Loading