//============================================================================= // // File : kvi_frame.cpp // Creation date : Sun Jun 18 2000 17:59:02 by Szymon Stefanek // // This file is part of the KVirc irc client distribution // Copyright (C) 1999-2000 Szymon Stefanek (pragma at kvirc dot net) // // This program is FREE software. You can redistribute it and/or // modify it under the terms of the GNU General Public License // as published by the Free Software Foundation; either version 2 // of the License, or (at your opinion) any later version. // // This program is distributed in the HOPE that it will be USEFUL, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. // See the GNU General Public License for more details. // // You should have received a copy of the GNU General Public License // along with this program. If not, write to the Free Software Foundation, // Inc. ,51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. // //============================================================================= #define __KVIRC__ #define _KVI_FRAME_CPP_ #include "kvi_debug.h" #include "kvi_app.h" #include "kvi_settings.h" #include "kvi_frame.h" #include "kvi_options.h" #include "kvi_menubar.h" #include "kvi_mdimanager.h" #include "kvi_mdichild.h" #include "kvi_iconmanager.h" #include "kvi_window.h" #include "kvi_taskbar.h" #include "kvi_console.h" #include "kvi_config.h" #include "kvi_internalcmd.h" #include "kvi_console.h" #include "kvi_debug.h" #include "kvi_irctoolbar.h" #include "kvi_confignames.h" #include "kvi_parameterlist.h" #include "kvi_module.h" #include "kvi_mextoolbar.h" #include "kvi_locale.h" #include "kvi_irccontext.h" #include "kvi_statusbar.h" #include "kvi_customtoolbar.h" #include "kvi_customtoolbarmanager.h" #include "kvi_customtoolbardescriptor.h" #include "kvi_actionmanager.h" #include "kvi_defaults.h" #include "kvi_ircview.h" #include "kvi_tal_popupmenu.h" #include "kvi_kvs_script.h" #include "kvi_kvs_eventtriggers.h" #include #include #include #include #include #include #include #include #include #ifdef COMPILE_USE_QT4 #include #define TQDockArea Q3DockArea #else #include #endif #ifdef COMPILE_USE_QT4 #include #include #include #else #include #endif #include #ifdef COMPILE_PSEUDO_TRANSPARENCY #include // kvi_app.h extern TQPixmap * g_pShadedParentGlobalDesktopBackground; extern TQPixmap * g_pShadedChildGlobalDesktopBackground; // FIXME: #warning "When a toolbar is moved , MdiManager is resized but does not update the MdiChild backgrounds" #endif // Declared and managed by KviApp (kvi_app.cpp) extern KviConfig * g_pWinPropertiesConfig; KVIRC_API KviFrame * g_pFrame = 0; // the one and only frame object KviFrame::KviFrame() : KviTalMainWindow(0,"kvirc_frame") { g_pFrame = this; setIcon(*(g_pIconManager->getSmallIcon(KVI_SMALLICON_KVIRC))); m_pWinList = new KviPointerList; m_pWinList->setAutoDelete(false); m_pModuleExtensionToolBarList = new KviPointerList; m_pModuleExtensionToolBarList->setAutoDelete(false); m_pActiveContext = 0; m_pDockExtension = 0; m_pSplitter = new TQSplitter(Qt::Horizontal,this,"main_splitter"); // m_pSplitter->setFrameShape(TQFrame::NoFrame); setCentralWidget(m_pSplitter); setUsesBigPixmaps(KVI_OPTION_BOOL(KviOption_boolUseBigIcons)); m_pMdi = new KviMdiManager(m_pSplitter,this,"mdi_manager"); connect(m_pMdi,TQT_SIGNAL(enteredSdiMode()),this,TQT_SLOT(enteredSdiMode())); connect(m_pMdi,TQT_SIGNAL(leftSdiMode()),this,TQT_SLOT(leftSdiMode())); // This theoretically had to exists before KviMdiManager (that uses enterSdiMode) m_pMenuBar = new KviMenuBar(this,"main_menu_bar"); #ifdef COMPILE_USE_QT4 setMenuWidget(m_pMenuBar); #endif if(KVI_OPTION_BOOL(KviOption_boolStatusBarVisible)) { m_pStatusBar = new KviStatusBar(this); #ifdef COMPILE_USE_QT4 setStatusBar(m_pStatusBar); #endif // torque: moved out of status bar constructor // because module init functions exectued in load() // couldn't access the status bar via g_pFrame->mainStatusBar() // (assignment of m_pStatusBar happened after load() and // the init function) m_pStatusBar->load(); } else m_pStatusBar = 0; m_pTaskBar = 0; createTaskBar(); if((KVI_OPTION_RECT(KviOption_rectFrameGeometry).width() < 100) || (KVI_OPTION_RECT(KviOption_rectFrameGeometry).height() < 100)) { // Try to find some reasonable defaults KVI_OPTION_RECT(KviOption_rectFrameGeometry) = TQRect(10,10,g_pApp->desktop()->width() - 200,g_pApp->desktop()->height() - 150); } resize(KVI_OPTION_RECT(KviOption_rectFrameGeometry).width(), KVI_OPTION_RECT(KviOption_rectFrameGeometry).height()); move(KVI_OPTION_RECT(KviOption_rectFrameGeometry).x(), KVI_OPTION_RECT(KviOption_rectFrameGeometry).y()); applyOptions(); m_pAccel = new KviAccel(this); installAccelerators(this); tqlayout()->setResizeMode(TQLayout::FreeResize); } KviFrame::~KviFrame() { KVI_OPTION_RECT(KviOption_rectFrameGeometry) = TQRect(pos().x(),pos().y(), size().width(),size().height()); KVI_OPTION_BOOL(KviOption_boolUseBigIcons) = usesBigPixmaps(); KVI_OPTION_BOOL(KviOption_boolMdiManagerInSdiMode) = m_pMdi->isInSDIMode(); KVI_OPTION_BOOL(KviOption_boolStatusBarVisible) = m_pStatusBar ? true : false; KviCustomToolBarManager::instance()->storeVisibilityState(); saveToolBarPositions(); saveModuleExtensionToolBars(); // Call the frame destructor callback AFTER saving the toolbar positions // This is because the destructor callback kills alls the KVS objects // and thus the eventual user toolbar objects too and their position // wouldn't be saved if they are shown at startup. g_pApp->frameDestructorCallback(); // Now start killing stuff // Explicitly kill all the module extension toolbars: qt has NOT to delete them: we must call their "die" method while(KviMexToolBar * t = m_pModuleExtensionToolBarList->first())t->die(); delete m_pModuleExtensionToolBarList; KVI_OPTION_BOOL(KviOption_boolShowDockExtension) = m_pDockExtension; if(m_pDockExtension) { m_pDockExtension->die(); m_pDockExtension = 0; } // the really last thing to do : close all the windows while(m_pWinList->first()) closeWindow(m_pWinList->first()); delete m_pWinList; delete m_pAccel; g_pFrame = 0; } int KviFrame::registerAccelerator(const TQString &szKeySequence,TQObject * recv,const char * slot) { int id = m_pAccel->insertItem(szKeySequence); m_pAccel->connectItem(id,recv,slot); return id; } void KviFrame::unregisterAccelerator(int id) { m_pAccel->removeItem(id); } void KviFrame::registerModuleExtensionToolBar(KviMexToolBar * t) { m_pModuleExtensionToolBarList->append(t); } void KviFrame::unregisterModuleExtensionToolBar(KviMexToolBar * t) { m_pModuleExtensionToolBarList->removeRef(t); } void KviFrame::restoreModuleExtensionToolBars() { for(TQStringList::Iterator it = KVI_OPTION_STRINGLIST(KviOption_stringlistModuleExtensionToolbars).begin();it != KVI_OPTION_STRINGLIST(KviOption_stringlistModuleExtensionToolbars).end();++it) { TQString szEntry = *it; int idx = szEntry.find(':'); if(idx != -1) { TQString szMod = szEntry.left(idx); szEntry.remove(0,idx + 1); g_pModuleExtensionManager->allocateExtension("toolbar",KviStr(szEntry),firstConsole(),0,0,szMod); } } } void KviFrame::saveModuleExtensionToolBars() { KVI_OPTION_STRINGLIST(KviOption_stringlistModuleExtensionToolbars).clear(); for(KviMexToolBar * t = m_pModuleExtensionToolBarList->first();t;t = m_pModuleExtensionToolBarList->next()) { TQString s = t->descriptor()->module()->name(); s += ":"; s += t->descriptor()->name().ptr(); //debug("FOUND TOOLBAR %s",t->descriptor()->name().ptr()); KVI_OPTION_STRINGLIST(KviOption_stringlistModuleExtensionToolbars).append(s); } } KviMexToolBar * KviFrame::moduleExtensionToolBar(int extensionId) { for(KviMexToolBar * t = m_pModuleExtensionToolBarList->first();t;t = m_pModuleExtensionToolBarList->next()) { if(extensionId == t->descriptor()->id())return t; } return 0; } /* @doc: keyboard @type: generic @title: Keyboard shortcuts @keyterms: Keyboard shortcuts @short: The list of the common keyboard shortcuts @body: [b]Ctrl+LeftArrow[/b]: Selection left to the previous word[br] [b]Ctrl+RightArrow[/b]: Selection right to the next word[br] [b]Ctrl+Shift+LeftArrow[/b]: Previous word[br] [b]Ctrl+Shift+RightArrow[/b]: Next word[br] [b]Alt+LeftArrow[/b]: Previous window[br] [b]Alt+RightArrow[/b]: Next window[br] [b]Alt+Shift+LeftArrow[/b]: Previous window in the same IRC context[/b] [b]Alt+Shift+RightArrow[/b]: Next window in the same IRC context[/b] [b]Ctrl+UpArrow[/b]: Maximize current window[br] [b]Ctrl+DownArrow[/b] or [b]ESC[/b]: Minimize current window[br] [b]Ctrl+<digit>[/b], [b]F1-F12[/b], [b]Shift+(F1-F12)[/b]: Script accelerators (see [event:onaccelkeypressed]OnAccelKeyPressed[/event])[br] [b]Shift+<F1-F12>[/b] window switch[br] [b]Tab in the first word of input[/b]: Completes nicknames in the current channel or query[br] [b]Tab after a leading /[/b]: Completes commands[br] [b]Tab after a / in the middle of input[/b]: Completes directories[br] [b]Tab after a $[/b]: Completes function names[br] [b]Shift+Tab after the first word of input[/b]: completes masks in the current channel or query[br] [b]Ctrl+B[/b]: Inserts the 'bold' mIRC text control character[br] [b]Ctrl+K[/b]: Inserts the 'color' mIRC text control character[br] [b]Ctrl+R[/b]: Inserts the 'reverse' mIRC text control character[br] [b]Ctrl+U[/b]: Inserts the 'underline' mIRC text control character[br] [b]Ctrl+O[/b]: Inserts the 'reset' mIRC text control character[br] [b]Ctrl+P[/b]: Inserts the 'non-crypt' (plain text) KVIrc control character used to disable encryption of the current text line[br] [b]Ctrl+C[/b]: Copies the selected text to clipboard[br] [b]Ctrl+X[/b]: Cuts the selected text[br] [b]Ctrl+V[/b]: Pastes the clipboard contents (same as middle mouse click)[br] [b]Ctrl+I[/b]: Inserts the 'icon' control code and pops up the icon list box [b]CursorUp[/b]: Moves backward in the command history[br] [b]CursorDown[/b]: Moves forward in the command history[br] [b]Ctrl+PageUp[/b]: Opens the history popup[br] [b]CursorRight[/b]: Moves the cursor to the right[br] [b]CursorLeft[/b]: Moves the cursor to the left :)[br] [b]Shift+CursorLeft[/b]: Moves the selection to the left[br] [b]Shift+RightCursor[/b]: Moves the selection to the right[br] [b]PageUp[/b]: Scrolls the output window up one page[br] [b]PageDown[/b]: Scrolls the output window down one page[b] [b]Shift+PageUp[/b]: Scrolls the output window up one line[br] [b]Shift+PageDown[/b]: Scrolls the output window down one line[b] [b]Alt+lt;numeric_sequence>[/b]: Inserts the character by ASCII/Unicode code[br] [b]Ctrl+Backspace[/b]: Shows or hides the multiline editor[br] [b]Ctrl+F4[/b]: Closes the current window[br] Alt+32: Inserts ASCII/Unicode character 32: ' ' (a space) Alt+00032: Same as above :) Alt+13: Inserts the Carriage Return (CR) control character Alt+77: Inserts ASCII/Unicode character 77: 'M' Alt+23566: Inserts Unicode character 23566 (an ideogram) */ KviAccel * KviFrame::installAccelerators(TQWidget * wnd) { TQWidget * pParent = wnd ? (TQWidget *)wnd : (TQWidget *)this; #ifdef COMPILE_USE_QT4 new TQShortcut(TQKeySequence(TQt::Key_Left + TQt::ALT),pParent,TQT_SLOT(switchToPrevWindow())); new TQShortcut(TQKeySequence(TQt::Key_Right + TQt::ALT),pParent,TQT_SLOT(switchToNextWindow())); new TQShortcut(TQKeySequence(TQt::Key_Up + TQt::CTRL),pParent,TQT_SLOT(maximizeWindow())); new TQShortcut(TQKeySequence(TQt::Key_Down + TQt::CTRL),pParent,TQT_SLOT(minimizeWindow())); new TQShortcut(TQKeySequence(TQt::Key_Escape +TQt::CTRL),pParent,TQT_SLOT(minimizeWindow())); new TQShortcut(TQKeySequence(TQt::Key_Left + TQt::ALT + TQt::SHIFT),pParent,TQT_SLOT(switchToPrevWindowInContext())); new TQShortcut(TQKeySequence(TQt::Key_Right + TQt::ALT + TQt::SHIFT),pParent,TQT_SLOT(switchToNextWindowInContext())); #endif KviAccel *ac = new KviAccel(pParent); static int accel_table[] = { TQt::Key_Left + TQt::ALT , // prev window TQt::Key_Right + TQt::ALT , // next window TQt::Key_Up + TQt::CTRL , // maximize window TQt::Key_Down + TQt::CTRL , // minimize window TQt::Key_Escape +TQt::CTRL, // minimize window TQt::Key_Left + TQt::ALT + TQt::SHIFT , // prev window in context TQt::Key_Right + TQt::ALT + TQt::SHIFT, // next window in context TQt::Key_F4 + TQt::CTRL , // close current window TQt::Key_1 + TQt::CTRL , // script accels... TQt::Key_2 + TQt::CTRL , TQt::Key_3 + TQt::CTRL , TQt::Key_4 + TQt::CTRL , TQt::Key_5 + TQt::CTRL , TQt::Key_6 + TQt::CTRL , TQt::Key_7 + TQt::CTRL , TQt::Key_8 + TQt::CTRL , TQt::Key_9 + TQt::CTRL , TQt::Key_0 + TQt::CTRL , TQt::Key_F1 , // reserved for context sensitive help TQt::Key_F2 , TQt::Key_F3 , TQt::Key_F4 , TQt::Key_F5 , TQt::Key_F6 , TQt::Key_F7 , TQt::Key_F8 , TQt::Key_F9 , TQt::Key_F10 , TQt::Key_F11 , TQt::Key_F12 , /* TQt::Key_F1 + TQt::SHIFT , // window select... TQt::Key_F2 + TQt::SHIFT , TQt::Key_F3 + TQt::SHIFT , TQt::Key_F4 + TQt::SHIFT , TQt::Key_F5 + TQt::SHIFT , TQt::Key_F6 + TQt::SHIFT , TQt::Key_F7 + TQt::SHIFT , TQt::Key_F8 + TQt::SHIFT , TQt::Key_F9 + TQt::SHIFT , TQt::Key_F10 + TQt::SHIFT , TQt::Key_F11 + TQt::SHIFT , TQt::Key_F12 + TQt::SHIFT ,*/ 0 }; int i=0; int keys; while((keys = accel_table[i])) { ac->insertItem(keys); i++; } connect(ac,TQT_SIGNAL(activated(int)),this,TQT_SLOT(accelActivated(int))); return ac; } void KviFrame::accelActivated(int id) { KviAccel * acc = (KviAccel *)TQT_TQOBJECT(const_cast(sender())); int keys = (int)(acc->key(id)); KviTaskBarItem *item = 0; debug("accel"); switch(keys) { case (TQt::Key_Left+TQt::ALT): switchToPrevWindow(); break; case (TQt::Key_Right+TQt::ALT): switchToNextWindow(); break; case (TQt::Key_Up+TQt::CTRL): maximizeWindow(); break; case (TQt::Key_Escape+TQt::CTRL): case (TQt::Key_Down+TQt::CTRL): minimizeWindow(); break; case (TQt::Key_Left+TQt::ALT+TQt::SHIFT): switchToPrevWindowInContext(); break; case (TQt::Key_Right+TQt::ALT+TQt::SHIFT): switchToNextWindowInContext(); break; case (TQt::Key_F4+TQt::CTRL): if(g_pActiveWindow)g_pActiveWindow->close(); break; case (TQt::Key_F1): g_pApp->contextSensitiveHelp(); break; /* case(TQt::Key_F1 + SHIFT): item = m_pTaskBar->item(0); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F2 + SHIFT): item = m_pTaskBar->item(1); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F3 + SHIFT): item = m_pTaskBar->item(2); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F4 + SHIFT): item = m_pTaskBar->item(3); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F5 + SHIFT): item = m_pTaskBar->item(4); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F6 + SHIFT): item = m_pTaskBar->item(5); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F7 + SHIFT): item = m_pTaskBar->item(6); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F8 + SHIFT): item = m_pTaskBar->item(7); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F9 + SHIFT): item = m_pTaskBar->item(8); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F10 + SHIFT): item = m_pTaskBar->item(9); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F11 + SHIFT): item = m_pTaskBar->item(10); if(item) setActiveWindow(item->window()); break; case(TQt::Key_F12 + SHIFT): item = m_pTaskBar->item(11); if(item) setActiveWindow(item->window()); break;*/ default: { KVS_TRIGGER_EVENT_1(KviEvent_OnAccelKeyPressed,g_pActiveWindow,(TQString)(acc->key(id))); } break; }; } void KviFrame::executeInternalCommand(int index) { KviKvsScript::run(kvi_getInternalCommandBuffer(index),firstConsole()); } void KviFrame::saveWindowProperties(KviWindow * wnd,const char * szSection) { g_pWinPropertiesConfig->setGroup(szSection); g_pWinPropertiesConfig->writeEntry("EntryTimestamp",(unsigned int)time(0)); // Allow max 80 window properties to be floating around while(g_pWinPropertiesConfig->groupsCount() > 80) { // Kill the oldest group KviConfigIterator it(*(g_pWinPropertiesConfig->dict())); KviStr minKey; unsigned int minVal = time(0); while(it.current() && minVal) { TQString * pVal = it.current()->find("EntryTimestamp"); if(pVal) { bool bOk; unsigned int uVal = pVal->toUInt(&bOk); if(bOk) { if(uVal < minVal) { minVal = uVal; minKey = it.currentKey(); } } else { minVal = 0; minKey = it.currentKey(); } } else { minVal = 0; minKey = it.currentKey(); } ++it; } if(minKey.hasData())g_pWinPropertiesConfig->clearGroup(minKey.ptr()); else debug("Oops...no minimum key found!"); } // The following line should NOT be needed...but just to be sure... g_pWinPropertiesConfig->setGroup(szSection); g_pWinPropertiesConfig->writeEntry("IsDocked",wnd->mdiParent()); // KviWindow * top = g_pActiveWindow; // if(!top)top = wnd; // g_pWinPropertiesConfig->writeEntry("IsMaximized",top->isMaximized()); g_pWinPropertiesConfig->writeEntry("WinRect",wnd->externalGeometry()); wnd->saveProperties(g_pWinPropertiesConfig); } void KviFrame::closeWindow(KviWindow *wnd) { // notify the destruction wnd->triggerDestructionEvents(); // save it's properties if(KVI_OPTION_BOOL(KviOption_boolWindowsRememberProperties)) // && (wnd->type() == KVI_WINDOW_TYPE_CHANNEL)) { TQString group; wnd->getConfigGroupName(group); // not uses default settings : store it always saveWindowProperties(wnd,group); } // forget it... m_pWinList->removeRef(wnd); // hide it if(wnd->mdiParent())wnd->mdiParent()->hide(); else wnd->hide(); if(wnd == g_pActiveWindow) { // we need another active window before destroying it KviMdiChild * pMdiChild = wnd->mdiParent(); if(pMdiChild) { pMdiChild = m_pMdi->highestChildExcluding(pMdiChild); } else { // the best candidate for the new active window // is the top mdiManager's child pMdiChild = m_pMdi->topChild(); } KviWindow * pCandidate; if(pMdiChild) { pCandidate = (KviWindow *)(pMdiChild->client()); } else { pCandidate = m_pWinList->first(); if(pCandidate == wnd)pCandidate = 0; } if(pCandidate) childWindowActivated(pCandidate); // else { m_pActiveWindow = 0; m_pActiveContext = 0; }; } if(wnd == g_pActiveWindow) // ops... :/ ... this happens only at shutdown { g_pActiveWindow = 0; m_pActiveContext = 0; } // and shut it down... // KviWindow will call childWindowDestroyed() here if(wnd->mdiParent())m_pMdi->destroyChild(wnd->mdiParent(),true); else delete wnd; } void KviFrame::addWindow(KviWindow *wnd,bool bShow) { m_pWinList->append(wnd); wnd->createTaskBarItem(); // create the window taskbar item AFTER it has been constructed TQString group; wnd->getConfigGroupName(group); bool bGroupSettings = false; if(g_pWinPropertiesConfig->hasGroup(group)) { g_pWinPropertiesConfig->setGroup(group); } else { bGroupSettings = true; if(g_pWinPropertiesConfig->hasGroup(wnd->typeString())) { g_pWinPropertiesConfig->setGroup(wnd->typeString()); } else { g_pWinPropertiesConfig->setGroup("no_settings_group"); wnd->loadProperties(g_pWinPropertiesConfig); // load it anyway (will set defaults if windows don't remember properties) goto default_docking; // no settings stored } } { wnd->loadProperties(g_pWinPropertiesConfig); // load it anyway (will set defaults if windows don't remember properties) if(KVI_OPTION_BOOL(KviOption_boolWindowsRememberProperties)) { bool bDocked = g_pWinPropertiesConfig->readBoolEntry("IsDocked",true); //bool bMaximized = g_pWinPropertiesConfig->readBoolEntry("IsMaximized",false); bool bMaximized; if(KVI_OPTION_BOOL(KviOption_boolMdiManagerInSdiMode)) { bMaximized = true; //KVI_OPTION_BOOL(KviOption_boolMdiManagerInSdiMode) = false; } else bMaximized = false; TQRect rect = g_pWinPropertiesConfig->readRectEntry("WinRect",TQRect(10,10,500,380)); if(bDocked) { // when group settings are used , we always cascade the windows // this means that windows that have no specialized config group name // are always cascaded : this is true for consoles , queries (and other windows) but not channels (and some other windows) KviMdiChild * lpC = dockWindow(wnd,false,bGroupSettings,&rect); lpC->setRestoredGeometry(rect); wnd->triggerCreationEvents(); if(bShow) { m_pMdi->showAndActivate(lpC); if(bMaximized)wnd->maximize(); // Handle the special case of this top level widget not being the active one. // In this situation the child will not get the focusInEvent // and thus will not call out childWindowActivated() method if(!isActiveWindow())childWindowActivated(wnd); } } else { wnd->setGeometry(rect); wnd->triggerCreationEvents(); if(bShow) { wnd->show(); if(bMaximized)wnd->maximize(); } wnd->youAreUndocked(); if(bShow) { wnd->raise(); wnd->setFocus(); } } goto docking_done; } } default_docking: { KviMdiChild * lpC = dockWindow(wnd,false); //cascade it wnd->triggerCreationEvents(); if(bShow) { m_pMdi->showAndActivate(lpC); if(KVI_OPTION_BOOL(KviOption_boolMdiManagerInSdiMode)) wnd->maximize(); // Handle the special case of this top level widget not being the active one. // In this situation the child will not get the focusInEvent // and thus will not call out childWindowActivated() method if(!isActiveWindow())childWindowActivated(wnd); } } docking_done: // we like to have an active window.. but don't trigger the events until it is really shown if(!g_pActiveWindow) { g_pActiveWindow = wnd; m_pActiveContext = wnd->context(); } } KviMdiChild * KviFrame::dockWindow(KviWindow *wnd,bool bShow,bool bCascade,TQRect *setGeom) { if(wnd->mdiParent())return wnd->mdiParent(); KviMdiChild * lpC = new KviMdiChild(m_pMdi,""); lpC->setClient(wnd); wnd->youAreDocked(); m_pMdi->manageChild(lpC,bCascade,setGeom); if(bShow)m_pMdi->showAndActivate(lpC); return lpC; } void KviFrame::undockWindow(KviWindow *wnd) { if(!(wnd->mdiParent()))return; KviMdiChild * lpC = wnd->mdiParent(); lpC->unsetClient(); m_pMdi->destroyChild(lpC,false); wnd->youAreUndocked(); wnd->raise(); wnd->setFocus(); } void KviFrame::newConsole() { createNewConsole(); } KviConsole * KviFrame::createNewConsole(bool bFirstInFrame) { // the first console must be created BEFORE the toolbars visible // at startup otherwise we cannot execute script code // which is necessary for the actions that are going to be added // to the toolbars KviConsole * c = new KviConsole(this,bFirstInFrame ? KVI_CONSOLE_FLAG_FIRSTINFRAME : 0); addWindow(c); if(bFirstInFrame) { restoreModuleExtensionToolBars(); KviCustomToolBarManager::instance()->createToolBarsVisibleAtStartup(); KviActionManager::instance()->delayedRegisterAccelerators(); restoreToolBarPositions(); } return c; } unsigned int KviFrame::consoleCount() { unsigned int count = 0; for(KviWindow * wnd = m_pWinList->first();wnd;wnd = m_pWinList->next()) { if(wnd->type() == KVI_WINDOW_TYPE_CONSOLE)count++; } return count; } KviConsole * KviFrame::firstConsole() { for(KviWindow * wnd = m_pWinList->first();wnd;wnd = m_pWinList->next()) { if(wnd->type() == KVI_WINDOW_TYPE_CONSOLE)return (KviConsole *)wnd; } __range_valid(false); return 0; //should newer be here!.. but sometimes we are ? } KviConsole * KviFrame::firstNotConnectedConsole() { for(KviWindow * wnd = m_pWinList->first();wnd;wnd = m_pWinList->next()) { if(wnd->type() == KVI_WINDOW_TYPE_CONSOLE) { if(!((KviConsole *)wnd)->connectionInProgress()) return (KviConsole *)wnd; } } return 0; } void KviFrame::childWindowCloseRequest(KviWindow *wnd) { closeWindow(wnd); } void KviFrame::unhighlightWindowsOfContext(KviIrcContext * c) { for(KviWindow *w = m_pWinList->first();w;w = m_pWinList->next()) if(w->context() == c)w->unhighlight(); } void KviFrame::setActiveWindow(KviWindow *wnd) { // ASSERT(m_pWinList->findRef(wnd)) if(wnd->isMinimized())wnd->restore(); if(wnd->mdiParent())wnd->setFocus(); else wnd->delayedAutoRaise(); } KviIrcConnection * KviFrame::activeConnection() { return m_pActiveContext ? m_pActiveContext->connection() : 0; } void KviFrame::childWindowSelectionStateChange(KviWindow * pWnd,bool bGotSelectionNow) { if(pWnd != g_pActiveWindow)return; emit activeWindowSelectionStateChanged(bGotSelectionNow); } void KviFrame::childContextStateChange(KviIrcContext * c) { if(c != m_pActiveContext)return; emit activeContextStateChanged(); } void KviFrame::childConnectionLagChange(KviIrcConnection * c) { KviIrcContext * ctx = c->context(); if(ctx != m_pActiveContext)return; emit activeConnectionLagChanged(); } void KviFrame::childConnectionServerInfoChange(KviIrcConnection * c) { KviIrcContext * ctx = c->context(); if(ctx != m_pActiveContext)return; emit activeConnectionServerInfoChanged(); } void KviFrame::childConnectionNickNameChange(KviIrcConnection * c) { KviIrcContext * ctx = c->context(); if(ctx != m_pActiveContext)return; emit activeConnectionNickNameChanged(); } void KviFrame::childConnectionAwayStateChange(KviIrcConnection * c) { KviIrcContext * ctx = c->context(); if(ctx != m_pActiveContext)return; emit activeConnectionAwayStateChanged(); } void KviFrame::childConnectionUserModeChange(KviIrcConnection * c) { KviIrcContext * ctx = c->context(); if(ctx != m_pActiveContext)return; emit activeConnectionUserModeChanged(); } void KviFrame::childWindowActivated(KviWindow *wnd) { // ASSERT(m_pWinList->findRef(wnd)) if(g_pActiveWindow == wnd)return; if(g_pActiveWindow)g_pActiveWindow->lostUserFocus(); // YES: it's HERE! g_pActiveWindow = wnd; bool bActiveContextChanged = (m_pActiveContext != wnd->context()); m_pActiveContext = wnd->context(); if(wnd->isMaximized() && wnd->mdiParent())updateCaption(); m_pTaskBar->setActiveItem(wnd->taskBarItem()); //wnd->gainedActiveWindowStatus(); // <-- atm unused if(g_pActiveWindow->view()) g_pActiveWindow->view()->clearUnreaded(); emit activeWindowChanged(); if(bActiveContextChanged)emit activeContextChanged(); KVS_TRIGGER_EVENT_0(KviEvent_OnWindowActivated,wnd); } void KviFrame::windowActivationChange(bool bOldActive) { // if we have just been activated by the WM // then update the active window task bar item // It will then reset its highlight state // and hopefully make the dock widget work correctly // in this case. // This will also trigger the OnWindowActivated event :) if(isActiveWindow()) { if(!bOldActive) { if(g_pActiveWindow) { KviWindow * pTmp = g_pActiveWindow; g_pActiveWindow = 0; // really ugly hack! childWindowActivated(pTmp); } } } else { if(g_pActiveWindow)g_pActiveWindow->lostUserFocus(); } } void KviFrame::enteredSdiMode() { updateCaption(); } void KviFrame::leftSdiMode() { updateCaption(); } #define KVI_DEFAULT_FRAME_CAPTION "KVIrc " KVI_VERSION " " KVI_RELEASE_NAME void KviFrame::updateCaption() { if(g_pActiveWindow) { if(g_pActiveWindow->isMaximized() && g_pActiveWindow->mdiParent()) { TQString tmp = g_pActiveWindow->plainTextCaption(); tmp += TQChar(' '); tmp += KVI_DEFAULT_FRAME_CAPTION; setCaption(tmp); return; } } setCaption(KVI_DEFAULT_FRAME_CAPTION); } void KviFrame::closeEvent(TQCloseEvent *e) { if(KVI_OPTION_BOOL(KviOption_boolCloseInTray)) { e->ignore(); if(!dockExtension()) { executeInternalCommand(KVI_INTERNALCOMMAND_DOCKWIDGET_SHOW); } if(dockExtension()) { dockExtension()->setPrevWindowState(windowState()); TQTimer::singleShot( 0, this, TQT_SLOT(hide()) ); } return; } if(KVI_OPTION_BOOL(KviOption_boolConfirmCloseWhenThereAreConnections)) { // check for running connections bool bGotRunningConnection = false; for(KviWindow * w = m_pWinList->first();w;w = m_pWinList->next()) { if(w->type() == KVI_WINDOW_TYPE_CONSOLE) { if(((KviConsole *)w)->connectionInProgress()) { bGotRunningConnection = true; break; } } } if(bGotRunningConnection) { TQString txt = "

