You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
If you're making examples then showing how the example can be integrated into a pre-existing imgui app would be good - turns out to be only a handful of lines of code but it took me hours to figure out what they were.
The following uses the blueprint example and layouts (which seems to be a drop-in replacement for ImGui
My existing app was built on the imgui docking branch so although there appears to be absolutely no explanation of what each of the branches are for I picked this one (because it mentioned docking...) https://github.com/thedmd/imgui/tree/feature/docking-layout-external
// Put this in your normal ImGui rendering loop
if (ImGui::Begin("nodeEditor")) {
static bool showStyleEditor = false;
if (ImGui::Button("Style Editor")) // show the style panel (I'm using docking so this appears as a separate viewport)
showStyleEditor = !showStyleEditor;
ImGui::SameLine();
static bool showFlow = false;
if (ImGui::Button("Show Flow")) // show flow dots for direction of link (this isn't working for me yet)
showFlow = !showFlow;
ImGui::SameLine();
static bool stopBlueprint = false;
if (ImGui::Button("Stop Editor")) // this triggers destruction of the editor ready for a fresh start
stopBlueprint = !stopBlueprint;
BlueprintNE_Main(showStyleEditor, showFlow, stopBlueprint);
}
ImGui::End();
This should replace the main() function in the blueprint example
(admittedly flow isn't yet working but I think that is a bigger issue as it doesn't trigger with the z key either)
void BlueprintNE_Main(bool& showStyleEditor, bool& showFlow, bool& stop)
{
static Example blueprintNodeEditor("Blueprints"); // 'Example' is the name of the struct. This is annoying because of conflicts with other examples but is what it is. It should be called something unique (eg BlueprintEditorStructV1)
static bool needsStart = true;
if (needsStart && stop) // if called with stop then don't progress if onStop has already been called.
return;
if (needsStart) {
needsStart = false;
blueprintNodeEditor.OnStart(); // Initialize editor. This loads the config and spawns hardcoded nodes. Ideally these should be loaded from file as a separate step
}
if (stop) {
blueprintNodeEditor.OnStop(); // Release textures and destroy editor
needsStart = true; // will need to be restarted if we want to use the editor again
return;
}
if (!showStyleEditor)
ImGui::SetCursorPos({ 5, 75 });
else
ImGui::SetCursorPos({ 250, 75 });
auto& io = ImGui::GetIO();
blueprintNodeEditor.OnFrame(io.DeltaTime); // Update the view each frame
if (showStyleEditor) {
blueprintNodeEditor.ShowStyleEditor(&showStyleEditor);
ImGui::SetCursorPos({ 5, 75 });
// blueprintNodeEditor.ShowLeftPane(350); // this crashes with this basic example due to icon issue (tries to set zero size)
// If you switch the invisible button to a normal one it won't crash
//if (ImGui::InvisibleButton("save", ImVec2((float)saveIconWidth, (float)saveIconHeight)))
// to this
//if (ImGui::Button("save"))
}
if (showFlow) {
// placeholder. Flow should trigger when pressing z-key, although this is only active if leftPane is running (and it crashes for me), so something else is not working when that's fixed this placeholder can be revisited
// for (auto& link : m_Links)
// ed::Flow(link.ID);
}
return;
}
Enabling the Left Pane and fixing Save/Restore
Using my current code the left pane will crash (because there are no icons loaded)
Changing to simple buttons fixes this with no loss of function.
NB:
The editor state (ie zoom and scroll) is saved between sessions.
However blueprint hardcodes the node positions and these are not saved
Also NB the buttons are saving/restoring a temporary state - not saving to a file
To allow the leftpane to show you will need to alter the save code (approx line 800)
to remove the dependence on icons and return to plain buttons.
you may also have to add an adjustment to position it correctly (for me the buttons were drawn off the pane)
The code automatically saves very basic information about nodes and state to a json file in the working directory called "Blueprint.json". However I've no idea how to trigger this manually nor how to add other details (eg user edits of contents of nodes) to this file.
commenting out the hardcoded positioning (approx line 530) does mean the hardcoded nodes are restored to their previous locations, but nodes previously added by the user are lost.
This is thus another vote for implementing examples of the state and node/link save/load functions into the side panel.
(or at an absolute minimum documenting what the code is doing - admittedly this is my biggest frustration throughout this entire library not just about save/load).
I spent ages digging around the backend code trying to figure this out. But it definitely doesn't seem to be easy to figure out and having traced my way around what I think it does it seems to be neither intuitive nor comprehensive.
Perhaps blueprint2 could also be merged with main as the following posts suggests this has a better strategy?
This was the most useful post I've found on the topic (but 3 years old there appears to have been no progress since then) #58
Incidentally this is a very basic initial load routine for importing a mermaid flow chart
bool LoadMermaidChart(const std::string& filepath, nodePlot& nP) {
std::cout << "Loading: " << filepath << std::endl;
std::ifstream iFile(filepath);
if (!iFile.is_open()) {
return false;
}
std::string line;
int nodeId = 0, linkId = 0;
std::map<std::string, int> nodeMap; // to map node name to its ID
// Default color
ImColor defaultColor(255, 255, 255);
while (std::getline(iFile, line)) {
std::cout << line << std::endl;
if (line.find("style") == 0) {
// Parsing the style for nodes
std::string nodeName = line.substr(6, line.find(' ') - 6); // getting the node name
std::string colorHex = line.substr(line.find('#') + 1);
int r = std::stoi(colorHex.substr(0, 2), nullptr, 16);
int g = std::stoi(colorHex.substr(2, 2), nullptr, 16);
int b = std::stoi(colorHex.substr(4, 2), nullptr, 16);
ImColor nodeColor(r, g, b);
// Assuming the node may not exist yet, so update or create node
if (!nodeMap.contains(nodeName)) {
nodeMap[nodeName] = nodeId++;
nP.m_Nodes.emplace_back(nodeMap[nodeName], nodeName.c_str(), nodeColor);
}
else {
for (auto& node : nP.m_Nodes) {
if (node.ID == (ed::NodeId)nodeMap[nodeName]) {
node.Color = nodeColor;
break;
}
}
}
}
else if (line.find("-->") != std::string::npos) {
// It's a link
size_t startBracketPos = line.find('[');
size_t endBracketPos = line.find(']');
std::string startNodeId = line.substr(0, startBracketPos);
trim(startNodeId);
std::string startNodeLabel = line.substr(startBracketPos + 1, endBracketPos - startBracketPos - 1);
size_t arrowPos = line.find("-->");
std::string arrow = line.substr(arrowPos, 3);
int arrowPlus3 = arrowPos + 3;
size_t startBracketPos2 = line.find('[', arrowPlus3);
size_t endBracketPos2 = line.find(']', arrowPlus3);
std::string endNodeId = line.substr(arrowPlus3, startBracketPos2 - arrowPlus3);
trim(endNodeId);
std::string endNodeLabel = line.substr(startBracketPos2 + 1, endBracketPos2 - startBracketPos2 - 1);
// Generate unique identifiers based on the labels
int startNodeNum = nodeId++;
int endNodeNum = nodeId++;
if (!nodeMap.contains(startNodeId)) {
nodeMap[startNodeId] = startNodeNum;
nP.m_Nodes.emplace_back(startNodeNum, startNodeLabel.c_str(), defaultColor);
nP.m_Nodes.back().Type = NodeType::mermaid;
}
else {
startNodeNum = nodeMap[startNodeLabel]; // Use existing ID
}
if (!nodeMap.contains(endNodeId)) {
nodeMap[endNodeId] = endNodeNum;
nP.m_Nodes.emplace_back(endNodeNum, endNodeLabel.c_str(), defaultColor);
nP.m_Nodes.back().Type = NodeType::mermaid;
}
else {
endNodeNum = nodeMap[endNodeLabel]; // Use existing ID
}
// Create the link
nP.m_Links.emplace_back(linkId++, startNodeNum, endNodeNum);
}
}
return true;
}
The text was updated successfully, but these errors were encountered:
This library provides you a canvas to draw ImGui nodes, it doesn't teach you how to serialize/deserialize data. You should implement that on your own, because everyone's node/graph structure is different and thus impossible to come up with a generic solution.
If you're making examples then showing how the example can be integrated into a pre-existing imgui app would be good - turns out to be only a handful of lines of code but it took me hours to figure out what they were.
The following uses the blueprint example and layouts (which seems to be a drop-in replacement for ImGui
My existing app was built on the imgui docking branch so although there appears to be absolutely no explanation of what each of the branches are for I picked this one (because it mentioned docking...)
https://github.com/thedmd/imgui/tree/feature/docking-layout-external
Adding to an existing Imgui app
This should replace the main() function in the blueprint example
(admittedly flow isn't yet working but I think that is a bigger issue as it doesn't trigger with the z key either)
Enabling the Left Pane and fixing Save/Restore
Using my current code the left pane will crash (because there are no icons loaded)
Changing to simple buttons fixes this with no loss of function.
NB:
The editor state (ie zoom and scroll) is saved between sessions.
However blueprint hardcodes the node positions and these are not saved
Also NB the buttons are saving/restoring a temporary state - not saving to a file
To allow the leftpane to show you will need to alter the save code (approx line 800)
to remove the dependence on icons and return to plain buttons.
you may also have to add an adjustment to position it correctly (for me the buttons were drawn off the pane)
Saving / Loading to/from file
The code automatically saves very basic information about nodes and state to a json file in the working directory called "Blueprint.json". However I've no idea how to trigger this manually nor how to add other details (eg user edits of contents of nodes) to this file.
commenting out the hardcoded positioning (approx line 530) does mean the hardcoded nodes are restored to their previous locations, but nodes previously added by the user are lost.
This is thus another vote for implementing examples of the state and node/link save/load functions into the side panel.
(or at an absolute minimum documenting what the code is doing - admittedly this is my biggest frustration throughout this entire library not just about save/load).
I spent ages digging around the backend code trying to figure this out. But it definitely doesn't seem to be easy to figure out and having traced my way around what I think it does it seems to be neither intuitive nor comprehensive.
Perhaps blueprint2 could also be merged with main as the following posts suggests this has a better strategy?
This was the most useful post I've found on the topic (but 3 years old there appears to have been no progress since then)
#58
Incidentally this is a very basic initial load routine for importing a mermaid flow chart
The text was updated successfully, but these errors were encountered: