March 12, 2011

khalidmushtaq65 khalidmushta..
Lab Rat
40 posts

Minimizing Application to Tray

Page  
1

Hi,

I have got a problem. I want my application to minimize to tray when I click on minimize button or close button.

I have got success with close button but when I click on minimize button, all the content on the window i.e. buttons, images, text etc disappears but a white window remains on screen with no content at all and when I click on tray and click show all the content becomes visible again.

I am using following code to minimize application to tray.

  1. void MainWindow::changeEvent(QEvent *event)
  2. {
  3.     if(event->type() == QEvent::WindowStateChange) {
  4.         if(isMinimized()) {
  5.             this->hide();
  6.             event->ignore();
  7.         }
  8.     }
  9. }

Thanks for any kind of help..

24 replies

March 12, 2011

Alicemirror Alicemirror
Lab Rat
825 posts

Hi, happy to find this post, I’m trying to solve the same problem too :)

What I think at the actual state of my tests (not got solution yet) is that the event should be managed with some other things. It seems a problem of repaint without the window in place of the white rectangle.

If I find more I update immediately!

 Signature 

Enrico Miglino (aka Alicemirror)
Tech Consulting
Islas Baleares, Ibiza (Spain)
http://www.contesti.eu

March 12, 2011

Volker Volker
Robot Herder
5428 posts

You should at least call the base class’ implementation of changeEvent() for the cases where you do not handle it yourself.

So add at the end of you method (supposing you have a QMainWindow based UI):

  1. QMainWindow::changeEvent(event);

(a guideline that holds for almost every virtual method that you re-implement)

March 12, 2011

khalidmushtaq65 khalidmushta..
Lab Rat
40 posts

Volker I have tried this too but can’t get through.

Will you please explain about QMainWindow based UI?

March 13, 2011

Volker Volker
Robot Herder
5428 posts

Your class MainWindow inherits from some base class. I suppose this is QMainWindow (others could be QDialog or QWidget for example).

And for the code. Did you try already:

  1. void MainWindow::changeEvent(QEvent *event)
  2. {
  3.     QMainWindow::changeEvent(event);
  4.     if(event->type() == QEvent::WindowStateChange)
  5.         if(isMinimized())
  6.             this->hide();
  7. }

This let’s Qt do the regular work and after the window is minimized you hide it.

March 13, 2011

khalidmushtaq65 khalidmushta..
Lab Rat
40 posts

I tried this but the same result again..
Just getting the blank screen while minimizing the application..
I can’t understand what’s the problem..

March 13, 2011

Gerolf Gerolf
Area 51 Engineer
3210 posts

Hi Khalidmushta,

what exactly do you want to achieve?

Minimize to system try, so to have a tray icon? Are you using QSystemTryIcon [doc.qt.nokia.com] ?
Can you show a bit more of your code which results in the problem? The best would be a very simple, small example showing the problem.

 Signature 

Nokia Certified Qt Specialist.
Programming Is Like Sex: One mistake and you have to support it for the rest of your life. (Michael Sinz)

March 13, 2011

khalidmushtaq65 khalidmushta..
Lab Rat
40 posts

I want to minimize my application to tray when I click on Minimize button and same for the close button..

I am using QSystemTryIcon, works fine with close button, but not working with minimize button.
When I click on minimize button all the contents get hide and a screen with white background continues to show..

This is for the minimize button that shows white background of screen but hides the content..

  1. void MainWindow::changeEvent(QEvent *event)
  2. {
  3.     if(event->type() == QEvent::WindowStateChange) {
  4.         if(isMinimized())
  5.             this->hide();
  6.             event->ignore();
  7.     }
  8. }

This is for the close button that works fine.

  1. void MainWindow::closeEvent(QCloseEvent *event)
  2. {
  3.     if (trayIcon->isVisible()) {
  4.         this->hide();
  5.         event->ignore();
  6.     }
  7. }

March 13, 2011

Andre Andre
Area 51 Engineer
6031 posts

khalidmushtaq65 wrote:

This is for the minimize button that shows white background of screen but hides the content..

  1. void MainWindow::changeEvent(QEvent *event)
  2. {
  3.     if(event->type() == QEvent::WindowStateChange) {
  4.         if(isMinimized())
  5.             this->hide();
  6.             event->ignore();
  7.     }
  8. }

Not sure if this is the problem, but shouldn’t that be:

  1. void MainWindow::changeEvent(QEvent *event)
  2. {
  3.     if(event->type() == QEvent::WindowStateChange) {
  4.         if(isMinimized()) {
  5.             this->hide();
  6.             event->ignore();
  7.         }
  8.     }
  9.     QMainWindow::changeEvent(event);
  10. }

 Signature 

Looking for Qt developers to join our team @ i-Optics: https://qt-project.org/forums/viewthread/25393/