"; txt += __tr2qs("There are active connections, are you sure you wish to "); txt += __tr2qs("quit KVIrc?"); txt += "

"; switch(TQMessageBox::warning(this,__tr2qs("Confirmation - KVIrc"),txt,__tr2qs("&Yes"),__tr2qs("&Always"),__tr2qs("&No"),2,2)) { case 0: // ok to close break; case 1: // ok to close but don't ask again KVI_OPTION_BOOL(KviOption_boolConfirmCloseWhenThereAreConnections) = false; break; case 2: e->ignore(); return; break; } } } e->accept(); if(g_pApp) g_pApp->destroyFrame(); } void KviFrame::resizeEvent(TQResizeEvent *e) { KVI_OPTION_RECT(KviOption_rectFrameGeometry) = TQRect(pos().x(),pos().y(), size().width(),size().height()); KviTalMainWindow::resizeEvent(e); } void KviFrame::updatePseudoTransparency() { #ifdef COMPILE_PSEUDO_TRANSPARENCY if(g_pShadedParentGlobalDesktopBackground)m_pMdi->viewport()->update(); if(g_pShadedChildGlobalDesktopBackground) { for(KviWindow * wnd = m_pWinList->first();wnd;wnd = m_pWinList->next())wnd->updateBackgrounds(); m_pTaskBar->updatePseudoTransparency(); } #endif } void KviFrame::moveEvent(TQMoveEvent *e) { KVI_OPTION_RECT(KviOption_rectFrameGeometry) = TQRect(pos().x(),pos().y(), size().width(),size().height()); #ifdef COMPILE_PSEUDO_TRANSPARENCY updatePseudoTransparency(); #endif KviTalMainWindow::moveEvent(e); } void KviFrame::applyOptions() { m_pMdi->update(); for(KviWindow * wnd = m_pWinList->first();wnd;wnd = m_pWinList->next())wnd->applyOptions(); updateCaption(); m_pTaskBar->applyOptions(); } void KviFrame::toggleStatusBar() { if(m_pStatusBar) { delete m_pStatusBar; m_pStatusBar = 0; } else { //if(statusBar())delete statusBar(); // kill any existing status bar (QT BUG) m_pStatusBar = new KviStatusBar(this); m_pStatusBar->load(); #ifdef COMPILE_USE_QT4 setStatusBar(m_pStatusBar); #endif m_pStatusBar->show(); #ifndef COMPILE_USE_QT4 setUpLayout(); #endif //!COMPILE_USE_QT4 } } void KviFrame::fillToolBarsPopup(KviTalPopupMenu * p) { p->clear(); disconnect(p,TQT_SIGNAL(activated(int)),this,TQT_SLOT(toolbarsPopupSelected(int))); // just to be sure connect(p,TQT_SIGNAL(activated(int)),this,TQT_SLOT(toolbarsPopupSelected(int))); int id; int cnt = 0; KviModuleExtensionDescriptorList * l = g_pModuleExtensionManager->getExtensionList("toolbar"); if(l) { for(KviModuleExtensionDescriptor * d = l->first();d;d = l->next()) { TQString label = __tr2qs("Show %1").tqarg(d->visibleName()); if(d->icon())id = p->insertItem(*(d->icon()),label); else id = p->insertItem(label); p->setItemChecked(id,moduleExtensionToolBar(d->id())); p->setItemParameter(id,d->id()); cnt++; } } // FIXME: Should this display "Hide %1" when the toolbar is already visible ? KviPointerHashTableIterator it2(*(KviCustomToolBarManager::instance()->descriptors())); if(it2.current()) { if(cnt > 0)p->insertSeparator(); while(KviCustomToolBarDescriptor * d = it2.current()) { TQString label = __tr2qs("Show %1").tqarg(d->label()); TQString ico = d->iconId(); // use the icon only if there is no check if(d->toolBar()) { id = p->insertItem(label); p->setItemChecked(id,true); } else { if(!ico.isEmpty()) { TQPixmap * pix = g_pIconManager->getImage(d->iconId()); if(pix) { id = p->insertItem(*pix,label); } else { id = p->insertItem(label); } } else { id = p->insertItem(label); } } p->setItemParameter(id,d->internalId()); ++it2; cnt++; } } if(cnt > 0)p->insertSeparator(); p->insertItem(*(g_pIconManager->getSmallIcon(KVI_SMALLICON_TOOLBAR)),__tr2qs("Customize..."),this,TQT_SLOT(customizeToolBars())); } void KviFrame::customizeToolBars() { KviKvsScript::run("toolbareditor.open",g_pActiveWindow); } void KviFrame::toolbarsPopupSelected(int id) { const TQObject * o = TQT_TQOBJECT(const_cast(sender())); if(!o)return; if(!o->inherits("KviTalPopupMenu"))return; const KviTalPopupMenu * p = (const KviTalPopupMenu *)o; int idext = p->itemParameter(id); KviCustomToolBarDescriptor * dd = KviCustomToolBarManager::instance()->findDescriptorByInternalId(idext); if(dd) { if(dd->toolBar())delete dd->toolBar(); else dd->createToolBar(); } if(KviMexToolBar * t = moduleExtensionToolBar(idext)) { t->die(); } else { g_pModuleExtensionManager->allocateExtension("toolbar",idext,firstConsole()); } } bool KviFrame::focusNextPrevChild(bool next) { //debug("FOCUS NEXT PREV CHILD"); TQWidget * w = focusWidget(); if(w) { #ifdef COMPILE_USE_QT4 if(w->focusPolicy() == TTQ_StrongFocus)return false; #else if(w->focusPolicy() == TQ_StrongFocus)return false; #endif //TQVariant v = w->property("KviProperty_FocusOwner"); //if(v.isValid())return false; // Do NOT change the focus widget! if(w->parent()) { TQVariant v = w->parent()->property("KviProperty_ChildFocusOwner"); if(v.isValid())return false; // Do NOT change the focus widget! } } // try to focus the widget on top of the Mdi if(m_pMdi->topChild()) { m_pMdi->focusTopChild(); return false; } return KviTalMainWindow::focusNextPrevChild(next); } //////////////////////////////////////////////////////////////////////////////////////////////////// // Toolbar positioning stuff //////////////////////////////////////////////////////////////////////////////////////////////////// void KviFrame::saveToolBarPositions() { TQString szTemp; g_pApp->getLocalKvircDirectory(szTemp,KviApp::Config,KVI_CONFIGFILE_TOOLBARS); TQFile f(szTemp); if(f.open(IO_WriteOnly | IO_Truncate)) { #ifdef COMPILE_USE_QT4 f.write(saveState(1)); #else //!COMPILE_USE_QT4 TQTextStream ts(&f); ts << *this; f.close(); #endif //!COMPILE_USE_QT4 } } void KviFrame::restoreToolBarPositions() { TQString szTemp; g_pApp->getLocalKvircDirectory(szTemp,KviApp::Config,KVI_CONFIGFILE_TOOLBARS); TQFile f(szTemp); bool bNeedDefaults = false; if(f.open(IO_ReadOnly)) { #ifdef COMPILE_USE_QT4 if(!restoreState(f.readAll(),1)) debug("Error while restoring toolbars position"); #else //!COMPILE_USE_QT4 TQTextStream ts(&f); ts >> *this; f.close(); #endif //!COMPILE_USE_QT4 } else { bNeedDefaults = true; } if(m_pTaskBar->inherits("KviTreeTaskBar")) { #ifdef COMPILE_USE_QT4 // ensure that it is not too wide m_pTaskBar->setMaximumWidth(600); if(m_pTaskBar->width() > 600) m_pTaskBar->setFixedWidth(250); #else //!COMPILE_USE_QT4 TQDockArea * a = m_pTaskBar->area(); if((a == topDock()) || (a == bottomDock())) { // nope.... need to move it a->removeDockWindow(m_pTaskBar,true,false); //int iMaxWidth = m_pTaskBar->maximumWidth(); leftDock()->moveDockWindow(m_pTaskBar); //m_pTaskBar->setMaximumWidth(iMaxWidth); //m_pTaskBar->setOrientationQt::Vertical); } // ensure that it is not too wide if(m_pTaskBar->width() > 600) m_pTaskBar->setFixedExtentWidth(250); #endif //!COMPILE_USE_QT4 } /*else if(m_pTaskBar->inherits("KviClassicTaskBar")) { TQDockArea * a = m_pTaskBar->area(); if((a == leftDock()) || (a == rightDock())) { // nope.... need to move it a->removeDockWindow(m_pTaskBar,true,false); bottomDock()->moveDockWindow(m_pTaskBar); bottomDock()->lineUp(true); } }*/ #ifndef COMPILE_USE_QT4 if(bNeedDefaults) lineUpDockWindows(false); #endif //!COMPILE_USE_QT4 } void KviFrame::createTaskBar() { if(KVI_OPTION_BOOL(KviOption_boolUseTreeWindowListTaskBar)) { m_pTaskBar = new KviTreeTaskBar(); #ifdef COMPILE_USE_QT4 m_pTaskBar->setAllowedAreas(TQt::LeftDockWidgetArea | TQt::RightDockWidgetArea); addDockWidget(TQt::LeftDockWidgetArea,m_pTaskBar); #else //!COMPILE_USE_QT4 setDockEnabled(m_pTaskBar,TQt::DockTop,false); setDockEnabled(m_pTaskBar,TQt::DockBottom,false); #endif //!COMPILE_USE_QT4 } else { m_pTaskBar = new KviClassicTaskBar(); #ifdef COMPILE_USE_QT4 m_pTaskBar->setAllowedAreas(TQt::AllDockWidgetAreas); addDockWidget(TQt::BottomDockWidgetArea,m_pTaskBar); #else //!COMPILE_USE_QT4 setDockEnabled(m_pTaskBar,TQt::DockTop,true); setDockEnabled(m_pTaskBar,TQt::DockBottom,true); #endif //!COMPILE_USE_QT4 } #ifndef COMPILE_USE_QT4 setDockEnabled(m_pTaskBar,TQt::DockLeft,true); setDockEnabled(m_pTaskBar,TQt::DockRight,true); #endif //!COMPILE_USE_QT4 } void KviFrame::recreateTaskBar() { TQString szOldClass = m_pTaskBar->className(); saveToolBarPositions(); KviWindow * w; for(w = m_pWinList->first();w;w = m_pWinList->next()) { w->destroyTaskBarItem(); } #ifndef COMPILE_USE_QT4 removeDockWindow(m_pTaskBar); #endif //!COMPILE_USE_QT4 delete m_pTaskBar; createTaskBar(); for(w = m_pWinList->first();w;w = m_pWinList->next()) { w->createTaskBarItem(); } restoreToolBarPositions(); /* TQString szNewClass = m_pTaskBar->className(); if(szOldClass != szNewClass) { // the class changed... // make sure that the tree task bar is in the left or right dock // and the classic one is in the top or bottom on TQt::Dock dock; int index; bool nl; int eo; getLocation(m_pTaskBar,dock,index,nl,eo); if(KVI_OPTION_BOOL(KviOption_boolUseTreeWindowListTaskBar)) { if((dock == TQt::Bottom) || (dock == TQt::Top)) moveDockWindow(m_pTaskBar,TQt::Left); } else { if((dock == TQt::Left) || (dock == TQt::Right)) moveDockWindow(m_pTaskBar,TQt::Bottom); } } */ if(g_pActiveWindow)m_pTaskBar->setActiveItem(g_pActiveWindow->taskBarItem()); } //////////////////////////////////////////////////////////////////////////////////////////////////// // Some accelerators //////////////////////////////////////////////////////////////////////////////////////////////////// void KviFrame::maximizeWindow(void) { if(!g_pActiveWindow)return; if(g_pActiveWindow->isMaximized())g_pActiveWindow->restore(); else g_pActiveWindow->maximize(); } void KviFrame::minimizeWindow(void) { if(g_pActiveWindow)g_pActiveWindow->minimize(); } void KviFrame::switchToPrevWindow(void) { m_pTaskBar->switchWindow(false,false); } void KviFrame::switchToNextWindow(void) { m_pTaskBar->switchWindow(true,false); } void KviFrame::switchToPrevWindowInContext(void) { m_pTaskBar->switchWindow(false,true); } void KviFrame::switchToNextWindowInContext(void) { m_pTaskBar->switchWindow(true,true); } void KviFrame::hideEvent ( TQHideEvent * e) { if(KVI_OPTION_BOOL(KviOption_boolMinimizeInTray)) { if(e->spontaneous()) { if(!dockExtension()) { executeInternalCommand(KVI_INTERNALCOMMAND_DOCKWIDGET_SHOW); } TQTimer::singleShot( 0, this, TQT_SLOT(hide()) ); } } } #include "kvi_frame.moc"