]> git.sur5r.net Git - bacula/bacula/blobdiff - bacula/src/qt-console/mainwin.cpp
Make undocking work
[bacula/bacula] / bacula / src / qt-console / mainwin.cpp
index be3fbce36fee2ae2637d9a8a550a5dd12c047c45..ff92afaf26c98a01a21705e24a0574738ccddea0 100644 (file)
@@ -1,7 +1,7 @@
 /*
    Bacula® - The Network Backup Solution
 
-   Copyright (C) 2007-2009 Free Software Foundation Europe e.V.
+   Copyright (C) 2007-2010 Free Software Foundation Europe e.V.
 
    The main author of Bacula is Kern Sibbald, with contributions from
    many others, a complete list can be found in the file AUTHORS.
@@ -27,7 +27,6 @@
 */
 
 /*
- *   Version $Id$
  *
  *  Main Window control for bat (qt-console)
  *
@@ -50,6 +49,7 @@
 #include "restore/restoretree.h"
 #include "help/help.h"
 #include "jobs/jobs.h"
+#include "medialist/mediaview.h"
 #ifdef HAVE_QWT
 #include "jobgraphs/jobplot.h"
 #endif
@@ -66,7 +66,11 @@ void message_callback(int /* type */, char *msg)
 
 MainWin::MainWin(QWidget *parent) : QMainWindow(parent)
 {
+   app->setOverrideCursor(QCursor(Qt::WaitCursor));
    m_isClosing = false;
+   m_waitState = false;
+   m_doConnect = false;
+   m_treeStackTrap = false;
    m_dtformat = "yyyy-MM-dd HH:mm:ss";
    mainWin = this;
    setupUi(this);                     /* Setup UI defined by main.ui (designer) */
@@ -76,12 +80,10 @@ MainWin::MainWin(QWidget *parent) : QMainWindow(parent)
    treeWidget->setColumnCount(1);
    treeWidget->setHeaderLabel( tr("Select Page") );
    treeWidget->setContextMenuPolicy(Qt::ActionsContextMenu);
-
+   // tabWidget->setTabsClosable(true);  /* wait for QT 4.5 */
    createPages();
 
-   resetFocus();
-
-   connectSignals();
+   resetFocus(); /* lineEdit->setFocus() */
 
 #ifndef HAVE_QWT
    actionJobPlot->setEnabled(false);
@@ -96,13 +98,25 @@ MainWin::MainWin(QWidget *parent) : QMainWindow(parent)
       console->connect_dir();
    }
    m_currentConsole = (Console*)getFromHash(m_firstItem);
-   m_currentConsole->setCurrent();
-   connectConsoleSignals();
+   QTimer::singleShot(5000, this, SLOT(popLists()));
    if (m_miscDebug) {
       QString directoryResourceName;
       m_currentConsole->getDirResName(directoryResourceName);
       Pmsg1(100, "Setting initial window to %s\n", directoryResourceName.toUtf8().data());
    }
+   app->restoreOverrideCursor();
+}
+
+void MainWin::popLists()
+{
+   foreach(Console *console, m_consoleHash) {
+      console->populateLists(true);
+   }
+   m_doConnect = true;
+   connectConsoleSignals();
+   connectSignals();
+   app->restoreOverrideCursor();
+   m_currentConsole->setCurrent();
 }
 
 void MainWin::createPages()
@@ -115,7 +129,7 @@ void MainWin::createPages()
    foreach_res(dir, R_DIRECTOR) {
 
       /* Create console tree stacked widget item */
-      m_currentConsole = new Console(stackedWidget);
+      m_currentConsole = new Console(tabWidget);
       m_currentConsole->setDirRes(dir);
       m_currentConsole->readSettings();
 
@@ -143,7 +157,6 @@ void MainWin::createPages()
       */
       QBrush redBrush(Qt::red);
       item->setForeground(0, redBrush);
-      m_currentConsole->dockPage();
 
       /*
        * Create instances in alphabetic order of the rest 
@@ -161,6 +174,7 @@ void MainWin::createPages()
          new JobPlot(NULL, pass);
 #endif
       new MediaList();
+      new MediaView();
       new Storage();
       if (m_openBrowser)
          new restoreTree();
@@ -168,7 +182,9 @@ void MainWin::createPages()
          new DirStat();
 
       treeWidget->expandItem(topItem);
-      stackedWidget->setCurrentWidget(m_currentConsole);
+      tabWidget->setCurrentWidget(m_currentConsole);
+      m_currentConsole->undockPage();
+      m_currentConsole->dockPage();
    }
    UnlockRes();
 }
@@ -238,8 +254,8 @@ void MainWin::connectSignals()
    connect(actionAbout_bat, SIGNAL(triggered()), this, SLOT(about()));
    connect(actionBat_Help, SIGNAL(triggered()), this, SLOT(help()));
    connect(treeWidget, SIGNAL(itemClicked(QTreeWidgetItem *, int)), this, SLOT(treeItemClicked(QTreeWidgetItem *, int)));
-   connect(treeWidget, SIGNAL( currentItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)), this, SLOT(treeItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)));
-   connect(stackedWidget, SIGNAL(currentChanged(int)), this, SLOT(stackItemChanged(int)));
+   connect(treeWidget, SIGNAL(currentItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)), this, SLOT(treeItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)));
+   connect(tabWidget, SIGNAL(currentChanged(int)), this, SLOT(stackItemChanged(int)));
    connect(actionQuit, SIGNAL(triggered()), app, SLOT(closeAllWindows()));
    connect(actionLabel, SIGNAL(triggered()), this,  SLOT(labelButtonClicked()));
    connect(actionRun, SIGNAL(triggered()), this,  SLOT(runButtonClicked()));
@@ -254,6 +270,8 @@ void MainWin::connectSignals()
    connect(actionToggleDock, SIGNAL(triggered()), this,  SLOT(toggleDockContextWindow()));
    connect(actionClosePage, SIGNAL(triggered()), this,  SLOT(closePage()));
    connect(actionPreferences, SIGNAL(triggered()), this,  SLOT(setPreferences()));
+   connect(actionRepopLists, SIGNAL(triggered()), this,  SLOT(repopLists()));
+   connect(actionReloadRepop, SIGNAL(triggered()), this,  SLOT(reloadRepopLists()));
 }
 
 void MainWin::disconnectSignals()
@@ -264,7 +282,7 @@ void MainWin::disconnectSignals()
    disconnect(actionBat_Help, SIGNAL(triggered()), this, SLOT(help()));
    disconnect(treeWidget, SIGNAL(itemClicked(QTreeWidgetItem *, int)), this, SLOT(treeItemClicked(QTreeWidgetItem *, int)));
    disconnect(treeWidget, SIGNAL( currentItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)), this, SLOT(treeItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)));
-   disconnect(stackedWidget, SIGNAL(currentChanged(int)), this, SLOT(stackItemChanged(int)));
+   disconnect(tabWidget, SIGNAL(currentChanged(int)), this, SLOT(stackItemChanged(int)));
    disconnect(actionQuit, SIGNAL(triggered()), app, SLOT(closeAllWindows()));
    disconnect(actionLabel, SIGNAL(triggered()), this,  SLOT(labelButtonClicked()));
    disconnect(actionRun, SIGNAL(triggered()), this,  SLOT(runButtonClicked()));
@@ -279,6 +297,8 @@ void MainWin::disconnectSignals()
    disconnect(actionToggleDock, SIGNAL(triggered()), this,  SLOT(toggleDockContextWindow()));
    disconnect(actionClosePage, SIGNAL(triggered()), this,  SLOT(closePage()));
    disconnect(actionPreferences, SIGNAL(triggered()), this,  SLOT(setPreferences()));
+   disconnect(actionRepopLists, SIGNAL(triggered()), this,  SLOT(repopLists()));
+   disconnect(actionReloadRepop, SIGNAL(triggered()), this,  SLOT(reloadRepopLists()));
 }
 
 /*
@@ -286,8 +306,18 @@ void MainWin::disconnectSignals()
  */
 void MainWin::waitEnter()
 {
+   if (m_waitState){ 
+      if (mainWin->m_connDebug)
+         Pmsg0(000, "Should Never Get Here DANGER DANGER, for now I'll return\n");
+      return;
+   }
+   m_waitState = true;
+   if (mainWin->m_connDebug)
+      Pmsg0(000, "Entering Wait State\n");
    app->setOverrideCursor(QCursor(Qt::WaitCursor));
    disconnectSignals();
+   disconnectConsoleSignals(m_currentConsole);
+   m_waitTreeItem = treeWidget->currentItem();
 }
 
 /*
@@ -295,26 +325,47 @@ void MainWin::waitEnter()
  */
 void MainWin::waitExit()
 {
+   m_waitState = false;
+   if (mainWin->m_connDebug) Pmsg0(000, "Exiting Wait State\n");
+   if (m_waitTreeItem != treeWidget->currentItem())
+      treeWidget->setCurrentItem(m_waitTreeItem);
+   if (m_doConnect) {
+      connectSignals();
+      connectConsoleSignals();
+   }
    app->restoreOverrideCursor();
-   connectSignals();
 }
 
 void MainWin::connectConsoleSignals()
 {
    connect(actionConnect, SIGNAL(triggered()), m_currentConsole, SLOT(connect_dir()));
    connect(actionSelectFont, SIGNAL(triggered()), m_currentConsole, SLOT(set_font()));
-   connect(actionStatusDir, SIGNAL(triggered()), m_currentConsole, SLOT(status_dir()));
    connect(actionMessages, SIGNAL(triggered()), m_currentConsole, SLOT(messages()));
 }
 
 void MainWin::disconnectConsoleSignals(Console *console)
 {
    disconnect(actionConnect, SIGNAL(triggered()), console, SLOT(connect_dir()));
-   disconnect(actionStatusDir, SIGNAL(triggered()), console, SLOT(status_dir()));
    disconnect(actionMessages, SIGNAL(triggered()), console, SLOT(messages()));
    disconnect(actionSelectFont, SIGNAL(triggered()), console, SLOT(set_font()));
 }
 
+
+/* 
+ * Two functions to respond to menu items to repop lists and execute reload and repopulate
+ * the lists for jobs, clients, filesets .. ..
+ */
+void MainWin::repopLists()
+{
+   m_currentConsole->populateLists(false);
+}
+void MainWin::reloadRepopLists()
+{
+   QString cmd = "reload";
+   m_currentConsole->consoleCommand(cmd);
+   m_currentConsole->populateLists(false);
+}
+
 /* 
  * Reimplementation of QWidget closeEvent virtual function   
  */
@@ -322,6 +373,13 @@ void MainWin::closeEvent(QCloseEvent *event)
 {
    m_isClosing = true;
    writeSettings();
+   /* Remove all groups from settings for OpenOnExit so that we can start some of the status windows */
+   foreach(Console *console, m_consoleHash){
+      QSettings settings(console->m_dir->name(), "bat");
+      settings.beginGroup("OpenOnExit");
+      settings.remove("");
+      settings.endGroup();
+   }
    /* close all non console pages, this will call settings in destructors */
    while (m_consoleHash.count() < m_pagehash.count()) {
       foreach(Pages *page, m_pagehash) {
@@ -351,6 +409,7 @@ void MainWin::writeSettings()
    settings.setValue("winPos", pos());
    settings.setValue("state", saveState());
    settings.endGroup();
+
 }
 
 void MainWin::readSettings()
@@ -373,10 +432,10 @@ void MainWin::treeItemClicked(QTreeWidgetItem *item, int /*column*/)
    /* Is this a page that has been inserted into the hash  */
    if (getFromHash(item)) {
       Pages* page = getFromHash(item);
-      int stackindex=stackedWidget->indexOf(page);
+      int stackindex=tabWidget->indexOf(page);
 
       if (stackindex >= 0) {
-         stackedWidget->setCurrentWidget(page);
+         tabWidget->setCurrentWidget(page);
       }
       /* run the virtual function in case this class overrides it */
       page->PgSeltreeWidgetClicked();
@@ -421,6 +480,9 @@ void MainWin::treeItemChanged(QTreeWidgetItem *currentitem, QTreeWidgetItem *pre
 
    /* this condition prevents a segfault.  The first time there is no previousitem*/
    if (previousitem) {
+      if (m_treeStackTrap == false) { /* keep track of previous items for going Back */
+         m_treeWidgetStack.append(previousitem);
+      }
       /* knowing the treeWidgetItem, get the page from the hash */
       previousPage = getFromHash(previousitem);
       previousConsole = m_consoleHash.value(previousitem);
@@ -454,12 +516,15 @@ void MainWin::treeItemChanged(QTreeWidgetItem *currentitem, QTreeWidgetItem *pre
          dirItem->setBackground(0, magentaBrush);
       }
       /* set the value for the currently active console */
-      int stackindex = stackedWidget->indexOf(nextPage);
+      int stackindex = tabWidget->indexOf(nextPage);
+      if (!nextPage->isOnceDocked()) {
+         nextPage->dockPage();
+      }
    
       /* Is this page currently on the stack or is it undocked */
       if (stackindex >= 0) {
          /* put this page on the top of the stack */
-         stackedWidget->setCurrentIndex(stackindex);
+         tabWidget->setCurrentIndex(stackindex);
       } else {
          /* it is undocked, raise it to the front */
          nextPage->raise();
@@ -510,8 +575,9 @@ void MainWin::statusPageButtonClicked()
          }
       }
    }
-   if (!found)
+   if (!found) {
       new DirStat();
+   }
 }
 
 void MainWin::restoreButtonClicked() 
@@ -533,11 +599,16 @@ void MainWin::jobPlotButtonClicked()
  */
 void MainWin::input_line()
 {
+   int conn;
    QString cmdStr = lineEdit->text();    /* Get the text */
    lineEdit->clear();                    /* clear the lineEdit box */
    if (m_currentConsole->is_connected()) {
-      /* Use consoleInput to allow typing anything */
-      m_currentConsole->consoleInput(cmdStr);
+      if (m_currentConsole->findDirComm(conn)) {
+         m_currentConsole->consoleCommand(cmdStr, conn);
+      } else {
+         /* Use consoleCommand to allow typing anything */
+         m_currentConsole->consoleCommand(cmdStr);
+      }
    } else {
       set_status(tr("Director not connected. Click on connect button."));
    }
@@ -593,7 +664,7 @@ void MainWin::set_status(const char *buf)
  */
 void MainWin::undockWindowButton()
 {
-   Pages* page = (Pages*)stackedWidget->currentWidget();
+   Pages* page = (Pages*)tabWidget->currentWidget();
    page->togglePageDocking();
 }
 
@@ -621,9 +692,16 @@ void MainWin::toggleDockContextWindow()
 void MainWin::stackItemChanged(int)
 {
    if (m_isClosing) return; /* if closing the application, do nothing here */
-   Pages* page = (Pages*)stackedWidget->currentWidget();
+   Pages* page = (Pages*)tabWidget->currentWidget();
    /* run the virtual function in case this class overrides it */
    page->currentStackItem();
+   if (!m_waitState) {
+      disconnect(treeWidget, SIGNAL(itemClicked(QTreeWidgetItem *, int)), this, SLOT(treeItemClicked(QTreeWidgetItem *, int)));
+      disconnect(treeWidget, SIGNAL( currentItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)), this, SLOT(treeItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)));
+      treeWidget->setCurrentItem(getFromHash(page));
+      connect(treeWidget, SIGNAL(itemClicked(QTreeWidgetItem *, int)), this, SLOT(treeItemClicked(QTreeWidgetItem *, int)));
+      connect(treeWidget, SIGNAL(currentItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)), this, SLOT(treeItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)));
+   }
 }
 
 /*
@@ -690,6 +768,7 @@ Console *MainWin::currentConsole()
 {
    return m_currentConsole;
 }
+
 /* Quick function to return the tree item for the director */
 QTreeWidgetItem *MainWin::currentTopItem()
 {
@@ -712,8 +791,6 @@ void MainWin::setPreferences()
    prefs.daysSpinBox->setValue(m_daysLimitVal);
    prefs.checkMessages->setCheckState(m_checkMessages ? Qt::Checked : Qt::Unchecked);
    prefs.checkMessagesSpin->setValue(m_checkMessagesInterval);
-   prefs.refreshStatusDir->setCheckState(m_refreshStatusDir ? Qt::Checked : Qt::Unchecked);
-   prefs.refreshStatusDirSpin->setValue(m_refreshStatusDirInterval);
    prefs.executeLongCheckBox->setCheckState(m_longList ? Qt::Checked : Qt::Unchecked);
    prefs.rtPopDirCheckBox->setCheckState(m_rtPopDirDebug ? Qt::Checked : Qt::Unchecked);
    prefs.rtDirCurICCheckBox->setCheckState(m_rtDirCurICDebug ? Qt::Checked : Qt::Unchecked);
@@ -768,8 +845,6 @@ void prefsDialog::accept()
    mainWin->m_daysLimitVal = this->daysSpinBox->value();
    mainWin->m_checkMessages = this->checkMessages->checkState() == Qt::Checked;
    mainWin->m_checkMessagesInterval = this->checkMessagesSpin->value();
-   mainWin->m_refreshStatusDir = this->refreshStatusDir->checkState() == Qt::Checked;
-   mainWin->m_refreshStatusDirInterval = this->refreshStatusDirSpin->value();
    mainWin->m_longList = this->executeLongCheckBox->checkState() == Qt::Checked;
 
    mainWin->m_rtPopDirDebug = this->rtPopDirCheckBox->checkState() == Qt::Checked;
@@ -813,8 +888,6 @@ void prefsDialog::accept()
    settings.beginGroup("Timers");
    settings.setValue("checkMessages", mainWin->m_checkMessages);
    settings.setValue("checkMessagesInterval", mainWin->m_checkMessagesInterval);
-   settings.setValue("refreshStatusDir", mainWin->m_refreshStatusDir);
-   settings.setValue("refreshStatusDirInterval", mainWin->m_refreshStatusDirInterval);
    settings.endGroup();
    settings.beginGroup("Misc");
    settings.setValue("longList", mainWin->m_longList);
@@ -866,8 +939,6 @@ void MainWin::readPreferences()
    settings.beginGroup("Timers");
    m_checkMessages = settings.value("checkMessages", false).toBool();
    m_checkMessagesInterval = settings.value("checkMessagesInterval", 28).toInt();
-   m_refreshStatusDir = settings.value("refreshStatusDir", false).toBool();
-   m_refreshStatusDirInterval = settings.value("refreshStatusDirInterval", 28).toInt();
    settings.endGroup();
    settings.beginGroup("Misc");
    m_longList = settings.value("longList", false).toBool();
@@ -901,3 +972,30 @@ void MainWin::setMessageIcon()
    else
       actionMessages->setIcon(QIcon(QString::fromUtf8(":/images/mail-message-new.png")));
 }
+
+void MainWin::goToPreviousPage()
+{
+   m_treeStackTrap = true;
+   bool done = false;
+   while (!done) {
+      /* If stack list is emtpty, then done */
+      if (m_treeWidgetStack.isEmpty()) {
+         done = true;
+      } else {
+         QTreeWidgetItem* testItem = m_treeWidgetStack.takeLast();
+         QTreeWidgetItemIterator it(treeWidget);
+         /* lets avoid a segfault by setting an item current that no longer exists */
+         while (*it) {
+            if (*it == testItem) {
+               if (testItem != treeWidget->currentItem()) {
+                  treeWidget->setCurrentItem(testItem);
+                  done = true;
+               }
+               break;
+            }
+            ++it;
+         }
+      }
+   }
+   m_treeStackTrap = false;
+}