March 13, 2011

khalidmushtaq65 khalidmushta..
Lab Rat
40 posts

I have tried that too but the problem still exists..

March 13, 2011

kkrzewniak kkrzewniak
Lab Rat
218 posts

  1. MainWindow::MainWindow(QWidget *parent) :
  2.     QMainWindow(parent)
  3. {
  4.     ui.setupUi(this);
  5.  
  6.     icon = new QSystemTrayIcon(this);
  7.     icon->show();
  8.  
  9.     menu = new QMenu(this);
  10.  
  11.     quitAction = new QAction("Quit",this);
  12.     connect(quitAction,SIGNAL(triggered()),this,SLOT(close()));
  13.     menu->addAction(quitAction);
  14.     icon->setContextMenu(menu);
  15.  
  16.     restore = new QAction("Restore",this);
  17.     restore->setEnabled(false);
  18.     connect(restore,SIGNAL(triggered()),this,SLOT(showNormal()));
  19.     menu->addAction(restore);
  20. }
  21.  
  22. void MainWindow::changeEvent(QEvent *e)
  23. {
  24.     QMainWindow::changeEvent(e);
  25.     switch (e->type()) {
  26.     case QEvent::LanguageChange:
  27.         ui.retranslateUi(this);
  28.         break;
  29.     case QEvent::WindowStateChange:
  30.     {
  31.         if(isMinimized())
  32.         {
  33.             hide();
  34.             restore->setEnabled(true);
  35.         }
  36.         else
  37.         {
  38.             restore->setEnabled(false);
  39.         }
  40.     }
  41.         break;
  42.     default:
  43.         break;
  44.     }
  45. }

Just put this code together to test Your issue it works ass expected on my Linux box. Why are You ignoring the change event? It’s not like the close event witch You need to ignore to prevent your window from actually closing.

 Signature 

Me, Grimlock, not “nice dino”. ME BASH BRAINS!

March 13, 2011

khalidmushtaq65 khalidmushta..
Lab Rat
40 posts

I am sorry to say that it’s not working too. Same problem exists..

March 13, 2011

Andre Andre
Area 51 Engineer
6031 posts

Well, if kkrzewniak tested the code he posted, and you just claim “it doesn’t work”, perhaps you should start by giving more information. For starters: what platform are we talking about anyway? Can you post a minimal, yet complete, complileable example that shows the problem?

 Signature 

Looking for Qt developers to join our team @ i-Optics: https://qt-project.org/forums/viewthread/25393/

March 13, 2011

khalidmushtaq65 khalidmushta..
Lab Rat
40 posts

I am using Microsoft Windows 7 Ultimate.

This is mainwindow.h

  1. #ifndef MAINWINDOW_H
  2. #define MAINWINDOW_H
  3.  
  4. #include <QWidget>
  5. #include <QSystemTrayIcon>
  6.  
  7. #include <QMainWindow>
  8.  
  9. class QMenu;
  10.  
  11. namespace Ui {
  12.     class MainWindow;
  13. }
  14.  
  15. class MainWindow : public QMainWindow
  16. {
  17.     Q_OBJECT
  18.  
  19. public:
  20.     explicit MainWindow(QWidget *parent = 0);
  21.     ~MainWindow();
  22.     bool createConnection();
  23.  
  24. private:
  25.     Ui::MainWindow *ui;
  26.  
  27.     // Tray Icon Functions
  28.     void createTrayActions();
  29.     void createTrayIcon();
  30.     void setTrayIcon();
  31.  
  32.     void closeEvent(QCloseEvent *);
  33.     void changeEvent(QEvent *);
  34.  
  35.     QSystemTrayIcon *trayIcon;
  36.     QMenu *trayIconMenu;
  37.     QAction *showHideTray;
  38.     QAction *closeTray;
  39.  
  40. private slots:
  41.     void trayIconClicked(QSystemTrayIcon::ActivationReason);
  42.     void showHideWindow();
  43.  
  44. };
  45.  
  46. #endif // MAINWINDOW_H

