diff options
Diffstat (limited to 'src/kommando.cpp')
-rw-r--r-- | src/kommando.cpp | 282 |
1 files changed, 282 insertions, 0 deletions
diff --git a/src/kommando.cpp b/src/kommando.cpp new file mode 100644 index 0000000..6996d1b --- /dev/null +++ b/src/kommando.cpp @@ -0,0 +1,282 @@ +/*************************************************************************** + * Copyright (C) 2005 by Daniel Stöckel * + * the_docter@gmx.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 option) 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., * + * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. * + ***************************************************************************/ +#include "kommando.h" + +#include <klocale.h> +#include <X11/Xlib.h> +#include <X11/Xmu/WinUtil.h> +#include <kpixmapeffect.h> + +#include "configuration.h" + +Kommando::Kommando() + : QWidget( 0, "Kommando", Qt::WDestructiveClose | + Qt::WStyle_Customize | + Qt::WStyle_NoBorder), + actMenu(0), + navbutton(this), + oldNavbuttonIconType(0) +{ + mTopLevelMenus.setAutoDelete(true); + + //set up the widget's properties + resize(); + setBackgroundMode( NoBackground ); + + //set up the navbutton + Config& config = Config::getSingleton(); + navbutton.move(config.menuRadius(),config.menuRadius()); + connect(&navbutton, SIGNAL(clicked()), this, SLOT(slotNavClick())); +} + +void Kommando::slotGlobAccel() +{ + toggle(); +} + +void Kommando::show( ) +{ + Window rep_root, rep_child; + int rep_rootx, rep_rooty; + unsigned int rep_mask; + int mousex, mousey; + Display* dpy = qt_xdisplay(); + Window win = qt_xrootwin(); + XClassHint hint; + + hint.res_class = 0; + hint.res_name = 0; + + //Get mouse coursor position and the application name of the window under the coursor + XQueryPointer (dpy, win, &rep_root, &rep_child, &rep_rootx, &rep_rooty, &mousex, &mousey, &rep_mask); + + rep_child = XmuClientWindow(dpy,rep_child); + if(XGetClassHint(dpy,rep_child,&hint) != 0){ + setActTopLevelMenu(hint.res_class); + } else { + setActTopLevelMenu("default"); + } + if(hint.res_class){ + XFree(hint.res_class); + } + if(hint.res_name){ + XFree(hint.res_name); + } + + Config& config = Config::getSingleton(); + move(mousex-config.menuRadius(),mousey-config.menuRadius()); + + //get the part of the screen the widget is drawn onto and apply a fade effect to it + mScreenshot = QPixmap::grabWindow( qt_xrootwin(), x(), y(), width(), height() ); + KPixmapEffect::fade( mScreenshot, config.opacity(), config.tintColor() ); + + QWidget::show(); +} + +void Kommando::hide( ) +{ + selectButton(BUTTON_DESELECT); + QWidget::hide(); +} + +void Kommando::toggle( ) +{ + if(!isHidden()){ + hide(); + } else { + show(); + } +} + +void Kommando::setActMenu( Menu * newMenu ) +{ + //disconnect everything + if(actMenu != 0){ + actMenu->disconnect(); + actMenu->hideButtons(); + } + + if(newMenu != 0){ + if(mTopLevelMenus.containsRef(newMenu)){ + navbutton.setIcon("error"); + } else { + navbutton.setIcon("back"); + } + + //initialize the new menu + connect(newMenu, SIGNAL(clicked(int)), this, SLOT(slotOnClick()) ); + connect(newMenu, SIGNAL(buttonSelected(int)),this,SLOT(slotButtonSelected(int))); + newMenu->showButtons(); + } + actMenu = newMenu; +} + +void Kommando::setActTopLevelMenu(const QString& appName ) +{ + Menu* menu = 0; + for(Menu* it = mTopLevelMenus.first(); it != 0; it = mTopLevelMenus.next()){ + if (it->appName() == appName){ + menu = it; + break; + } + //get a default menu, assume that a toplevel menu with QString::null or "default" as appname is one + if ((it->appName() == QString::null) || (it->appName() == "default")){ + menu = it; + } + } + setActMenu(menu); +} + +void Kommando::setTopLevelMenus( const QPtrList<Menu>& newmenus ) +{ + setActMenu(0); + //No need to clear the list, because autoDelete is turned on in + //mTopLevelMenus + mTopLevelMenus = newmenus; +} + +void Kommando::windowActivationChange( bool oldActive ) +{ + //if the menu loses focus hide it + if(oldActive){ + hide(); + } +} + +void Kommando::paintEvent( QPaintEvent * evt ) +{ + QPainter p(this); + p.drawPixmap(evt->rect().topLeft(),mScreenshot,evt->rect()); +} + +void Kommando::wheelEvent( QWheelEvent * evt ) +{ + actMenu->selectButton(actMenu->selectedButtonNum()+evt->delta()/120); +} + +void Kommando::execute( ) +{ + if(!isHidden()){ + Menu* temp = actMenu->execute(); + if(temp){ + setActMenu(temp); + } else { + hide(); + } + } +} + +void Kommando::slotOnClick( ) +{ + execute(); +} + +void Kommando::slotNavClick( ) +{ + if(actMenu->selectedButtonNum()==BUTTON_DESELECT){ + if(mTopLevelMenus.containsRef(actMenu)){ + hide(); + } else { + setActMenu(actMenu->parentMenu()); + } + } else { + execute(); + } +} + +void Kommando::slotButtonSelected( int type ) +{ + if(oldNavbuttonIconType != type){ + switch(type){ + case 0: + if(mTopLevelMenus.containsRef(actMenu)){ + navbutton.setIcon("error"); + } else { + navbutton.setIcon("back"); + } + break; + case RoundButton::Commando: + navbutton.setIcon("exec"); + break; + case RoundButton::Submenu: + navbutton.setIcon("folder"); + break; + } + oldNavbuttonIconType=type; + } +} + +void Kommando::keyPressEvent( QKeyEvent * evt ) +{ + switch(evt->key()){ + case Qt::Key_Left: + actMenu->selectButton(actMenu->selectedButtonNum()-1); + break; + case Qt::Key_Right: + actMenu->selectButton(actMenu->selectedButtonNum()+1); + break; + case Qt::Key_Return: + slotNavClick(); + break; + case Qt::Key_Escape: + if(mTopLevelMenus.containsRef(actMenu)){ + hide(); + } else { + setActMenu(actMenu->parentMenu()); + } + break; + case Qt::Key_1: + case Qt::Key_2: + case Qt::Key_3: + case Qt::Key_4: + case Qt::Key_5: + case Qt::Key_6: + case Qt::Key_7: + case Qt::Key_8: + case Qt::Key_9: + //We want to get the number of the button, so treat the enum as number (yes I know, but it works fine :->) + actMenu->selectButton(evt->key() - Qt::Key_1); + break; + } +} + +void Kommando::setNavButtonSize( unsigned short size ) +{ + navbutton.setRadius(size); + Config& config = Config::getSingleton(); + navbutton.move(config.menuRadius(),config.menuRadius()); +} + +void Kommando::resize( ) +{ + Config& config = Config::getSingleton(); + setFixedSize(config.menuSize(),config.menuSize()); + //apply a circular mask + QRegion mask(rect(),QRegion::Ellipse); + setMask(mask); +} + +void Kommando::selectButton( int num ) +{ + if(!isHidden()) + actMenu->selectButton(num); +} + +#include "kommando.moc" |