PDA

View Full Version : Toggle dialog visibility on application switch



gvanvoor
18th June 2012, 00:53
Hi,

I am working on an application containing several tool dialogs and that can have several document windows open simultaneously.
In order for the tool dialogs to be accessible at all times, I've set the AlwaysOnTop flag.
However, I don't want my tool dialogs to stay on top of dialogs of other applications when the user switches to another application (basically I would want to be able to reproduce the behavior of e.g. the palettes in Photoshop).
Does anyone know how to achieve this?
Thanks in advance.

mentalmushroom
18th June 2012, 08:51
try something like this:



// main.cpp
MyApplication a(argc, argv);
MainWindow w;
QObject::connect(&a, SIGNAL(activated()), w.getDialog(), SLOT(show()));
QObject::connect(&a, SIGNAL(deactivated()), w.getDialog(), SLOT(hide()));
w.show();


// application class header
class MyApplication : public QApplication
{
Q_OBJECT

public:
MyApplication(int argc, char **argv);
~MyApplication();

signals:
void activated();
void deactivated();

private:
bool eventFilter(QObject *obj, QEvent *event);
};

// application class implementation
MyApplication::MyApplication(int argc, char **argv): QApplication(argc, argv)
{
installEventFilter(this);
}

bool MyApplication::eventFilter(QObject *obj, QEvent *event)
{
if (event->type() == QEvent::ApplicationActivate)
emit activated();
else if (event->type() == QEvent::ApplicationDeactivate)
emit deactivated();

return false;
}

amleto
18th June 2012, 09:24
isn't this exactly what Qt:Tool window flag is for? :)


By default, tool windows will disappear when the application is inactive.

gvanvoor
18th June 2012, 17:55
try something like this:



// main.cpp
MyApplication a(argc, argv);
MainWindow w;
QObject::connect(&a, SIGNAL(activated()), w.getDialog(), SLOT(show()));
QObject::connect(&a, SIGNAL(deactivated()), w.getDialog(), SLOT(hide()));
w.show();


// application class header
class MyApplication : public QApplication
{
Q_OBJECT

public:
MyApplication(int argc, char **argv);
~MyApplication();

signals:
void activated();
void deactivated();

private:
bool eventFilter(QObject *obj, QEvent *event);
};

// application class implementation
MyApplication::MyApplication(int argc, char **argv): QApplication(argc, argv)
{
installEventFilter(this);
}

bool MyApplication::eventFilter(QObject *obj, QEvent *event)
{
if (event->type() == QEvent::ApplicationActivate)
emit activated();
else if (event->type() == QEvent::ApplicationDeactivate)
emit deactivated();

return false;
}


I've tried that, but unfortunately the ApplicationDeactivate is sent when closing a window while remaining in the same application.

Added after 4 minutes:


isn't this exactly what Qt:Tool window flag is for? :)

It probably is, but doesn't work that way on Windows: when I specify the Qt::Tool flag without the Qt::AlwaysOnTop flag my tool palettes don't stay on top of my document windows.

mentalmushroom
18th June 2012, 19:10
the ApplicationDeactivate is sent when closing a window while remaining in the same application
I've tried it with a one modal dialog and I had no such problem. Maybe you can try to set some flag when a window is closed, so you can distinguish this kind of event then (but don't forget to reset it).

wysota
18th June 2012, 19:21
Qt::Tool should work just fine on Windows.

gvanvoor
19th June 2012, 12:02
Qt::Tool should work just fine on Windows.

It doesn't in my particular case :-(
My document windows are QMainWindows with the default flags, my tools palette have Qt::Tool | Qt::WindowTitleHint | Qt::CustomizeWindowHint | Qt::WindowStaysOnTopHint | Qt::WindowCloseButtonHint flags (the WindowStaysOnTopHint is only there to prevent the tools windows to hide under the document windows, but given the unwanted side effects I'ld like ot get rid of it).
I'm using Qt 4.8 on Windows 7.

wysota
19th June 2012, 12:20
It doesn't in my particular case :-(
Maybe you are using it wrong. Try the window flags example (or demo) that comes with Qt and see if that works.

gvanvoor
19th June 2012, 21:54
Maybe you are using it wrong. Try the window flags example (or demo) that comes with Qt and see if that works.

I might be using it wrongly, but in that case someone will undoubtedly find what's wrong in this minimal code sample that reproduces the problem:


int main(int argc, char *argv[])
{
QApplication a(argc, argv);

QMainWindow * theDocumentWindow = new QMainWindow();
theDocumentWindow->setWindowTitle( "Document Window" );
theDocumentWindow->setCentralWidget( new QLabel( "Document" ) );
theDocumentWindow->show();

QWidget * theToolsPalette = new QWidget( NULL, Qt::Tool | Qt::WindowTitleHint | Qt::CustomizeWindowHint | Qt::WindowCloseButtonHint );
theToolsPalette->setWindowTitle( "Tools Palette" );
QHBoxLayout * thePaletteLayout = new QHBoxLayout( theToolsPalette );
thePaletteLayout->addWidget( new QLabel( "Tools" ) );
theToolsPalette->show();

return a.exec();
}


In the real program window creation is done in the application of course.

wysota
19th June 2012, 22:14
Why don't you just try the example I pointed you to?

gvanvoor
20th June 2012, 07:20
Why don't you just try the example I pointed you to?

I did, but couldn't find a combination of flags that resulted in the desired behavior. Am I doing something wrong or just expecting too much? The only solution I see at this point is to write a class that raises the tool palettes every time a (document) window has been activated.

wysota
20th June 2012, 10:43
So this doesn't work?


cat main.cpp
#include <QtGui>

int main(int argc, char **argv) {
QApplication app(argc, argv);
QWidget w;
QWidget d(&w);
d.setWindowFlags(Qt::Tool);
w.show();
d.show();
return app.exec();
}

gvanvoor
20th June 2012, 12:11
So this doesn't work?


cat main.cpp
#include <QtGui>

int main(int argc, char **argv) {
QApplication app(argc, argv);
QWidget w;
QWidget d(&w);
d.setWindowFlags(Qt::Tool);
w.show();
d.show();
return app.exec();
}

This probably works, but as I have more than one Document Window and the tools need to stay on top of all of them I can't use that :-(