This is mainwindow.cpp

  1. #include "mainwindow.h"
  2. #include "ui_mainwindow.h"
  3. #include <QMessageBox>
  4. #include <QtSql/QSqlError>
  5. #include <QMenu>
  6. #include <QCloseEvent>
  7. #include <QDir>
  8.  
  9. MainWindow::MainWindow(QWidget *parent) :
  10.     QMainWindow(parent),
  11.     ui(new Ui::MainWindow)
  12. {
  13.     ui->setupUi(this);
  14.  
  15.     createTrayActions();
  16.     createTrayIcon();
  17.     setTrayIcon();
  18.     trayIcon->show();
  19. }
  20. void MainWindow::changeEvent(QEvent *event)
  21. {
  22.     QMainWindow::changeEvent(event);
  23.     if(event->type() == QEvent::WindowStateChange) {
  24.         if(isMinimized())
  25.             this->hide();
  26.     }
  27. }
  28.  
  29. void MainWindow::closeEvent(QCloseEvent *event)
  30. {
  31.     if (trayIcon->isVisible()) {
  32.         showHideWindow();
  33.         event->ignore();
  34.     }
  35. }
  36.  
  37. void MainWindow::showHideWindow()
  38. {
  39.     if(this->isVisible())
  40.     {
  41.         this->hide();
  42.         showHideTray->setIcon(QIcon(":/images/arrow_up.ico"));
  43.         showHideTray->setText("Show Main Window");
  44.     }
  45.     else
  46.     {
  47.         this->show();
  48.         showHideTray->setIcon(QIcon(":/images/arrow_down.ico"));
  49.         showHideTray->setText("Hide Main Window");
  50.     }
  51. }
  52.  
  53. void MainWindow::trayIconClicked(QSystemTrayIcon::ActivationReason reason)
  54. {
  55.     if(reason == QSystemTrayIcon::DoubleClick)
  56.         showHideWindow();
  57. }
  58.  
  59. void MainWindow::setTrayIcon()
  60. {
  61.     trayIcon->setIcon(QIcon(":/images/Download.ico"));
  62. }
  63. void MainWindow::createTrayIcon()
  64. {
  65.     trayIconMenu = new QMenu(this);
  66.     trayIconMenu->addAction(showHideTray);
  67.     trayIconMenu->addSeparator();
  68.     trayIconMenu->addAction(closeTray);
  69.  
  70.     trayIcon = new QSystemTrayIcon(this);
  71.     trayIcon->setContextMenu(trayIconMenu);
  72.  
  73.     connect(
  74.             trayIcon,
  75.           SIGNAL(activated(QSystemTrayIcon::ActivationReason)),
  76.             this,
  77.             SLOT(trayIconClicked(QSystemTrayIcon::ActivationReason))
  78.            );
  79. }
  80. void MainWindow::createTrayActions()
  81. {
  82.     showHideTray = new QAction(tr("&Hide Main Window"), this);
  83.     connect(showHideTray, SIGNAL(triggered()), this, SLOT(showHideWindow()));
  84.     showHideTray->setIcon(QIcon(":/images/arrow_down.ico"));
  85.     closeTray = new QAction(tr("&Exit"), this);
  86.     connect(closeTray, SIGNAL(triggered()), qApp, SLOT(quit()));
  87.     closeTray->setIcon(QIcon(":/images/Delete.png"));
  88. }
  89. MainWindow::~MainWindow()
  90. {
  91.     delete ui;
  92.     delete trayIcon;
  93.     delete trayIconMenu;
  94.     delete showHideTray;
  95.     delete closeTray;
  96. }

March 13, 2011

Alicemirror Alicemirror
Lab Rat
825 posts

If it can be useful for those is trying to solve this problem:

Actually I develop under linux ubuntu then rebuild under windows 7 ultimate and under xp. I use virtual machines but it doesn’t matter, the machine is as a real computer (little slow).

Using the beta Qt-Quick and Qt-Creator + Qt-sdk (all Qt wrote correct, eh Andre ? :) :) ) I experience problems under Windows 7. Strange problems that probably are not so depending from the application itself.

 Signature 

Enrico Miglino (aka Alicemirror)
Tech Consulting
Islas Baleares, Ibiza (Spain)
http://www.contesti.eu

March 13, 2011

Gerolf Gerolf
Area 51 Engineer
3210 posts

Hi khalidmushta..,

I created an app using sys tray icon which works on windows 7.
You can find the sources on gitorious [gitorious.org]

The code, where I minimize / restore to / from system tray looks like this:

  1. void GiWorldClock::hideEvent(QHideEvent* pEvent)
  2. {
  3.     if(isMinimized())
  4.     {
  5.         ::ShowWindow(this->winId(), SW_HIDE);
  6.         m_pRestoreAction->setEnabled(true);
  7.         m_pMinAction->setDisabled(true);
  8.     }
  9.     QWidget::hideEvent(pEvent);
  10. }
  11.  
  12. void GiWorldClock::showEvent(QShowEvent* pEvent)
  13. {
  14.     QWidget::showEvent(pEvent);
  15.     ::ShowWindow(this->winId(), SW_SHOW);
  16.     m_pRestoreAction->setDisabled(true);
  17.     m_pMinAction->setEnabled(true);
  18. }

 Signature 

Nokia Certified Qt Specialist.
Programming Is Like Sex: One mistake and you have to support it for the rest of your life. (Michael Sinz)

Page  
1

  ‹‹ "_Z9qBadAllocv could not be located in the dynamic link library QtCore4.dll"      Resize a dialog box ››

You must log in to post a reply. Not a member yet? Register here!