jvcleave / ofxImGui

Use ImGui in openFrameworks
299 stars 123 forks source link

GUI disappears when second-to-last openframeworks window is closed #81

Closed s-ol closed 5 years ago

s-ol commented 6 years ago

This is a weird one, I first thought it was an issue in openframeworks but it seems it's not.

openframeworks/openFrameworks#6134

basically when I create extra windows in openframeworks (after initializing an ofxImGui::Gui instance) and then close them (without using ofxImGui in them at all) then the Gui instance in the main window stops working and begin(), end() and draw() just don't do anything at all anymore.

Here you can find a minimal example project to reproduce the issue: repro.zip

with one window:

with two or more windows:

s-ol commented 6 years ago

Oh, and the whole thing happens on Linux but doesn't on OS X...

jvcleave commented 6 years ago

can you see if you have values here?

https://github.com/jvcleave/ofxImGui/blob/master/src/EngineGLFW.cpp#L160

s-ol commented 6 years ago

@jvcleave Just checked, fb_width and fb_height look okay - match window size on start, change on resize and stay stable when new windows are added or removed. They also keep tracking window size after the bug is triggered.

Btw I forgot to mention: I also logged Gui#exit and EngineGLFW#exit but they didn't get called until the whole program exited properly.

s-ol commented 6 years ago

logging the draw lists, they also seem normal. In the demo I attached I get one list (draw_data->CmdListsCount == 1) with two entries (cmd_list->CmdBuffer.Size == 2) and this also persists after the bug is triggered.

The issue is present also both with and without GL context sharing.

s-ol commented 6 years ago

Texture ID, tri counts and scissoring areas from https://github.com/jvcleave/ofxImGui/blob/master/src/EngineGLFW.cpp#L230-232 are also stable. Does this mean it's an upstream bug?

If so, the question remains: how is the bug triggered in ImGui? We must be somehow poking it through the ImGui IO object, GL state or something similar, and there could still be a bug in openframeworks-side code there.

jvcleave commented 6 years ago

the fact that it doesn't happen on OSX is pretty weird. Have you tried destroying the ofxImGui instance and recreating it to see if it shows back up?

s-ol commented 6 years ago

Aha! This is some progress :) After the bug is triggered, a single gui.setup() is enough to bring it back. That's good to know - but even more interesting is that an extra gui.setup() before the bug is triggered prevents it from happening!

This is still the same codebase I attached above - gui.setup() is called already in ofApp::setup but it seems this is somehow too early and it breaks something. I found two ways to fix it at the moment:

s-ol commented 6 years ago

argh, this fixes it in my reproduction case but not my actual application :/

EDIT: nevermind, I must've been doing something wrong - it works the same there.

s-ol commented 6 years ago

The problem with this (dirty) fix is that calling setup twice causes all keystrokes to be doubled; but if I remove the first setup in ofApp::setup the issue is triggered again.

EDIT: The doube-input happens because of a memory leak in Gui::setup that doesn't destruct the old Engine object, which in turn doesn't remove the Event Listeners. Fix is in #82.

s-ol commented 6 years ago

just confirmed that the issue happens on Windows as well - zip from OP works the same there.

jvcleave commented 5 years ago

closed with #82 - thanks!

s-ol commented 5 years ago

Hey @jvcleave - #82 actually only fixes the side effects of my workaround. Starting with a single Gui::setup() still shows the problems described here.

thorikawa commented 5 years ago

I have the same issue and the workarounds suggested by @s-ol did not work for me. @s-ol could you share how you actually solved the problem? I applied two ways you suggested above to the repro.zip project, but neither of them worked.

My environment:

s-ol commented 5 years ago

@thorikawa can you try this branch? I don't remember anymore all the details that I have done, but for me it works with this branch https://github.com/s-ol/ofxImGui/tree/docking

and the following in my ofApp setup / update:

void ofApp::setup() {
  gui.setup(nullptr, false);
}

void ofApp::update() {
  if (!isSetup) {
    gui.setup(nullptr, false);
    isSetup = true;
  }
}
thorikawa commented 5 years ago

@s-ol Thank you very much! After several trials, I finally got it to work. I need to call gui.setup after the second window closes, so modify your example a little bit.

Working code:

void ofApp::setup() {
  gui.setup(nullptr, false);
  isSetup = true;
}

void ofApp::update() {
    // isSetup guard still causes the issue
    //if (isSetup) {
        gui.setup(nullptr, false);
        isSetup = false;
    //}
}

void ofApp::draw() {
  ofClear(100, 0, 0, 255);
  ofDrawBitmapString("main, space to create previews", 100, 100);

  gui.begin();
  if (ImGui::Begin("Test Window"))
    ImGui::Text("This is just a test, press space to create previews");
  ImGui::End();
  gui.end();

  gui.draw();
}

I am not sure about the side effect of calling gui.setup multiple times... but it is working anyway. I will investigate more later.

thorikawa commented 5 years ago

For the record, the working example I pasted above works only with @s-ol 's docking branch. It does not work with the current master.