summaryrefslogtreecommitdiffstats
path: root/kicker/libkicker
diff options
context:
space:
mode:
Diffstat (limited to 'kicker/libkicker')
-rw-r--r--kicker/libkicker/CMakeLists.txt42
-rw-r--r--kicker/libkicker/Makefile.am19
-rw-r--r--kicker/libkicker/appletinfo.cpp112
-rw-r--r--kicker/libkicker/appletinfo.h92
-rw-r--r--kicker/libkicker/global.cpp490
-rw-r--r--kicker/libkicker/global.h112
-rw-r--r--kicker/libkicker/kickerSettings.kcfg509
-rw-r--r--kicker/libkicker/kickerSettings.kcfgc8
-rw-r--r--kicker/libkicker/kickertip.cpp568
-rw-r--r--kicker/libkicker/kickertip.h121
-rw-r--r--kicker/libkicker/kshadowengine.cpp251
-rw-r--r--kicker/libkicker/kshadowengine.h123
-rw-r--r--kicker/libkicker/kshadowsettings.cpp182
-rw-r--r--kicker/libkicker/kshadowsettings.h236
-rw-r--r--kicker/libkicker/menuinfo.cpp68
-rw-r--r--kicker/libkicker/menuinfo.h52
-rw-r--r--kicker/libkicker/panelbutton.cpp1103
-rw-r--r--kicker/libkicker/panelbutton.h488
-rw-r--r--kicker/libkicker/paneldrag.cpp180
-rw-r--r--kicker/libkicker/paneldrag.h68
-rw-r--r--kicker/libkicker/panner.cpp396
-rw-r--r--kicker/libkicker/panner.h115
-rw-r--r--kicker/libkicker/simplebutton.cpp289
-rw-r--r--kicker/libkicker/simplebutton.h91
24 files changed, 5715 insertions, 0 deletions
diff --git a/kicker/libkicker/CMakeLists.txt b/kicker/libkicker/CMakeLists.txt
new file mode 100644
index 000000000..e2ec5a6ba
--- /dev/null
+++ b/kicker/libkicker/CMakeLists.txt
@@ -0,0 +1,42 @@
+#################################################
+#
+# (C) 2010-2011 Serghei Amelian
+# serghei (DOT) amelian (AT) gmail.com
+#
+# Improvements and feedback are welcome
+#
+#################################################
+
+include_directories(
+ ${CMAKE_CURRENT_BINARY_DIR}
+ ${TDE_INCLUDE_DIR}
+ ${TQT_INCLUDE_DIRS}
+)
+
+link_directories(
+ ${TQT_LIBRARY_DIRS}
+)
+
+
+##### other data ################################
+
+install( FILES kickerSettings.kcfg DESTINATION ${KCFG_INSTALL_DIR} )
+
+
+##### kickermain (shared) #######################
+
+set( target kickermain )
+
+set( ${target}_SRCS
+ appletinfo.cpp global.cpp kickertip.cpp menuinfo.cpp
+ panelbutton.cpp panner.cpp kickerSettings.kcfgc
+ kshadowsettings.cpp kshadowengine.cpp paneldrag.cpp
+ simplebutton.cpp
+)
+
+tde_add_library( ${target} SHARED AUTOMOC
+ SOURCES ${${target}_SRCS}
+ VERSION 1.0.0
+ LINK tdeio-shared
+ DESTINATION ${LIB_INSTALL_DIR}
+)
diff --git a/kicker/libkicker/Makefile.am b/kicker/libkicker/Makefile.am
new file mode 100644
index 000000000..fb917c67e
--- /dev/null
+++ b/kicker/libkicker/Makefile.am
@@ -0,0 +1,19 @@
+INCLUDES = $(all_includes)
+
+lib_LTLIBRARIES = libkickermain.la
+
+libkickermain_la_SOURCES = appletinfo.cpp global.cpp kickertip.cpp \
+ menuinfo.cpp panelbutton.cpp panner.cpp \
+ kickerSettings.kcfgc kshadowsettings.cpp \
+ kshadowengine.cpp paneldrag.cpp \
+ simplebutton.cpp
+
+libkickermain_la_METASOURCES = AUTO
+
+libkickermain_la_LDFLAGS = $(all_libraries) -version-info 1:0:0 -no-undefined
+libkickermain_la_LIBADD = $(LIB_TDEIO)
+
+kde_kcfg_DATA = kickerSettings.kcfg
+
+messages: rc.cpp
+ $(XGETTEXT) *.cpp *.h -o $(podir)/libkicker.pot
diff --git a/kicker/libkicker/appletinfo.cpp b/kicker/libkicker/appletinfo.cpp
new file mode 100644
index 000000000..4a851df55
--- /dev/null
+++ b/kicker/libkicker/appletinfo.cpp
@@ -0,0 +1,112 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#include <tqfileinfo.h>
+#include <kdesktopfile.h>
+#include <tdeapplication.h>
+
+#include "appletinfo.h"
+
+AppletInfo::AppletInfo( const TQString& deskFile, const TQString& configFile, const AppletInfo::AppletType type)
+ : m_type (type),
+ m_unique(true),
+ m_hidden(false)
+{
+ TQFileInfo fi(deskFile);
+ m_desktopFile = fi.fileName();
+
+ const char* resource = "applets";
+ switch (type)
+ {
+ case Extension:
+ resource = "extensions";
+ break;
+ case BuiltinButton:
+ resource = "builtinbuttons";
+ break;
+ case SpecialButton:
+ resource = "specialbuttons";
+ break;
+ case Undefined:
+ case Applet:
+ default:
+ break;
+ }
+
+ KDesktopFile df(m_desktopFile, true, resource);
+
+ // set the appletssimple attributes
+ setName(df.readName());
+ setComment(df.readComment());
+ setIcon(df.readIcon());
+
+ // library
+ setLibrary(df.readEntry("X-TDE-Library"));
+
+ // is it a unique applet?
+ setIsUnique(df.readBoolEntry("X-TDE-UniqueApplet", false));
+
+ // should it be shown in the gui?
+ m_hidden = df.readBoolEntry("Hidden", false);
+
+ if (configFile.isEmpty())
+ {
+ // generate a config file base name from the library name
+ m_configFile = m_lib.lower();
+
+ if (m_unique)
+ {
+ m_configFile.append("rc");
+ }
+ else
+ {
+ m_configFile.append("_")
+ .append(kapp->randomString(20).lower())
+ .append("_rc");
+ }
+ }
+ else
+ {
+ m_configFile = configFile;
+ }
+}
+
+bool AppletInfo::operator!=( const AppletInfo& rhs) const
+{
+ return configFile() != rhs.configFile();
+}
+
+bool AppletInfo::operator<( const AppletInfo& rhs ) const
+{
+ return ( TQString::localeAwareCompare( name(), rhs.name() ) < 0 );
+}
+
+bool AppletInfo::operator> ( const AppletInfo& rhs ) const
+{
+ return ( TQString::localeAwareCompare( name(), rhs.name() ) > 0 );
+}
+
+bool AppletInfo::operator<= ( const AppletInfo& rhs ) const
+{
+ return ( TQString::localeAwareCompare( name(), rhs.name() ) <= 0 );
+}
diff --git a/kicker/libkicker/appletinfo.h b/kicker/libkicker/appletinfo.h
new file mode 100644
index 000000000..f89bb6aea
--- /dev/null
+++ b/kicker/libkicker/appletinfo.h
@@ -0,0 +1,92 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#ifndef __appletinfo_h__
+#define __appletinfo_h__
+
+#include <tqmap.h>
+#include <tqptrlist.h>
+#include <tqstring.h>
+#include <tqvaluevector.h>
+
+#include <kdemacros.h>
+
+class KDE_EXPORT AppletInfo
+{
+ public:
+ typedef TQValueVector<AppletInfo> List;
+ typedef TQMap<TQObject*, AppletInfo*> Dict;
+
+ enum AppletType { Undefined = 0,
+ Applet = 1,
+ BuiltinButton = 2,
+ SpecialButton = 4,
+ Extension = 8,
+ Button = BuiltinButton | SpecialButton };
+
+ AppletInfo(const TQString& desktopFile = TQString::null,
+ const TQString& configFile = TQString::null,
+ const AppletType type = Undefined);
+
+ TQString name() const { return m_name; }
+ TQString comment() const { return m_comment; }
+ TQString icon() const { return m_icon; }
+
+ AppletType type() const { return m_type; }
+
+ TQString library() const { return m_lib; }
+ TQString desktopFile() const { return m_desktopFile; }
+ TQString configFile() const { return m_configFile; }
+
+ bool isUniqueApplet() const { return m_unique; }
+ bool isHidden() const { return m_hidden; }
+
+ void setConfigFile(TQString cf) { m_configFile = cf; }
+
+ bool operator<(const AppletInfo& rhs) const;
+ bool operator>(const AppletInfo& rhs) const;
+ bool operator<=(const AppletInfo& rhs) const;
+ bool operator!=(const AppletInfo& rhs) const;
+
+ void setType(AppletType type) { m_type = type; }
+
+ protected:
+ void setName(TQString name) { m_name = name; }
+ void setComment(TQString comment) { m_comment = comment; }
+ void setIcon(TQString icon) { m_icon = icon; }
+ void setLibrary(TQString lib) { m_lib = lib; }
+ void setIsUnique(bool u) { m_unique = u; }
+
+ private:
+ TQString m_name;
+ TQString m_comment;
+ TQString m_icon;
+ TQString m_lib;
+ TQString m_desktopFile;
+ TQString m_configFile;
+ AppletType m_type;
+ bool m_unique;
+ bool m_hidden;
+};
+
+#endif
diff --git a/kicker/libkicker/global.cpp b/kicker/libkicker/global.cpp
new file mode 100644
index 000000000..62f7f055a
--- /dev/null
+++ b/kicker/libkicker/global.cpp
@@ -0,0 +1,490 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#include <tqapplication.h>
+#include <tqbitmap.h>
+#include <tqfile.h>
+#include <tqpopupmenu.h>
+#include <tqregexp.h>
+#include <tqpainter.h>
+
+#include <kiconeffect.h>
+#include <kiconloader.h>
+#include <tdeio/netaccess.h>
+#include <kstandarddirs.h>
+#include <kservice.h>
+#include <ksimpleconfig.h>
+
+#include "global.h"
+#include "kickerSettings.h"
+
+namespace KickerLib
+{
+
+KPanelExtension::Position directionToPosition(KPanelApplet::Direction d )
+{
+ switch (d)
+ {
+ case KPanelApplet::Down:
+ return KPanelExtension::Top;
+ break;
+
+ case KPanelApplet::Left:
+ return KPanelExtension::Right;
+ break;
+
+ case KPanelApplet::Right:
+ return KPanelExtension::Left;
+ break;
+
+ case KPanelApplet::Up:
+ default:
+ return KPanelExtension::Bottom;
+ break;
+ }
+}
+
+KPanelExtension::Position directionToPopupPosition(KPanelApplet::Direction d)
+{
+ switch (d)
+ {
+ case KPanelApplet::Up:
+ return KPanelExtension::Top;
+ break;
+
+ case KPanelApplet::Down:
+ return KPanelExtension::Bottom;
+ break;
+
+ case KPanelApplet::Left:
+ return KPanelExtension::Left;
+ break;
+
+ case KPanelApplet::Right:
+ default:
+ return KPanelExtension::Right;
+ break;
+ }
+}
+
+KPanelApplet::Direction positionToDirection(KPanelExtension::Position p)
+{
+ switch (p)
+ {
+ case KPanelExtension::Top:
+ return KPanelApplet::Down;
+ break;
+
+ case KPanelExtension::Right:
+ return KPanelApplet::Left;
+ break;
+
+ case KPanelExtension::Left:
+ return KPanelApplet::Right;
+ break;
+
+ case KPanelExtension::Bottom:
+ default:
+ return KPanelApplet::Up;
+ break;
+ }
+}
+
+KPanelApplet::Direction arrowToDirection(TQt::ArrowType p)
+{
+ switch (p)
+ {
+ case Qt::DownArrow:
+ return KPanelApplet::Down;
+ break;
+
+ case Qt::LeftArrow:
+ return KPanelApplet::Left;
+ break;
+
+ case Qt::RightArrow:
+ return KPanelApplet::Right;
+ break;
+
+ case Qt::UpArrow:
+ default:
+ return KPanelApplet::Up;
+ break;
+ }
+}
+
+int sizeValue(KPanelExtension::Size s)
+{
+ switch (s)
+ {
+ case KPanelExtension::SizeTiny:
+ return 24;
+ break;
+
+ case KPanelExtension::SizeSmall:
+ return 30;
+ break;
+
+ case KPanelExtension::SizeNormal:
+ return 46;
+ break;
+
+ case KPanelExtension::SizeLarge:
+ default:
+ return 58;
+ break;
+ }
+}
+
+int maxButtonDim()
+{
+ int maxDim;
+ //return (2 * KickerSettings::iconMargin()) + TDEIcon::SizeLarge;
+
+ KSimpleConfig *kickerconfig = new KSimpleConfig( TQString::fromLatin1( "kickerrc" ));
+ kickerconfig->setGroup("General");
+ maxDim = (2 * KickerSettings::iconMargin()) + kickerconfig->readNumEntry("panelIconWidth", TDEIcon::SizeLarge);;
+ delete kickerconfig;
+ return maxDim;
+}
+
+TQString newDesktopFile(const KURL& url)
+{
+ TQString base = url.fileName();
+ if (base.endsWith(".desktop"))
+ base.truncate(base.length()-8);
+ TQRegExp r("(.*)(?=-\\d+)");
+ if (r.search(base) > -1)
+ base = r.cap(1);
+
+ TQString file = base + ".desktop";
+
+ for(int n = 1; ++n; )
+ {
+ TQString path = locate("appdata", file);
+ if (path.isEmpty())
+ break;
+
+ file = TQString("%2-%1.desktop").arg(n).arg(base);
+ }
+ file = locateLocal("appdata", file);
+ return file;
+}
+
+TQString copyDesktopFile(const KURL& url)
+{
+ TQString file = newDesktopFile(url);
+ KURL dest;
+ dest.setPath(file);
+ TDEIO::NetAccess::upload(url.path(), dest, 0);
+ return file;
+}
+
+TQPopupMenu* reduceMenu(TQPopupMenu *menu)
+{
+ if (menu->count() != 1)
+ {
+ return menu;
+ }
+
+ TQMenuItem *item = menu->findItem(menu->idAt(0));
+
+ if (item->popup())
+ {
+ return reduceMenu(item->popup());
+ }
+
+ return menu;
+}
+
+TQPoint popupPosition(KPanelApplet::Direction d,
+ const TQWidget* popup,
+ const TQWidget* source,
+ const TQPoint& offset)
+{
+ TQRect r;
+ if (source->isTopLevel())
+ {
+ r = source->geometry();
+ }
+ else
+ {
+ r = TQRect(source->mapToGlobal(TQPoint(0, 0)),
+ source->mapToGlobal(TQPoint(source->width(), source->height())));
+
+ switch (d)
+ {
+ case KPanelApplet::Left:
+ case KPanelApplet::Right:
+ r.setLeft( source->topLevelWidget()->x() );
+ r.setWidth( source->topLevelWidget()->width() );
+ break;
+ case KPanelApplet::Up:
+ case KPanelApplet::Down:
+ r.setTop( source->topLevelWidget()->y() );
+ r.setHeight( source->topLevelWidget()->height() );
+ break;
+ }
+ }
+
+ switch (d)
+ {
+ case KPanelApplet::Left:
+ case KPanelApplet::Right:
+ {
+ TQDesktopWidget* desktop = TQApplication::desktop();
+ TQRect screen = desktop->screenGeometry(desktop->screenNumber(const_cast<TQWidget*>(source)));
+ int x = (d == KPanelApplet::Left) ? r.left() - popup->width() :
+ r.right() + 1;
+ int y = r.top() + offset.y();
+
+ // try to keep this on screen
+ if (y + popup->height() > screen.bottom())
+ {
+ y = r.bottom() - popup->height() + offset.y();
+
+ if (y < screen.top())
+ {
+ y = screen.bottom() - popup->height();
+
+ if (y < screen.top())
+ {
+ y = screen.top();
+ }
+ }
+ }
+
+ return TQPoint(x, y);
+ }
+ case KPanelApplet::Up:
+ case KPanelApplet::Down:
+ default:
+ {
+ int x = 0;
+ int y = (d == KPanelApplet::Up) ? r.top() - popup->height() :
+ r.bottom() + 1;
+
+ if (TQApplication::reverseLayout())
+ {
+ x = r.right() - popup->width() + 1;
+
+ if (offset.x() > 0)
+ {
+ x -= r.width() - offset.x();
+ }
+
+ // try to keep this on the screen
+ if (x - popup->width() < 0)
+ {
+ x = r.left();
+ }
+
+ return TQPoint(x, y);
+ }
+ else
+ {
+ TQDesktopWidget* desktop = TQApplication::desktop();
+ TQRect screen = desktop->screenGeometry(desktop->screenNumber(const_cast<TQWidget*>(source)));
+ x = r.left() + offset.x();
+
+ // try to keep this on the screen
+ if (x + popup->width() > screen.right())
+ {
+ x = r.right() - popup->width() + 1 + offset.x();
+
+ if (x < screen.left())
+ {
+ x = screen.left();
+ }
+ }
+ }
+
+ return TQPoint(x, y);
+ }
+ }
+}
+
+void colorize(TQImage& image)
+{
+ TDEConfig *config = TDEGlobal::config();
+ config->setGroup("WM");
+ TQColor color = TQApplication::palette().active().highlight();
+ TQColor activeTitle = config->readColorEntry("activeBackground", &color);
+ TQColor inactiveTitle = config->readColorEntry("inactiveBackground", &color);
+
+ // figure out which color is most suitable for recoloring to
+ int h1, s1, v1, h2, s2, v2, h3, s3, v3;
+ activeTitle.hsv(&h1, &s1, &v1);
+ inactiveTitle.hsv(&h2, &s2, &v2);
+ TQApplication::palette().active().background().hsv(&h3, &s3, &v3);
+
+ if ( (kAbs(h1-h3)+kAbs(s1-s3)+kAbs(v1-v3) < kAbs(h2-h3)+kAbs(s2-s3)+kAbs(v2-v3)) &&
+ ((kAbs(h1-h3)+kAbs(s1-s3)+kAbs(v1-v3) < 32) || (s1 < 32)) && (s2 > s1))
+ color = inactiveTitle;
+ else
+ color = activeTitle;
+
+ // limit max/min brightness
+ int r, g, b;
+ color.rgb(&r, &g, &b);
+ int gray = tqGray(r, g, b);
+ if (gray > 180) {
+ r = (r - (gray - 180) < 0 ? 0 : r - (gray - 180));
+ g = (g - (gray - 180) < 0 ? 0 : g - (gray - 180));
+ b = (b - (gray - 180) < 0 ? 0 : b - (gray - 180));
+ } else if (gray < 76) {
+ r = (r + (76 - gray) > 255 ? 255 : r + (76 - gray));
+ g = (g + (76 - gray) > 255 ? 255 : g + (76 - gray));
+ b = (b + (76 - gray) > 255 ? 255 : b + (76 - gray));
+ }
+ color.setRgb(r, g, b);
+ TDEIconEffect::colorize(image, color, 1.0);
+}
+
+TQColor blendColors(const TQColor& c1, const TQColor& c2)
+{
+ int r1, g1, b1;
+ int r2, g2, b2;
+
+ c1.rgb(&r1, &g1, &b1);
+ c2.rgb(&r2, &g2, &b2);
+
+ r1 += (int) (.5 * (r2 - r1));
+ g1 += (int) (.5 * (g2 - g1));
+ b1 += (int) (.5 * (b2 - b1));
+
+ return TQColor(r1, g1, b1);
+}
+
+TQColor shadowColor(const TQColor& c)
+{
+ int r = c.red();
+ int g = c.green();
+ int b = c.blue();
+
+ if ( r < 128 )
+ r = 255;
+ else
+ r = 0;
+
+ if ( g < 128 )
+ g = 255;
+ else
+ g = 0;
+
+ if ( b < 128 )
+ b = 255;
+ else
+ b = 0;
+
+ return TQColor( r, g, b );
+}
+
+TQIconSet menuIconSet(const TQString& icon)
+{
+ TQIconSet iconset;
+ int iconSize = KickerSettings::menuEntryHeight();
+
+ if (iconSize < 0)
+ {
+ return iconset;
+ }
+
+ if (icon != "unknown")
+ {
+ if (iconSize > 0)
+ {
+ iconset = TDEGlobal::iconLoader()->loadIconSet(icon,
+ TDEIcon::NoGroup,
+ iconSize, true);
+ }
+ else if (iconSize == 0)
+ {
+ TQPixmap normal = TDEGlobal::iconLoader()->loadIcon(icon,
+ TDEIcon::Small,
+ 0,
+ TDEIcon::DefaultState,
+ 0,
+ true);
+
+ TQPixmap active = TDEGlobal::iconLoader()->loadIcon(icon,
+ TDEIcon::Small,
+ 0,
+ TDEIcon::ActiveState,
+ 0,
+ true);
+
+ // make sure they are not larger than 20x20
+ if (normal.width() > 20 || normal.height() > 20)
+ {
+ normal.convertFromImage(TQImage(normal.convertToImage()).smoothScale(20,20));
+ }
+
+ if (active.width() > 20 || active.height() > 20)
+ {
+ active.convertFromImage(TQImage(active.convertToImage()).smoothScale(20,20));
+ }
+
+ iconset.setPixmap(normal, TQIconSet::Small, TQIconSet::Normal);
+ iconset.setPixmap(active, TQIconSet::Small, TQIconSet::Active);
+ }
+ }
+
+ if (iconset.isNull())
+ {
+ TQPixmap pix(iconSize, iconSize);
+ TQBitmap map(iconSize, iconSize, true);
+ pix.setMask(map);
+ iconset = TQIconSet(pix, pix);
+ }
+
+ return iconset;
+}
+
+void drawBlendedRect(TQPainter *p, const TQRect &r, const TQColor &color, int alpha)
+{
+ static TQPixmap pix;
+ static TQColor last_color = Qt::black;
+ static int last_alpha = 0;
+
+ if (pix.isNull() || last_color != color || last_alpha != alpha)
+ {
+ TQImage img(16, 16, 32);
+#ifdef USE_QT4
+ img.setAlphaBuffer(true);
+ img.fill(((uint)(alpha & 0xFF) << 24) | (color.rgb() & 0xFFFFFF));
+#else // USE_QT4
+ img.setAlphaBuffer(false);
+ img.fill(((uint)(alpha & 0xFF) << 24) | (color.rgb() & 0xFFFFFF));
+ img.setAlphaBuffer(true);
+#endif // USE_QT4
+ pix.convertFromImage(img);
+ last_color = color;
+ last_alpha = alpha;
+ }
+
+ p->drawTiledPixmap(r, pix);
+}
+
+} // namespace
+
diff --git a/kicker/libkicker/global.h b/kicker/libkicker/global.h
new file mode 100644
index 000000000..663987174
--- /dev/null
+++ b/kicker/libkicker/global.h
@@ -0,0 +1,112 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#ifndef __pglobal_h__
+#define __pglobal_h__
+
+#include <tqiconset.h>
+#include <tqmap.h>
+
+#include <kpanelapplet.h>
+#include <kpanelextension.h>
+#include <kurl.h>
+
+namespace KickerLib
+{
+
+/*
+ * Functions to convert between various enums
+ */
+KDE_EXPORT KPanelExtension::Position directionToPosition(KPanelApplet::Direction d);
+KDE_EXPORT KPanelExtension::Position directionToPopupPosition(KPanelApplet::Direction d);
+KDE_EXPORT KPanelApplet::Direction positionToDirection(KPanelExtension::Position p);
+KDE_EXPORT KPanelApplet::Direction arrowToDirection(TQt::ArrowType p);
+KDE_EXPORT int sizeValue(KPanelExtension::Size s);
+
+/**
+ * Pixel sizes for but sizes and margins
+ */
+KDE_EXPORT int maxButtonDim();
+
+/**
+ * Tint the image to reflect the current color scheme
+ * Used, for instance, by KMenu side bar
+ */
+KDE_EXPORT void colorize(TQImage& image);
+
+/**
+ * Blend a color rectangle on a painter
+ */
+KDE_EXPORT void drawBlendedRect(TQPainter *p, const TQRect &r, const TQColor &color = Qt::black, int alpha = 0x40);
+
+/**
+ * Blend two colours together to get a colour halfway in between
+ */
+KDE_EXPORT TQColor blendColors(const TQColor& c1, const TQColor& c2);
+
+/**
+ * Create or copy .desktop files for use in kicker safely and easily
+ */
+KDE_EXPORT TQString copyDesktopFile(const KURL&url);
+KDE_EXPORT TQString newDesktopFile(const KURL&url);
+
+
+/**
+ * Reduces a popup menu
+ *
+ * When a popup menu contains only 1 sub-menu, it makes no sense to
+ * show this popup-menu but we better show the sub-menu directly.
+ *
+ * This function checks whether that is the case and returns either the
+ * original menu or the sub-menu when appropriate.
+ */
+KDE_EXPORT TQPopupMenu *reduceMenu(TQPopupMenu *);
+
+
+/**
+ * Calculate the appropriate position for a popup menu based on the
+ * direction, the size of the menu, the widget geometry, and a optional
+ * point in the local coordinates of the widget.
+ */
+KDE_EXPORT TQPoint popupPosition(KPanelApplet::Direction d,
+ const TQWidget* popup,
+ const TQWidget* source,
+ const TQPoint& offset = TQPoint(0, 0));
+
+/**
+ * Calculate an acceptable inverse of the given color wich will be used
+ * as the shadow color.
+ */
+KDE_EXPORT TQColor shadowColor(const TQColor& c);
+
+/**
+ * Get an appropriate for a menu in Plasma. As the user may set this size
+ * globally, it is important to always use this method.
+ * @param icon the name of icon requested
+ * @return the icon set for the requested icon
+ */
+KDE_EXPORT TQIconSet menuIconSet(const TQString& icon);
+
+}
+
+#endif // __pglobal_h__
diff --git a/kicker/libkicker/kickerSettings.kcfg b/kicker/libkicker/kickerSettings.kcfg
new file mode 100644
index 000000000..0abc51bf0
--- /dev/null
+++ b/kicker/libkicker/kickerSettings.kcfg
@@ -0,0 +1,509 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<kcfg xmlns="http://www.kde.org/standards/kcfg/1.0"
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+ xsi:schemaLocation="http://www.kde.org/standards/kcfg/1.0
+ http://www.kde.org/standards/kcfg/1.0/kcfg.xsd" >
+
+<include>tdeapplication.h</include>
+<include>tdelocale.h</include>
+<kcfgfile arg="true" />
+
+<group name="General">
+
+<entry name="Locked" type="Bool" >
+ <label>When this option is enabled, the panels may not be moved and items cannot be removed or added</label>
+ <default>false</default>
+ </entry>
+
+<entry name="ConserveSpace" type="Bool" >
+ <label>Enable conserve space</label>
+ <default>true</default>
+ </entry>
+
+<entry name="Transparent" type="Bool" >
+ <label>Enable transparency</label>
+ <whatsthis>When this option is enabled, the panel will become pseudo-transparent</whatsthis>
+ <default>false</default>
+ </entry>
+
+<entry name="UseResizeHandle" type="Bool" >
+ <label>Enable resize handles</label>
+ <whatsthis>When this option is enabled, the panel will provide a resize handle on order to change its width via click-and-drag</whatsthis>
+ <default>false</default>
+ </entry>
+
+<entry name="ShowDeepButtons" type="Bool" >
+ <label>Make the task buttons push further into the screen when activated</label>
+ <default>false</default>
+ </entry>
+
+<entry name="MenubarPanelTransparent" type="Bool" >
+ <label>Enable transparency for menubar panel</label>
+ <whatsthis>When this option is enabled, the panel containing the menubar will become pseudo-transparent as well</whatsthis>
+ <default>false</default>
+ </entry>
+
+<entry name="MenubarPanelBlurred" type="Bool" >
+ <label>Enable blurring for menubar panel</label>
+ <whatsthis>When this option is enabled, the panel containing the menubar will blur pseudo-transparent image</whatsthis>
+ <default>false</default>
+ </entry>
+
+<entry name="UseBackgroundTheme" type="Bool" >
+ <label>Enable background image</label>
+ <whatsthis>When this option is enabled, the panel will display a tiled image as its background</whatsthis>
+ <default>true</default>
+ </entry>
+
+<entry name="ColorizeBackground" type="Bool" >
+ <label>Enable colourized background.</label>
+ <default>false</default>
+ </entry>
+
+<entry name="RotateBackground" type="Bool" >
+ <label>Rotate background</label>
+ <whatsthis>When this option is enabled, when the panel is placed on the side or top edges of the screen, the background image will be rotated to match the panel's orientation</whatsthis>
+ <default>true</default>
+ </entry>
+
+<entry name="BackgroundTheme" type="Path" >
+ <label>Background image</label>
+ <whatsthis>Here you can choose an image to be displayed on the panel. Press the 'browse' button to choose a theme using the file dialog. This option is only effective if 'Enable background image' is selected</whatsthis>
+ <default>wallpapers/default.png</default>
+ </entry>
+
+<entry name="TintValue" type="Int" >
+ <label>Controls the saturation level of the tint color used with transparent panels</label>
+ <default>33</default>
+ <min>0</min>
+ <max>100</max>
+ </entry>
+
+<entry name="TintColor" type="Color" >
+ <label>The tint color used to colorize transparent panels</label>
+ <default code="true">(TQApplication::palette().active().mid())</default>
+ <whatsthis>This option sets the color to use when tinting transparent panels</whatsthis>
+ </entry>
+
+<entry name="UnhideLocation" type="Int">
+ <label>Raise when the pointer touches the screen here</label>
+ <default>0</default>
+ </entry>
+
+<entry name="FadeOutAppletHandles" type="Bool">
+ <label>Fade out applet handles</label>
+ <default>true</default>
+ <whatsthis>Select this option to make applet handles only visible on mouse hover. Applet handles let you move, remove and configure applets.</whatsthis>
+ </entry>
+
+<entry name="HideAppletHandles" type="Bool">
+ <label>Hide applet handles</label>
+ <default>false</default>
+ <whatsthis>Select this option to always hide the applet handles. Beware this could disable moving, removing or configuring some applets.</whatsthis>
+ </entry>
+
+<entry name="ShowToolTips" type="Bool" >
+ <label>Show informational tooltips</label>
+ <default>true</default>
+ </entry>
+
+<entry name="ShowIconActivationEffect" type="Bool" >
+ <label>Show visual effect when panel icon is activated.</label>
+ <default>true</default>
+ </entry>
+
+<entry name="UntrustedApplets" type="StringList">
+ <label>A list of applets that have been loaded at runtime. In the case of a crash these applets will not be loaded at the next Kicker start, in case they caused the crash</label>
+ </entry>
+
+<entry name="UntrustedExtensions" type="StringList">
+ <label>A list of extensions that have been loaded at runtime. In the case of a crash these extensions will not be loaded at the next Kicker start, in case they caused the crash</label>
+ </entry>
+
+<entry name="LegacyKMenu" type="Bool" >
+ <label>When this option is enabled, the classic TDE Menu is used.</label>
+ <default>true</default>
+ </entry>
+
+<entry name="OpenOnHover" type="Bool" >
+ <label>When this option is enabled, the Kickoff Menu opens on mouse hover.</label>
+ <default>true</default>
+ </entry>
+
+<entry name="ScrollFlipView" type="Bool" >
+ <label>When this option is enabled, the Kickoff Menu application view switching will scroll.</label>
+ <default>true</default>
+ </entry>
+
+<entry name="KMenuWidth" type="Int">
+ <label>Preferred width of the KMenu</label>
+ <default>0</default>
+ </entry>
+
+<entry name="KMenuHeight" type="Int">
+ <label>Preferred width of the KMenu</label>
+ <default>0</default>
+ </entry>
+
+<entry name="KickoffFontPointSizeOffset" type="Int" >
+ <label>With this option the scale of the fonts Kickoff uses can be influenced</label>
+ <default>0</default>
+ <min>-100</min>
+ <max>100</max>
+ </entry>
+
+<entry name="KickoffSearchAddressBook" type="Bool" >
+ <label>When this option is enabled, tdeabc is utilized to search for addresses. This may start KMail.</label>
+ <default>false</default>
+ </entry>
+
+<entry name="KickoffDrawGeekoEye" type="Bool" >
+ <label>When this option is enabled, the Geeko eye moves when the mouse hovers the start menu button</label>
+ <default>false</default>
+ </entry>
+
+<entry name="KickoffTabBarFormat" type="Enum" >
+ <choices>
+ <choice name="LabelAndIcon">
+ <label>Show names and icons on tabs</label>
+ </choice>
+ <choice name="LabelOnly">
+ <label>Show only the names</label>
+ </choice>
+ <choice name="IconOnly">
+ <label>Show only the icons</label>
+ </choice>
+ </choices>
+ <default>LabelAndIcon</default>
+ <label>Appearace of the Kickoff tabbar</label>
+ </entry>
+
+<entry name="KickoffSwitchTabsOnHover" type="Bool" >
+ <label>When this option is enabled, the tabs in the Kickoff menu will switch without the need to click</label>
+ <default>true</default>
+ </entry>
+
+
+</group>
+
+<group name="menus">
+
+ <entry name="MenuEntryFormat" type="Enum" >
+ <choices>
+ <choice name="NameOnly">
+ <label>Show simple menu entries</label>
+ </choice>
+ <choice name="NameAndDescription">
+ <label>Show names first on detailed entries</label>
+ </choice>
+ <choice name="DescriptionOnly">
+ <label>Show only description for menu entries</label>
+ </choice>
+ <choice name="DescriptionAndName">
+ <label>Show detailed menu entries</label>
+ </choice>
+ </choices>
+ <default>DescriptionAndName</default>
+ <label>Formation of the menu entry text</label>
+ </entry>
+
+<entry name="ShowMenuTitles" type="Bool" >
+ <label>Show section titles in Kmenu</label>
+ <default>true</default>
+ </entry>
+
+<entry name="ReduceMenuDepth" type="Bool" >
+ <label>Simplify menus with only a single item inside</label>
+ <default>false</default>
+ </entry>
+
+<entry name="MenuEntryHeight" type="Int" >
+ <label>Height of menu entries in pixels</label>
+ <default>0</default>
+ </entry>
+
+<entry name="ShowHiddenFiles" type="Bool" >
+ <label>Show hidden files in Quick Browser</label>
+ <default>false</default>
+ </entry>
+
+<entry name="MaxEntries2" type="UInt" >
+ <label>Maximum number of entries</label>
+ <default>30</default>
+ <min>1</min>
+ </entry>
+
+<entry name="UseBookmarks" type="Bool" >
+ <label>Show bookmarks in KMenu</label>
+ <default>false</default>
+ </entry>
+
+<entry name="UseBrowser" type="Bool" >
+ <label>Use the Quick Browser</label>
+ <default>false</default>
+ </entry>
+
+<entry name="MenuExtensions" key="Extensions" type="StringList" >
+ <label>Optional Menus</label>
+ <default>prefmenu.desktop,systemmenu.desktop</default>
+ </entry>
+
+<entry name="RecentAppsStat" type="StringList" >
+ <label>Recently used applications</label>
+ </entry>
+
+<entry name="NumVisibleEntries" type="UInt" >
+ <label>Number of visible entries</label>
+ <default>5</default>
+ <max>100</max>
+ </entry>
+
+<entry name="RecentVsOften" type="Bool" >
+ <label>Show most recently used applications rather than most frequently used</label>
+ <default>false</default>
+ </entry>
+
+<entry name="Favorites" type="StringList">
+ <label>The menu entries shown in the Favorites tab</label>
+ </entry>
+
+<entry name="FirstRun" type="Bool" >
+ <label>Whether the panel has been started before or not</label>
+ <default>false</default>
+ </entry>
+
+<entry name="FirstSeenApps" type="StringList">
+ <label>When the applications were first seen by Kickoff</label>
+ </entry>
+
+</group>
+
+<group name="button_tiles">
+
+<entry name="EnableKMenuTiles" type="Bool">
+ <label>Enable a tile background image for the KMenu button</label>
+ <default>false</default>
+ </entry>
+
+<entry name="EnableDesktopButtonTiles" type="Bool">
+ <label>Enable a tile background image for the Desktop button</label>
+ <default>false</default>
+ </entry>
+
+<entry name="EnableURLTiles" type="Bool" >
+ <label>Enable a tile background image for Application, URL and special buttons</label>
+ <default>false</default>
+ </entry>
+
+<entry name="EnableBrowserTiles" type="Bool" >
+ <label>Enable a tile background image for the Quick Browser button</label>
+ <default>false</default>
+ </entry>
+
+<entry name="EnableWindowListTiles" type="Bool" >
+ <label>Enable a tile background image for the Window List button</label>
+ <default>false</default>
+ </entry>
+
+<entry name="KMenuTile" type="Path" >
+ <label>Image tile for Kmenu button background</label>
+ </entry>
+
+<entry name="KMenuTileColor" type="Color" >
+ <label>Color to use for Kmenu button background</label>
+ <default code="true">QColor()</default>
+ </entry>
+
+<entry name="DesktopButtonTile" type="Path" >
+ <label>Image tile for Desktop button background</label>
+ </entry>
+
+<entry name="DesktopButtonTileColor" type="Color" >
+ <label>Color to use for Kmenu button background</label>
+ <default code="true">QColor()</default>
+ </entry>
+
+<entry name="URLTile" type="Path" >
+ <label>Image tile for Application, URL and special button backgrounds</label>
+ </entry>
+
+<entry name="URLTileColor" type="Color" >
+ <label>Color to use for Application, URL and special button backgrounds</label>
+ <default code="true">QColor()</default>
+ </entry>
+
+<entry name="BrowserTile" type="Path" >
+ <label>Image tile for Browser button background</label>
+ </entry>
+
+<entry name="BrowserTileColor" type="Color" >
+ <label>Color to use for Browser button background</label>
+ <default code="true">QColor()</default>
+ </entry>
+
+<entry name="WindowListTile" type="Path" >
+ <label>Image tile for Window List button background</label>
+ </entry>
+
+<entry name="WindowListTileColor" type="Color" >
+ <label>Color to use for Window List button background</label>
+ <default code="true">QColor()</default>
+ </entry>
+
+</group>
+
+<group name="KMenu" >
+
+ <entry name="UseSidePixmap" type="Bool" >
+ <label>Use side image in Kmenu</label>
+ <default>true</default>
+ </entry>
+
+ <entry name="UseTooltip" type="Bool" >
+ <label>Use Tooltip in Kmenu</label>
+ <default>false</default>
+ </entry>
+
+ <entry name="UseSearchBar" type="Bool" >
+ <label>Show searh field in Kmenu</label>
+ <default>true</default>
+ </entry>
+
+ <entry name="UseTopSide" type="Bool" >
+ <label>Use side image on top of Kmenu</label>
+ <default>false</default>
+ </entry>
+
+ <entry name="LeftSideTopPixmapName" key="LeftSideTopName" type="String" >
+ <label>The name of the file to use as the side image in the TDE Menu</label>
+ <default>kside_top_left.png</default>
+ </entry>
+
+ <entry name="RightSideTopPixmapName" key="RightSideTopName" type="String" >
+ <label>The name of the file to use as the side image in the TDE Menu</label>
+ <default>kside_top_right.png</default>
+ </entry>
+
+ <entry name="SideTopTileName" key="SideTopTileName" type="String" >
+ <label>The name of the file used as a tile to fill the height of TDE Menu that SidePixmapName does not cover</label>
+ <default>kside_top_tile.png</default>
+ </entry>
+
+ <entry name="SidePixmapName" key="SideName" type="String" >
+ <label>The name of the file to use as the side image in the TDE Menu</label>
+ <default>kside.png</default>
+ </entry>
+
+ <entry name="SideTileName" key="SideTileName" type="String" >
+ <label>The name of the file used as a tile to fill the height of TDE Menu that SidePixmapName does not cover</label>
+ <default>kside_tile.png</default>
+ </entry>
+
+ <entry name="ShowKMenuText" key="ShowText" type="Bool" >
+ <label>Show text on the TDE Menu button</label>
+ <default>false</default>
+ </entry>
+
+ <entry name="KMenuText" key="Text" type="String" >
+ <label>Text to be shown on TDE Menu Button</label>
+ <default code="true">i18n("Applications")</default>
+ </entry>
+
+ <entry name="CustomKMenuIcon" key="CustomIcon" type="Path" >
+ <label>Custom TDE Menu Button Icon</label>
+ <default code="true">QString("kmenu")</default>
+ </entry>
+
+</group>
+
+<group name="buttons" >
+
+<entry name="ShowMouseOverEffects" key="EnableIconZoom" type="Bool" >
+ <label>Enable icon mouse over effects</label>
+ <default>true</default>
+ </entry>
+
+<entry name="MouseOversShowIcon" type="Bool" >
+ <label>Show icons in mouse over effects</label>
+ <default>true</default>
+ </entry>
+
+<entry name="MouseOversShowText" type="Bool" >
+ <label>Show text in mouse over effects</label>
+ <default>true</default>
+ </entry>
+
+<entry name="MouseOversSpeed" type="Int" >
+ <label>Controls how fast the tooltips fade in, measured in thousandths of a second</label>
+ <default>500</default>
+ <min>0</min>
+ </entry>
+
+ <entry name="MouseOversShowDelay" type="UInt" >
+ <label>Mouse over effects are shown after the defined time (in milliseconds)</label>
+ <default>500</default>
+ </entry>
+
+ <entry name="MouseOversHideDelay" type="UInt" >
+ <label>Mouse over effects are hidden after the defined time (in milliseconds)</label>
+ <default>200</default>
+ </entry>
+
+<entry name="EnableTileBackground" type="Bool" >
+ <label>Enable background tiles</label>
+ <default>false</default>
+ </entry>
+
+<entry name="IconMargin" key="IconMargin" type="Int" >
+ <label>The margin between panel icons and the panel border</label>
+ <default>3</default>
+ </entry>
+
+<entry name="MaximumTDEMenuButtonHeight" key="MaximumTDEMenuButtonHeight" type="Int" >
+ <label>The maximum height of the TDE Menu button in pixels</label>
+ <default>30</default>
+ </entry>
+
+<entry name="RemoveButtonsWhenBroken" type="Bool" >
+ <label>Buttons that represent KServices (applications, primarily) watch for the removal of the service and delete themselves when this happens. This setting turns this off.</label>
+ <default>true</default>
+ </entry>
+
+<entry name="ButtonFont" key="Font" type="Font" >
+ <label>Font for the buttons with text.</label>
+ <default code="true">TDEGlobalSettings::generalFont()</default>
+ </entry>
+
+<entry name="ButtonTextColor" key="TextColor" type="Color" >
+ <label>Text color for the buttons.</label>
+ <default code="true">TDEGlobalSettings::textColor()</default>
+ </entry>
+
+</group>
+
+ <group name="SearchField">
+ <entry key="History" type="PathList">
+ <default></default>
+ <label></label>
+ <whatsthis></whatsthis>
+ </entry>
+ <entry key="HistoryLength" type="Int">
+ <default>50</default>
+ <label></label>
+ <whatsthis></whatsthis>
+ </entry>
+ <entry key="CompletionItems" type="PathList">
+ <default></default>
+ <label></label>
+ <whatsthis></whatsthis>
+ </entry>
+ <entry key="CompletionMode" type="Int">
+ <default>2</default>
+ <label></label>
+ <whatsthis></whatsthis>
+ </entry>
+ </group>
+
+</kcfg>
+
+
diff --git a/kicker/libkicker/kickerSettings.kcfgc b/kicker/libkicker/kickerSettings.kcfgc
new file mode 100644
index 000000000..8e0b42d93
--- /dev/null
+++ b/kicker/libkicker/kickerSettings.kcfgc
@@ -0,0 +1,8 @@
+File=kickerSettings.kcfg
+Singleton=true
+ClassName=KickerSettings
+Mutators=true
+Visibility=KDE_EXPORT
+IncludeFiles=tqapplication.h
+GlobalEnums=true
+MemberVariables=dpointer
diff --git a/kicker/libkicker/kickertip.cpp b/kicker/libkicker/kickertip.cpp
new file mode 100644
index 000000000..0a6000f37
--- /dev/null
+++ b/kicker/libkicker/kickertip.cpp
@@ -0,0 +1,568 @@
+/*****************************************************************
+
+Copyright (c) 2004 Zack Rusin <[email protected]>
+ Sami Kyostil <[email protected]>
+ Aaron J. Seigo <[email protected]>
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#include <tqapplication.h>
+#include <tqpainter.h>
+#include <tqsimplerichtext.h>
+#include <tqtimer.h>
+#include <tqtooltip.h>
+
+#include <kdialog.h>
+
+#include "global.h"
+
+#include "kickertip.h"
+#include "kickerSettings.h"
+
+// putting this #include higher results in compile errors
+#include <netwm.h>
+#include <assert.h>
+
+static const int DEFAULT_FRAMES_PER_SECOND = 30;
+
+KickerTip* KickerTip::m_self = 0;
+int KickerTip::m_tippingEnabled = 1;
+
+void KickerTip::Client::updateKickerTip() const
+{
+ if (KickerTip::the()->isTippingFor(dynamic_cast<const TQWidget*>(this)) &&
+ KickerTip::the()->isVisible())
+ {
+ KickerTip::the()->display();
+ }
+}
+
+KickerTip* KickerTip::the()
+{
+ if (!m_self)
+ {
+ m_self = new KickerTip(0);
+ }
+
+ return m_self;
+}
+
+KickerTip::KickerTip(TQWidget * parent)
+ : TQWidget(parent, "animtt",WX11BypassWM),
+ m_richText(0),
+ m_mimeFactory(0),
+ m_dissolveSize(0),
+ m_dissolveDelta(-1),
+ m_direction(KPanelApplet::Up),
+ m_dirty(false),
+ m_tippingFor(0),
+ m_timer(0, "KickerTip::m_timer"),
+ m_frameTimer(0, "KickerTip::m_frameTimer")
+{
+ setFocusPolicy(TQ_NoFocus);
+ setBackgroundMode(NoBackground);
+ resize(0, 0);
+ hide();
+ connect(&m_frameTimer, TQT_SIGNAL(timeout()), TQT_SLOT(internalUpdate()));
+// // FIXME: The settingsChanged(SettingsCategory) signal is not available under Trinity; where was it originally supposed to come from?
+// connect(kapp, TQT_SIGNAL(settingsChanged(SettingsCategory)), TQT_SLOT(slotSettingsChanged()));
+}
+
+KickerTip::~KickerTip()
+{
+ delete m_richText;
+ delete m_mimeFactory;
+}
+
+void KickerTip::slotSettingsChanged()
+{
+ TQToolTip::setGloballyEnabled(KickerSettings::showToolTips());
+}
+
+void KickerTip::display()
+{
+ if (!tippingEnabled())
+ {
+ return;
+ }
+
+ {
+ // prevent tips from showing when the active window is fullscreened
+ NETRootInfo ri(tqt_xdisplay(), NET::ActiveWindow);
+ NETWinInfo wi(tqt_xdisplay(), ri.activeWindow(), ri.rootWindow(), NET::WMState);
+ if (wi.state() & NET::FullScreen)
+ {
+ return;
+ }
+ }
+
+ TQWidget *widget = const_cast<TQWidget*>(m_tippingFor);
+ KickerTip::Client *client = dynamic_cast<KickerTip::Client*>(widget);
+
+ if (!client)
+ {
+ return;
+ }
+
+ // delete the mimefactory and create a new one so any old pixmaps used in the
+ // richtext area are freed but the mimefactory is ready to be added to in
+ // the call to updateKickerTip
+ delete m_mimeFactory;
+ m_mimeFactory = new TQMimeSourceFactory();
+
+ // Declare interchange object and define defaults.
+ Data data;
+ data.maskEffect = Dissolve;
+ data.duration = 2000;
+ data.direction = KPanelApplet::Up;
+ data.mimeFactory = m_mimeFactory;
+
+ // Tickle the information out of the bastard.
+ client->updateKickerTip(data);
+
+ // Hide the tip if there is nothing to show
+ if (data.message.isEmpty() && data.subtext.isEmpty() && data.icon.isNull())
+ {
+ hide();
+ return;
+ }
+
+ delete m_richText;
+ m_richText = new TQSimpleRichText("<qt><h3>" + data.message + "</h3><p>" +
+ data.subtext + "</p></qt>", font(), TQString(), 0,
+ m_mimeFactory);
+ m_richText->setWidth(640);
+ m_direction = data.direction;
+
+ if (KickerSettings::mouseOversShowIcon())
+ {
+ m_icon = data.icon;
+ }
+ else if (KickerSettings::mouseOversShowText())
+ {
+ m_icon = TQPixmap();
+ }
+ else
+ {
+ // don't bother since we have NOTHING to show
+ return;
+ }
+
+ m_maskEffect = isVisible() ? Plain : data.maskEffect;
+ m_dissolveSize = 24;
+ m_dissolveDelta = -1;
+
+ displayInternal();
+
+ m_frameTimer.start(1000 / DEFAULT_FRAMES_PER_SECOND);
+
+ // close the message window after given mS
+ if (data.duration > 0)
+ {
+ disconnect(&m_timer, TQT_SIGNAL(timeout()), 0, 0);
+ connect(&m_timer, TQT_SIGNAL(timeout()), TQT_SLOT(hide()));
+ m_timer.start(data.duration, true);
+ }
+ else
+ {
+ m_timer.stop();
+ }
+
+ move(KickerLib::popupPosition(m_direction, this, m_tippingFor));
+ show();
+}
+
+void KickerTip::paintEvent(TQPaintEvent * e)
+{
+ if (m_dirty)
+ {
+ displayInternal();
+ m_dirty = false;
+ }
+
+ TQPainter p(this);
+ p.drawPixmap(e->rect().topLeft(), m_pixmap, e->rect());
+}
+
+void KickerTip::mousePressEvent(TQMouseEvent * /*e*/)
+{
+ m_timer.stop();
+ hide();
+}
+
+static void drawRoundRect(TQPainter &p, const TQRect &r)
+{
+ static int line[8] = { 1, 3, 4, 5, 6, 7, 7, 8 };
+ static int border[8] = { 1, 2, 1, 1, 1, 1, 1, 1 };
+ int xl, xr, y1, y2;
+ TQPen pen = p.pen();
+ bool drawBorder = pen.style() != TQPen::NoPen;
+
+ if (r.width() < 16 || r.height() < 16)
+ {
+ p.drawRect(r);
+ return;
+ }
+
+ p.fillRect(r.x(), r.y() + 8, r.width(), r.height() - 16, p.brush());
+ p.fillRect(r.x() + 8, r.y(), r.width() - 16, r.height(), p.brush());
+
+ p.setPen(p.brush().color());
+
+ for (int i = 0; i < 8; i++)
+ {
+ xl = i;
+ xr = r.width() - i - 1;
+ y1 = 7;
+ y2 = 7 - (line[i] - 1);
+
+ p.drawLine(xl, y1, xl, y2);
+ p.drawLine(xr, y1, xr, y2);
+
+ y1 = r.height() - y1 - 1;
+ y2 = r.height() - y2 - 1;
+
+ p.drawLine(xl, y1, xl, y2);
+ p.drawLine(xr, y1, xr, y2);
+
+ }
+
+ if (drawBorder)
+ {
+ p.setPen(pen);
+
+ if (r.height() > 16)
+ {
+ p.drawLine(r.x(), r.y() + 8, r.x(), r.y() + r.height() - 9);
+ p.drawLine(r.x() + r.width() - 1, r.y() + 8, r.x() + r.width() - 1, r.y() + r.height() - 9);
+ }
+ if (r.width() > 16)
+ {
+ p.drawLine(r.x() + 8, r.y(), r.x() + r.width() - 9, r.y());
+ p.drawLine(r.x() + 8, r.y() + r.height() - 1, r.x() + r.width() - 9, r.y() + r.height() - 1);
+ }
+
+ for (int i = 0; i < 8; i++)
+ {
+ xl = i;
+ xr = r.width() - i - 1;
+ y2 = 7 - (line[i] - 1);
+ y1 = y2 + (border[i] - 1);
+
+ p.drawLine(xl, y1, xl, y2);
+ p.drawLine(xr, y1, xr, y2);
+
+ y1 = r.height() - y1 - 1;
+ y2 = r.height() - y2 - 1;
+
+ p.drawLine(xl, y1, xl, y2);
+ p.drawLine(xr, y1, xr, y2);
+
+ }
+ }
+}
+
+void KickerTip::plainMask()
+{
+ TQPainter maskPainter(&m_mask);
+
+ m_mask.fill(Qt::color0);
+
+ maskPainter.setBrush(Qt::color1);
+ maskPainter.setPen(Qt::NoPen);
+ //maskPainter.drawRoundRect(m_mask.rect(), 1600 / m_mask.rect().width(), 1600 / m_mask.rect().height());
+ drawRoundRect(maskPainter, m_mask.rect());
+ setMask(m_mask);
+ m_frameTimer.stop();
+}
+
+void KickerTip::dissolveMask()
+{
+ TQPainter maskPainter(&m_mask);
+
+ m_mask.fill(Qt::color0);
+
+ maskPainter.setBrush(Qt::color1);
+ maskPainter.setPen(Qt::NoPen);
+ //maskPainter.drawRoundRect(m_mask.rect(), 1600 / m_mask.rect().width(), 1600 / m_mask.rect().height());
+ drawRoundRect(maskPainter, m_mask.rect());
+
+ m_dissolveSize += m_dissolveDelta;
+
+ if (m_dissolveSize > 0)
+ {
+ maskPainter.setRasterOp(TQt::EraseROP);
+
+ int x, y, s;
+ const int size = 16;
+
+ for (y = 0; y < height() + size; y += size)
+ {
+ x = width();
+ s = 4 * m_dissolveSize * x / 128;
+ for (; x > -size; x -= size, s -= 2)
+ {
+ if (s < 0)
+ {
+ break;
+ }
+ maskPainter.drawEllipse(x - s / 2, y - s / 2, s, s);
+ }
+ }
+ }
+ else if (m_dissolveSize < 0)
+ {
+ m_frameTimer.stop();
+ m_dissolveDelta = 1;
+ }
+
+ setMask(m_mask);
+}
+
+void KickerTip::displayInternal()
+{
+ // we need to check for m_tippingFor here as well as m_richText
+ // since if one is really persistant and moves the mouse around very fast
+ // you can trigger a situation where m_tippingFor gets reset to 0 but
+ // before display() is called!
+ if (!m_tippingFor || !m_richText)
+ {
+ return;
+ }
+
+ // determine text rectangle
+ TQRect textRect(0, 0, 0, 0);
+ if (KickerSettings::mouseOversShowText())
+ {
+ textRect.setWidth(m_richText->widthUsed());
+ textRect.setHeight(m_richText->height());
+ }
+
+ int margin = KDialog::marginHint();
+ int height = TQMAX(m_icon.height(), textRect.height()) + 2 * margin;
+ int textX = m_icon.isNull() ? margin : 2 + m_icon.width() + 2 * margin;
+ int width = textX + textRect.width() + margin;
+ int textY = (height - textRect.height()) / 2;
+
+ // resize pixmap, mask and widget
+ bool firstTime = m_dissolveSize == 24;
+ if (firstTime)
+ {
+ m_mask.resize(width, height);
+ m_pixmap.resize(width, height);
+ resize(width, height);
+ if (isVisible())
+ {
+ // we've already been shown before, but we may grow larger.
+ // in the case of Up or Right displaying tips, this growth can
+ // result in the tip occluding the panel and causing it to redraw
+ // once we return back to display() causing horrid flicker
+ move(KickerLib::popupPosition(m_direction, this, m_tippingFor));
+ }
+ }
+
+ // create and set transparency mask
+ switch(m_maskEffect)
+ {
+ case Plain:
+ plainMask();
+ break;
+
+ case Dissolve:
+ dissolveMask();
+ break;
+ }
+
+ // draw background
+ TQPainter bufferPainter(&m_pixmap);
+ bufferPainter.setPen(colorGroup().foreground());
+ bufferPainter.setBrush(colorGroup().background());
+ //bufferPainter.drawRoundRect(0, 0, width, height, 1600 / width, 1600 / height);
+ drawRoundRect(bufferPainter, TQRect(0, 0, width, height));
+
+ // draw icon if present
+ if (!m_icon.isNull())
+ {
+ bufferPainter.drawPixmap(margin,
+ margin,
+ m_icon, 0, 0,
+ m_icon.width(), m_icon.height());
+ }
+
+ if (KickerSettings::mouseOversShowText())
+ {
+ // draw text shadow
+ TQColorGroup cg = colorGroup();
+ cg.setColor(TQColorGroup::Text, cg.background().dark(115));
+ int shadowOffset = TQApplication::reverseLayout() ? -1 : 1;
+ m_richText->draw(&bufferPainter, textX + shadowOffset, textY + 1, TQRect(), cg);
+
+ // draw text
+ cg = colorGroup();
+ m_richText->draw(&bufferPainter, textX, textY, rect(), cg);
+ }
+}
+
+void KickerTip::tipFor(const TQWidget* w)
+{
+ if (m_tippingFor)
+ {
+ disconnect(m_tippingFor, TQT_SIGNAL(destroyed(TQObject*)),
+ this, TQT_SLOT(tipperDestroyed(TQObject*)));
+ }
+
+ m_tippingFor = w;
+
+ if (m_tippingFor)
+ {
+ connect(m_tippingFor, TQT_SIGNAL(destroyed(TQObject*)),
+ this, TQT_SLOT(tipperDestroyed(TQObject*)));
+ }
+}
+
+void KickerTip::untipFor(const TQWidget* w)
+{
+ if (isTippingFor(w))
+ hide();
+}
+
+bool KickerTip::isTippingFor(const TQWidget* w) const
+{
+ return m_tippingFor == w;
+}
+
+void KickerTip::tipperDestroyed(TQObject* o)
+{
+ // we can't do a dynamic cast because we are in the process of dying
+ // so static it is.
+ untipFor(TQT_TQWIDGET(o));
+}
+
+void KickerTip::internalUpdate()
+{
+ m_dirty = true;
+ repaint(false);
+}
+
+void KickerTip::enableTipping(bool tip)
+{
+ if (tip)
+ {
+ m_tippingEnabled++;
+ }
+ else
+ {
+ m_tippingEnabled--;
+ }
+
+// assert(m_tippingEnabled >= -1);
+
+ if (m_tippingEnabled < 1 && m_self)
+ {
+ m_self->m_timer.stop();
+ m_self->hide();
+ }
+}
+
+bool KickerTip::tippingEnabled()
+{
+ return m_tippingEnabled > 0;
+}
+
+void KickerTip::hide()
+{
+ tipFor(0);
+ m_timer.stop();
+ m_frameTimer.stop();
+ TQWidget::hide();
+
+ TQToolTip::setGloballyEnabled(KickerSettings::showToolTips());
+}
+
+bool KickerTip::eventFilter(TQObject *object, TQEvent *event)
+{
+ if (!tippingEnabled())
+ {
+ return false;
+ }
+
+ if (!object->isWidgetType())
+ {
+ return false;
+ }
+
+ TQWidget *widget = TQT_TQWIDGET(object);
+
+ switch (event->type())
+ {
+ case TQEvent::Enter:
+ if (!KickerSettings::showMouseOverEffects())
+ {
+ return false;
+ }
+
+ if (!mouseGrabber() &&
+ !tqApp->activePopupWidget() &&
+ !isTippingFor(widget))
+ {
+ TQToolTip::setGloballyEnabled(false);
+
+ tipFor(widget);
+ m_timer.stop();
+ disconnect(&m_timer, TQT_SIGNAL(timeout()), 0, 0);
+ connect(&m_timer, TQT_SIGNAL(timeout()), TQT_SLOT(display()));
+
+ // delay to avoid false starts
+ // e.g. when the user quickly zooms their mouse over
+ // a button then out of kicker
+ if (isVisible())
+ {
+ m_timer.start(150, true);
+ }
+ else
+ {
+ m_timer.start(KickerSettings::mouseOversShowDelay(), true);
+ }
+ }
+ break;
+ case TQEvent::Leave:
+ m_timer.stop();
+
+ if (isTippingFor(widget) && isVisible())
+ {
+ disconnect(&m_timer, TQT_SIGNAL(timeout()), 0, 0);
+ connect(&m_timer, TQT_SIGNAL(timeout()), TQT_SLOT(hide()));
+ m_timer.start(KickerSettings::mouseOversHideDelay(), true);
+ }
+
+ tipFor(0);
+ break;
+ case TQEvent::MouseButtonPress:
+ m_timer.stop();
+ hide();
+ default:
+ break;
+ }
+
+ return false;
+}
+
+#include <kickertip.moc>
+
diff --git a/kicker/libkicker/kickertip.h b/kicker/libkicker/kickertip.h
new file mode 100644
index 000000000..b7332967f
--- /dev/null
+++ b/kicker/libkicker/kickertip.h
@@ -0,0 +1,121 @@
+/*****************************************************************
+
+Copyright (c) 2004 Zack Rusin <[email protected]>
+ Sami Kyostil <[email protected]>
+ Aaron J. Seigo <[email protected]>
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#ifndef KICKER_TIP_H
+#define KICKER_TIP_H
+
+#include <tqbitmap.h>
+#include <tqpixmap.h>
+#include <tqtimer.h>
+#include <tqwidget.h>
+
+#include <kpanelapplet.h>
+
+class TQMimeSourceFactory;
+class TQPaintEvent;
+class TQSimpleRichText;
+class TQTimer;
+
+class KDE_EXPORT KickerTip : public TQWidget
+{
+ Q_OBJECT
+
+public:
+ enum MaskEffect { Plain, Dissolve };
+
+ struct Data
+ {
+ TQString message;
+ TQString subtext;
+ TQPixmap icon;
+ KickerTip::MaskEffect maskEffect;
+ int duration;
+ KPanelApplet::Direction direction;
+
+ // do NOT delete this in the client!
+ TQMimeSourceFactory* mimeFactory;
+ };
+
+ class KDE_EXPORT Client
+ {
+ public:
+ virtual void updateKickerTip(KickerTip::Data&) = 0;
+ void updateKickerTip() const;
+ };
+
+ static KickerTip* the();
+ static void enableTipping(bool tip);
+ static bool tippingEnabled();
+
+ void untipFor(const TQWidget* w);
+ bool eventFilter(TQObject *o, TQEvent *e);
+
+protected:
+ KickerTip(TQWidget * parent);
+ ~KickerTip();
+
+ void paintEvent(TQPaintEvent * e);
+ void mousePressEvent(TQMouseEvent * e);
+
+ void plainMask();
+ void dissolveMask();
+
+ void displayInternal();
+ void hide();
+
+ void tipFor(const TQWidget* w);
+ bool isTippingFor(const TQWidget* w) const;
+
+protected slots:
+ void tipperDestroyed(TQObject* o);
+ void internalUpdate();
+ void display();
+ void slotSettingsChanged();
+
+private:
+ TQBitmap m_mask;
+ TQPixmap m_pixmap;
+ TQPixmap m_icon;
+ MaskEffect m_maskEffect;
+ TQSimpleRichText* m_richText;
+ TQMimeSourceFactory* m_mimeFactory;
+
+ int m_dissolveSize;
+ int m_dissolveDelta;
+ KPanelApplet::Direction m_direction;
+
+ TQTimer m_timer;
+ TQTimer m_frameTimer;
+ bool m_dirty;
+
+ const TQWidget* m_tippingFor;
+
+ static KickerTip* m_self;
+ static int m_tippingEnabled;
+
+ friend class KickerTip::Client;
+};
+
+#endif
diff --git a/kicker/libkicker/kshadowengine.cpp b/kicker/libkicker/kshadowengine.cpp
new file mode 100644
index 000000000..a933026d5
--- /dev/null
+++ b/kicker/libkicker/kshadowengine.cpp
@@ -0,0 +1,251 @@
+/* This file is proposed to be part of the KDE libraries.
+ * Copyright (C) 2003 Laur Ivan <[email protected]>
+ *
+ * Many thanks to:
+ * - Bernardo Hung <[email protected]> for the enhanced shadow
+ * algorithm (currently used)
+ * - Tim Jansen <[email protected]> for the API updates and fixes.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License version 2 as published by the Free Software Foundation.
+ *
+ * This library 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
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <tqcolor.h>
+#include <tqpainter.h>
+#include <tqbitmap.h>
+#include <tqpixmap.h>
+
+#include "kshadowsettings.h"
+#include "kshadowengine.h"
+
+KShadowEngine::KShadowEngine() :
+ m_shadowSettings( new KShadowSettings )
+{
+}
+
+KShadowEngine::~KShadowEngine()
+{
+ delete m_shadowSettings;
+}
+
+KShadowEngine::KShadowEngine(KShadowSettings *fx) :
+ m_shadowSettings(0L)
+{
+ setShadowSettings(fx);
+}
+
+
+void KShadowEngine::setShadowSettings(KShadowSettings *fx)
+{
+ delete m_shadowSettings;
+
+ m_shadowSettings = fx;
+}
+
+KShadowSettings *KShadowEngine::shadowSettings()
+{
+ return m_shadowSettings;
+}
+
+TQImage KShadowEngine::makeShadow(const TQPixmap& textPixmap, const TQColor &bgColor)
+{
+ TQImage result;
+
+ // create a new image for for the shaddow
+ int w = textPixmap.width();
+ int h = textPixmap.height();
+
+ // avoid calling these methods for every pixel
+ int bgRed = bgColor.red();
+ int bgGreen = bgColor.green();
+ int bgBlue = bgColor.blue();
+
+ int thick = m_shadowSettings->thickness() >> 1;
+
+ double alphaShadow;
+
+ /*
+ * This is the source pixmap
+ */
+ TQImage img = TQImage(textPixmap.convertToImage()).convertDepth(32);
+
+ /*
+ * Resize the image if necessary
+ */
+ if ((result.width() != w) || (result.height() != h))
+ {
+ result.create(w, h, 32);
+ }
+
+ result.fill(0); // all black
+ result.setAlphaBuffer(true);
+
+ for (int i = thick; i < w - thick; i++)
+ {
+ for (int j = thick; j < h - thick; j++)
+ {
+ switch (m_shadowSettings->algorithm())
+ {
+ case KShadowSettings::DoubleLinearDecay:
+ alphaShadow = doubleLinearDecay(img, i, j);
+ break;
+ case KShadowSettings::RadialDecay:
+ alphaShadow = radialDecay(img, i, j);
+ break;
+ case KShadowSettings::NoDecay:
+ alphaShadow = noDecay(img, i, j);
+ break;
+ case KShadowSettings::DefaultDecay:
+ default:
+ alphaShadow = defaultDecay(img, i, j);
+ }
+
+ alphaShadow = (alphaShadow > m_shadowSettings->maxOpacity()) ? m_shadowSettings->maxOpacity() : alphaShadow;
+
+ // update the shadow's i,j pixel.
+ result.setPixel(i,j, tqRgba(bgRed, bgGreen , bgBlue, (int) alphaShadow));
+ }
+ }
+ return result;
+}
+
+// Multiplication factor for pixels directly above, under, or next to the text
+#define AXIS_FACTOR 2.0
+// Multiplication factor for pixels diagonal to the text
+#define DIAGONAL_FACTOR 1.0
+
+double KShadowEngine::defaultDecay(TQImage& source, int i, int j)
+{
+ if ((i < 1) || (j < 1) || (i > source.width() - 2) || (j > source.height() - 2))
+ return 0;
+
+ double alphaShadow;
+ alphaShadow =(tqGray(source.pixel(i-1,j-1)) * DIAGONAL_FACTOR +
+ tqGray(source.pixel(i-1,j )) * AXIS_FACTOR +
+ tqGray(source.pixel(i-1,j+1)) * DIAGONAL_FACTOR +
+ tqGray(source.pixel(i ,j-1)) * AXIS_FACTOR +
+ 0 +
+ tqGray(source.pixel(i ,j+1)) * AXIS_FACTOR +
+ tqGray(source.pixel(i+1,j-1)) * DIAGONAL_FACTOR +
+ tqGray(source.pixel(i+1,j )) * AXIS_FACTOR +
+ tqGray(source.pixel(i+1,j+1)) * DIAGONAL_FACTOR) / m_shadowSettings->multiplicationFactor();
+
+ return alphaShadow;
+}
+
+double KShadowEngine::doubleLinearDecay(TQImage& source, int i, int j)
+{
+ //printf("img: %p, %d %d\n", (char *) &source, i, j);
+ return defaultDecay( source, i, j ); // for now
+}
+
+double KShadowEngine::radialDecay(TQImage& source, int i, int j)
+{
+ //printf("img: %p, %d %d\n", (char *) &source, i, j);
+ return defaultDecay( source, i, j ); // for now
+}
+
+double KShadowEngine::noDecay(TQImage& source, int i, int j)
+{
+ // create a new image for for the shaddow
+ int w = source.width();
+ int h = source.height();
+ int sx, sy;
+ //int thick = m_shadowSettings->thickness() >> 1;
+
+ double alphaShadow = 0;
+ double opacity = 0;
+ for (int k = 1; k <= m_shadowSettings->thickness(); k++) {
+ /* Generate a shadow THICKNESS pixels thicker
+ * on either side than the text image. Ensure
+ * that i +/- k and j +/- k are within the
+ * bounds of the text pixmap.
+ */
+ opacity = 0;
+ for (int l = -k; l <= k; l++) {
+ if (i < k)
+ sx = 0;
+ else if (i >= w - k)
+ sx = w - 1;
+ else
+ sx = i + l;
+
+ for (int m = -k; m <= k; m++) {
+ if (j < k)
+ sy = 0;
+ else if (j >= h - k)
+ sy = h - 1;
+ else
+ sy = j + m;
+
+ opacity += tqGray(source.pixel(sx, sy));
+ }
+ }
+ alphaShadow += opacity / m_shadowSettings->multiplicationFactor();
+ }
+ return alphaShadow;
+}
+
+KTextShadowEngine::KTextShadowEngine() : KShadowEngine()
+{
+ KShadowSettings *shadset = new KShadowSettings();
+
+ shadset->setOffsetX(0);
+ shadset->setOffsetY(0);
+ shadset->setThickness(1);
+ shadset->setMaxOpacity(96);
+
+ setShadowSettings(shadset);
+}
+
+// taken from mtaskbar, by Sebastian Wolff
+void KTextShadowEngine::drawText(TQPainter &p, const TQRect &tr, int tf, const TQString &str, const TQSize &size)
+{
+ // get the color of the shadow: white for dark text, black for bright text
+ TQPen textPen = p.pen();
+ TQColor shadCol = textPen.color();
+
+ if (shadCol.red() +
+ shadCol.green() +
+ shadCol.blue() <= 3*256/2-1)
+ {
+ shadCol = TQColor(255,255,255);
+ }
+ else
+ {
+ shadCol = TQColor(0,0,0);
+ }
+
+ // get a transparent pixmap
+ TQPainter pixPainter;
+ TQPixmap textPixmap(size);
+
+ textPixmap.fill(TQColor(0,0,0));
+ textPixmap.setMask(textPixmap.createHeuristicMask(true));
+
+ // draw text
+ pixPainter.begin(&textPixmap);
+ pixPainter.setPen(Qt::white);
+ pixPainter.setFont(p.font()); // get the font from the root painter
+ pixPainter.drawText(tr, tf, str);
+ pixPainter.end();
+
+ // draw shadow
+ TQImage img = makeShadow(textPixmap, shadCol);
+
+ // return
+ p.drawImage(0, 0, img);
+ p.drawText(tr, tf, str);
+}
+
diff --git a/kicker/libkicker/kshadowengine.h b/kicker/libkicker/kshadowengine.h
new file mode 100644
index 000000000..1ddc093ff
--- /dev/null
+++ b/kicker/libkicker/kshadowengine.h
@@ -0,0 +1,123 @@
+/* This file is proposed to be part of the KDE libraries.
+ * Copyright (C) 2003 Laur Ivan <[email protected]>
+ *
+ * Many thanks to:
+ * - Bernardo Hung <[email protected]> for the enhanced shadow
+ * algorithm (currently used)
+ * - Tim Jansen <[email protected]> for the API updates and fixes.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License version 2 as published by the Free Software Foundation.
+ *
+ * This library 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
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#ifndef __FX_SHADOW
+#define __FX_SHADOW
+
+#include <tqpixmap.h>
+#include <tqimage.h>
+#include <tqcolor.h>
+
+#include <kdemacros.h>
+
+class KShadowSettings;
+
+/**
+ * This class implements the shadow algorithm(s). It uses a FxData
+ * object for its parameters. Note that the shadow algorithm is using the
+ * luminosity of the original pixmap for the shadow one.
+ * @see KShadowSettings
+ * @author [email protected]
+ * @since 3.2
+ */
+class KDE_EXPORT KShadowEngine
+{
+public:
+ /// Creates a new shadow engine.
+ KShadowEngine();
+
+ ~KShadowEngine();
+
+ /**
+ * Creates a new shadow engine.
+ * @param fx the shadow settings object with the configuration. The Shadow
+ * Engine will own this object and also delete it. Must
+ * be heap-allocated
+ */
+ KShadowEngine(KShadowSettings *fx);
+
+ /**
+ * Set the KShadowSettings object.
+ * @param fx the shadow settings object with the configuration. The Shadow
+ * Engine will own this object and also delete it. Must
+ * be heap-allocated.
+ */
+ void setShadowSettings(KShadowSettings *fx);
+
+ /**
+ * Get the current KShadowSettings.
+ * @param the current shadow settings
+ */
+ KShadowSettings *shadowSettings();
+
+ /**
+ * Make shadow!
+ *
+ * textPixmap is the original pixmap where a (white) text is drawn.
+ * bgColor is the color used for the shadow.
+ * @param textPixmap the pixmap of the text
+ * @param bgColor the background color
+ * @return the resulting image
+ */
+ TQImage makeShadow(const TQPixmap& textPixmap, const TQColor &bgColor);
+
+private:
+ // No static objects in libs, and no static deleters in tdefx...
+ //static KShadowSettings s_defaultShadowSettings;
+
+ KShadowSettings *m_shadowSettings;
+
+ /*
+ * a simple algorithm with 3 pixels thickness
+ */
+ double defaultDecay(TQImage& source, int x, int y);
+
+ /*
+ * a slower algorithm where the influence of a pixel
+ * is tqGray(px)/(abs(dx) + abs(dy) +1).
+ */
+ double doubleLinearDecay(TQImage& source, int x, int y);
+
+ /*
+ * a very slow algorithm where the influence of a pixel
+ * is tqGray(px)/(sqrt(sqr(dx) + sqr(dy)) +1).
+ */
+ double radialDecay(TQImage& source, int x, int y);
+
+ /*
+ * a nice/fast algorithm proposed by Bernardo Hung
+ */
+ double noDecay(TQImage& source, int x, int y);
+
+ void *d;
+};
+
+class KDE_EXPORT KTextShadowEngine : public KShadowEngine
+{
+public:
+ KTextShadowEngine();
+
+ void drawText(TQPainter &p, const TQRect &tr, int tf, const TQString &str, const TQSize &size);
+};
+
+#endif
diff --git a/kicker/libkicker/kshadowsettings.cpp b/kicker/libkicker/kshadowsettings.cpp
new file mode 100644
index 000000000..4d6bce5c3
--- /dev/null
+++ b/kicker/libkicker/kshadowsettings.cpp
@@ -0,0 +1,182 @@
+/* This file is proposed to be part of the KDE libraries.
+ * Copyright (C) 2003 Laur Ivan <[email protected]>
+ *
+ * Many thanks to:
+ * - Tim Jansen <[email protected]> for the API updates and fixes.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License version 2 as published by the Free Software Foundation.
+ *
+ * This library 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
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#include <tqstring.h>
+#include <tqstringlist.h>
+#include "kshadowsettings.h"
+
+KShadowSettings::KShadowSettings()
+{
+ // init the components with some default values
+ setDefaults();
+}
+
+// load/save methods
+void KShadowSettings::fromString(const TQString &val)
+{
+ setOffsetX(val.section(',', OFFSET_X, OFFSET_X).toInt());
+ setOffsetY(val.section(',', OFFSET_Y, OFFSET_Y).toInt());
+ setMultiplicationFactor(val.section(',', MULTIPLICATION_FACTOR, MULTIPLICATION_FACTOR).toDouble());
+ setMaxOpacity(val.section(',', MAX_OPACITY, MAX_OPACITY).toDouble());
+ setThickness(val.section(',', THICKNESS, THICKNESS).toInt());
+ setAlgorithm((Algorithm) val.section(',', ALGORITHM, ALGORITHM).toInt());
+ setSelectionType((SelectionType)val.section(',', SELECTION_TYPE, SELECTION_TYPE).toInt());
+}
+
+TQString KShadowSettings::toString() const
+{
+ TQString result;
+ result.sprintf("%d,%d,%f,%f,%d,%d,%d",
+ offsetX(),
+ offsetY(),
+ multiplicationFactor(),
+ maxOpacity(),
+ thickness(),
+ (int)algorithm(),
+ (int)selectionType());
+ return result;
+}
+
+//***********************************
+// get methods
+//***********************************
+
+/**
+ * Returns the decay algorithm to be used (see the alg. enumeration in the .h)
+ */
+KShadowSettings::Algorithm KShadowSettings::algorithm() const
+{
+ return _algorithm;
+}
+
+/**
+ * Returns a multiplication facor used to average the resulted data
+ */
+double KShadowSettings::multiplicationFactor() const
+{
+ return _multiplicationFactor;
+}
+
+/**
+ * Returns the max opacity allowed (0 = transparent, 255 = opaque)
+ */
+double KShadowSettings::maxOpacity() const
+{
+ return _maxOpacity;
+}
+
+/**
+ * Returns the Y offset (0 is centered on text)
+ */
+int KShadowSettings::offsetX() const
+{
+ return _offsetX;
+}
+
+/**
+ * Returns the Y offset (0 is centered on text)
+ */
+int KShadowSettings::offsetY() const
+{
+ return _offsetY;
+}
+
+/**
+ * Returns the thickness. Used by the KShadow algorithm
+ */
+int KShadowSettings::thickness() const
+{
+ return _thickness;
+}
+
+/**
+ * Returns the selection type
+ */
+KShadowSettings::SelectionType KShadowSettings::selectionType() const
+{
+ return _selectionType;
+}
+
+// set methods
+/**
+ * set the default parameters
+ */
+void KShadowSettings::setDefaults()
+{
+ fromString(DEFAULT_SHADOW_CONFIGURATION);
+}
+
+
+/**
+ * Set the algorithm
+ */
+void KShadowSettings::setAlgorithm(Algorithm val)
+{
+ _algorithm = val;
+}
+
+/**
+ * Set the multiplication factor
+ */
+void KShadowSettings::setMultiplicationFactor(double val)
+{
+ _multiplicationFactor = val;
+}
+
+/**
+ * Set the max. opacity
+ */
+void KShadowSettings::setMaxOpacity(double val)
+{
+ _maxOpacity = val;
+}
+
+/**
+ * Set the X offset of the shadow
+ */
+void KShadowSettings::setOffsetX(int val)
+{
+ _offsetX = val;
+}
+
+/**
+ * Set the Y offset of the shadow
+ */
+void KShadowSettings::setOffsetY(int val)
+{
+ _offsetY = val;
+}
+
+/**
+ * Set the shadow thickness
+ */
+void KShadowSettings::setThickness(int val)
+{
+ _thickness = val;
+}
+
+/**
+ * Set the selection type
+ */
+void KShadowSettings::setSelectionType(SelectionType val)
+{
+ _selectionType = val;
+}
diff --git a/kicker/libkicker/kshadowsettings.h b/kicker/libkicker/kshadowsettings.h
new file mode 100644
index 000000000..e222b964d
--- /dev/null
+++ b/kicker/libkicker/kshadowsettings.h
@@ -0,0 +1,236 @@
+/* This file is proposed to be part of the KDE libraries.
+ * Copyright (C) 2003 Laur Ivan <[email protected]>
+ *
+ * Many thanks to:
+ * - Tim Jansen <[email protected]> for the API updates and fixes.
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License version 2 as published by the Free Software Foundation.
+ *
+ * This library 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
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+ */
+
+#ifndef __FX_DATA
+#define __FX_DATA
+
+#include <kdemacros.h>
+
+#define SHADOW_CONFIG_ENTRY TQString("ShadowParameters")
+#define SHADOW_TEXT_COLOR TQString("ShadowTextColor")
+#define SHADOW_TEXT_BACKGROUND TQString("ShadowTextBackground")
+
+// fallback configuration string
+#define DEFAULT_SHADOW_CONFIGURATION TQString("0,0,4.0,120.0,2,1,1,0,0,0")
+
+/**
+ * This class is the implementation of a structure for the
+ * various parameters required by the shadow class.
+ *
+ * One may afford this implementation since the shadow class is
+ * designed to be used as singleton for an application.
+ * @see KShadowEngine
+ * @author [email protected]
+ * @since 3.2
+ */
+class KDE_EXPORT KShadowSettings
+{
+ public:
+ /**
+ * Specifies the order of the options.
+ * @see fromString
+ */
+ enum ConfigurationOrder
+ {
+ OFFSET_X = 0,
+ OFFSET_Y = OFFSET_X + 1,
+ MULTIPLICATION_FACTOR = OFFSET_Y + 1,
+ MAX_OPACITY = MULTIPLICATION_FACTOR + 1,
+ THICKNESS = MAX_OPACITY + 1,
+ ALGORITHM = THICKNESS + 1,
+ SELECTION_TYPE = ALGORITHM + 1
+ };
+
+ public:
+ /**
+ * The algorithm used.
+ */
+ enum Algorithm
+ {
+ DefaultDecay = 1, ///< the default AXIS/DIAGONAL_FACTOR based alg
+ DoubleLinearDecay, ///< decay factor is 1/dx+dy
+ RadialDecay, ///< decay factor is 1/sqrt(dx*dx + dy*dy)
+ NoDecay ///< decay factor is 1 always
+ };
+
+ /**
+ * The selected method used.
+ */
+ enum SelectionType
+ {
+ InverseVideoOnSelection = 0, ///< when selected, the halo is on I/Video
+ SelectionColorsOnSelection ///< the halo is made w/ selected colors
+ };
+
+ /**
+ * The default constructor.
+ * Creates an object with default settings for all the variabless.
+ */
+ KShadowSettings();
+
+ // load/save methods
+ /**
+ * Loads the configuration from a string.
+ * @param the string to load from (comma-separated values)
+ * @see ConfigurationOrder
+ */
+ virtual void fromString(const TQString &s);
+ /**
+ * Saves the configuration to a string.
+ * @return the configuration (comma-separated values)
+ * @see ConfigurationOrder
+ */
+ virtual TQString toString() const;
+
+ // get methods
+ /**
+ * Returns the x offset of the shadow.
+ * @return the x offset
+ */
+ int offsetX() const;
+
+ /**
+ * Returns the y offset of the shadow.
+ * @return the y offset
+ */
+ int offsetY() const;
+
+ /**
+ * Returns the multiplication factor.
+ * @return the multiplication factor
+ */
+ double multiplicationFactor() const;
+
+ /**
+ * Returns the maximum opacity of the shadow.
+ * @return the maximum opacity
+ */
+ double maxOpacity() const;
+
+ /**
+ * Returns the thickness.
+ * @return the thickness
+ */
+ int thickness() const;
+
+ /**
+ * Returns the used algorithm.
+ * @return the algorithm used
+ */
+ Algorithm algorithm() const;
+
+ /**
+ * Returns the selection type used.
+ * @return the selection type
+ */
+ SelectionType selectionType() const;
+
+ // set methods
+ /**
+ * Sets default values.
+ */
+ virtual void setDefaults();
+
+ /**
+ * Sets the used algorithm.
+ * @param a the algorithm used
+ */
+ virtual void setAlgorithm(Algorithm a);
+
+ /**
+ * Sets the multiplication factor.
+ * @param mf the multiplication factor
+ */
+ virtual void setMultiplicationFactor(double mf);
+
+ /**
+ * Sets the maximum opacity of the shadow.
+ * @param mo the maximum opacity
+ */
+ virtual void setMaxOpacity(double mo);
+
+ /**
+ * Sets the x offset of the shadow.
+ * @param x the x offset
+ */
+ virtual void setOffsetX(int x);
+
+ /**
+ * Sets the y offset of the shadow.
+ * @param y the y offset
+ */
+ virtual void setOffsetY(int y);
+
+ /**
+ * Sets the thickness.
+ * @param t the thickness
+ */
+ virtual void setThickness(int t);
+
+ /**
+ * Sets the selection type used.
+ * @param s the selection type
+ */
+ virtual void setSelectionType(SelectionType s);
+
+ private:
+
+ /*
+ * The employed algorithm (see fxshadow.h)
+ */
+ Algorithm _algorithm;
+
+ /**
+ * This is the multiplication factor for the resulted shadow
+ */
+ double _multiplicationFactor;
+
+ /**
+ * The maximum permitted opacity for the shadow
+ */
+ double _maxOpacity;
+
+ /*
+ * offsetX and offsetY are the x/y offsets of the shadow with
+ * the mention that 0,0 is a centered shadow.
+ */
+ int _offsetX;
+ int _offsetY;
+
+ /*
+ * The shadow thickness:
+ * shadow is this many pixels thicker than the text.
+ */
+ int _thickness;
+
+ /*
+ * If the value is InverseVideoOnSelection, then the fg/bg
+ * colours are swapped when the element is selected.
+ * Otherwise, the selected fg/bg colors are used for text
+ * as well
+ */
+ SelectionType _selectionType;
+
+ void *d;
+};
+
+
+#endif
diff --git a/kicker/libkicker/menuinfo.cpp b/kicker/libkicker/menuinfo.cpp
new file mode 100644
index 000000000..a8e4bf1fa
--- /dev/null
+++ b/kicker/libkicker/menuinfo.cpp
@@ -0,0 +1,68 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#include "menuinfo.h"
+
+#include <tqfile.h>
+#include <tqwidget.h>
+
+#include <tdeapplication.h>
+#include <ksimpleconfig.h>
+#include <klibloader.h>
+#include <kstandarddirs.h>
+#include <kpanelmenu.h>
+#include <tdeparts/componentfactory.h>
+
+MenuInfo::MenuInfo(const TQString& desktopFile)
+{
+ KSimpleConfig df(locate("data", TQString::fromLatin1("kicker/menuext/%1").arg(desktopFile)));
+ df.setGroup("Desktop Entry");
+
+ TQStringList list = df.readListEntry("X-TDE-AuthorizeAction");
+ if (kapp && !list.isEmpty())
+ {
+ for(TQStringList::ConstIterator it = list.begin();
+ it != list.end();
+ ++it)
+ {
+ if (!kapp->authorize((*it).stripWhiteSpace()))
+ return;
+ }
+ }
+
+ name_ = df.readEntry("Name");
+ comment_ = df.readEntry("Comment");
+ icon_ = df.readEntry("Icon");
+ library_ = df.readEntry("X-TDE-Library");
+ desktopfile_ = desktopFile;
+}
+
+KPanelMenu* MenuInfo::load(TQWidget *parent, const char *name)
+{
+ if (library_.isEmpty())
+ return 0;
+
+ return KParts::ComponentFactory::createInstanceFromLibrary<KPanelMenu>(
+ TQFile::encodeName( library_ ),
+ TQT_TQOBJECT(parent), name );
+}
diff --git a/kicker/libkicker/menuinfo.h b/kicker/libkicker/menuinfo.h
new file mode 100644
index 000000000..5925d4826
--- /dev/null
+++ b/kicker/libkicker/menuinfo.h
@@ -0,0 +1,52 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#ifndef _menuinfo_h_
+#define _menuinfo_h_
+
+#include <tqstring.h>
+
+#include <kdemacros.h>
+
+class KPanelMenu;
+class TQWidget;
+
+class KDE_EXPORT MenuInfo
+{
+public:
+ MenuInfo(const TQString& desktopFile);
+
+ TQString name() const { return name_; }
+ TQString comment() const { return comment_; }
+ TQString icon() const { return icon_; }
+ TQString library() const { return library_; }
+ TQString desktopFile() const { return desktopfile_; }
+ bool isValid() const { return !name_.isEmpty(); }
+
+ KPanelMenu* load(TQWidget *parent = 0, const char *name = 0);
+
+private:
+ TQString name_, comment_, icon_, library_, desktopfile_;
+};
+
+#endif
diff --git a/kicker/libkicker/panelbutton.cpp b/kicker/libkicker/panelbutton.cpp
new file mode 100644
index 000000000..aaac124c2
--- /dev/null
+++ b/kicker/libkicker/panelbutton.cpp
@@ -0,0 +1,1103 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#undef None // Qt4
+#include <tqcursor.h>
+#include <tqfile.h>
+#include <tqfontmetrics.h>
+#include <tqpainter.h>
+#include <tqpopupmenu.h>
+#include <tqstyle.h>
+#include <tqstylesheet.h>
+#include <tqtooltip.h>
+#include <tqpixmap.h>
+
+#include <tdeapplication.h>
+#include <tdeconfig.h>
+#include <kcursor.h>
+#include <kdialog.h>
+#include <kdirwatch.h>
+#include <tdeglobal.h>
+#include <tdeglobalsettings.h>
+#include <kiconloader.h>
+#include <kicontheme.h>
+#include <kiconeffect.h>
+#include <kipc.h>
+#include <kstandarddirs.h>
+#include <tdelocale.h>
+#include <kdebug.h>
+
+#include "global.h"
+
+#include "kshadowengine.h"
+#include "kshadowsettings.h"
+
+#include "kickerSettings.h"
+#include "panelbutton.h"
+#include "panelbutton.moc"
+
+// For now link these two
+#define m_disableHighlighting m_forceStandardCursor
+
+// init static variable
+KShadowEngine* PanelButton::s_textShadowEngine = 0L;
+
+PanelButton::PanelButton( TQWidget* parent, const char* name, bool forceStandardCursor )
+ : TQButton(parent, name),
+ m_valid(true),
+ m_isLeftMouseButtonDown(false),
+ m_drawArrow(false),
+ m_highlight(false),
+ m_changeCursorOverItem(forceStandardCursor?false:true),
+ m_hasAcceptedDrag(false),
+ m_centerInContainer(true),
+ m_arrowDirection(KPanelExtension::Bottom),
+ m_popupDirection(KPanelApplet::Up),
+ m_iconAlignment(AlignCenter),
+ m_orientation(Qt::Horizontal),
+ m_size((TDEIcon::StdSizes)-1),
+ m_fontPercent(0.40),
+ m_forceStandardCursor(forceStandardCursor)
+{
+ setBackgroundOrigin(AncestorOrigin);
+ setWFlags(TQt::WNoAutoErase);
+ TDEGlobal::locale()->insertCatalogue("libkicker");
+ calculateIconSize();
+ setAcceptDrops(true);
+
+ m_textColor = TDEGlobalSettings::textColor();
+
+ updateSettings(TDEApplication::SETTINGS_MOUSE);
+
+ kapp->addKipcEventMask(KIPC::SettingsChanged | KIPC::IconChanged);
+
+ installEventFilter(KickerTip::the());
+
+ connect(kapp, TQT_SIGNAL(settingsChanged(int)), TQT_SLOT(updateSettings(int)));
+ connect(kapp, TQT_SIGNAL(iconChanged(int)), TQT_SLOT(updateIcon(int)));
+}
+
+void PanelButton::configure()
+{
+ TQString name = tileName();
+ if( name.isEmpty() )
+ return;
+
+ if (!KickerSettings::enableTileBackground())
+ {
+ setTile(TQString::null);
+ return;
+ }
+
+ TDEConfigGroup tilesGroup( TDEGlobal::config(), "button_tiles" );
+ if( !tilesGroup.readBoolEntry( "Enable" + name + "Tiles", true ) ) {
+ setTile( TQString::null );
+ return;
+ }
+
+ TQString tile = tilesGroup.readEntry( name + "Tile" );
+ TQColor color = TQColor();
+
+ if (tile == "Colorize")
+ {
+ color = tilesGroup.readColorEntry( name + "TileColor" );
+ tile = TQString::null;
+ }
+
+ setTile( tile, color );
+}
+
+void PanelButton::setTile(const TQString& tile, const TQColor& color)
+{
+ if (tile == m_tile && m_tileColor == color)
+ {
+ return;
+ }
+
+ m_tile = tile;
+ m_tileColor = color;
+ loadTiles();
+ update();
+}
+
+void PanelButton::setDrawArrow(bool drawArrow)
+{
+ if (m_drawArrow == drawArrow)
+ {
+ return;
+ }
+
+ m_drawArrow = drawArrow;
+ update();
+}
+
+TQImage PanelButton::loadTile(const TQString& tile,
+ const TQSize& size,
+ const TQString& state)
+{
+ TQString name = tile;
+
+ if (size.height() < 42)
+ {
+ name += "_tiny_";
+ }
+ else if (size.height() < 54)
+ {
+ name += "_normal_";
+ }
+ else
+ {
+ name += "_large_";
+ }
+
+ name += state + ".png";
+
+ TQImage tileImg(TDEGlobal::dirs()->findResource("tiles", name));
+
+ // scale if size does not match exactly
+ if (!tileImg.isNull() && tileImg.size() != size)
+ {
+ tileImg = tileImg.smoothScale(size);
+ }
+
+ return tileImg;
+}
+
+void PanelButton::setEnabled(bool enable)
+{
+ TQButton::setEnabled(enable);
+ loadIcons();
+ update();
+}
+
+void PanelButton::setPopupDirection(KPanelApplet::Direction d)
+{
+ m_popupDirection = d;
+ setArrowDirection(KickerLib::directionToPopupPosition(d));
+}
+
+void PanelButton::setIconAlignment(TQ_Alignment align)
+{
+ m_iconAlignment = align;
+ update();
+}
+
+void PanelButton::setOrientation(Orientation o)
+{
+ m_orientation = o;
+}
+
+void PanelButton::updateIcon(int group)
+{
+ if (group != TDEIcon::Panel)
+ {
+ return;
+ }
+
+ loadIcons();
+ update();
+}
+
+void PanelButton::updateSettings(int category)
+{
+ if (category != TDEApplication::SETTINGS_MOUSE)
+ {
+ return;
+ }
+
+ if (m_forceStandardCursor == FALSE)
+ m_changeCursorOverItem = TDEGlobalSettings::changeCursorOverIcon();
+ else
+ m_changeCursorOverItem = FALSE;
+
+ if (m_changeCursorOverItem)
+ {
+ setCursor(KCursor::handCursor());
+ }
+ else
+ {
+ unsetCursor();
+ }
+}
+
+void PanelButton::checkForDeletion(const TQString& path)
+{
+ if (path == m_backingFile)
+ {
+ setEnabled(false);
+ TQTimer::singleShot(1000, this, TQT_SLOT(scheduleForRemoval()));
+ }
+}
+
+bool PanelButton::checkForBackingFile()
+{
+ return TQFile::exists(m_backingFile);
+}
+
+void PanelButton::scheduleForRemoval()
+{
+ static int timelapse = 1000;
+ if (checkForBackingFile())
+ {
+ setEnabled(true);
+ timelapse = 1000;
+ emit hideme(false);
+ return;
+ }
+ else if (KickerSettings::removeButtonsWhenBroken())
+ {
+ if (timelapse > 255*1000) // we'v given it ~8.5 minutes by this point
+ {
+ emit removeme();
+ return;
+ }
+
+ if (timelapse > 3000 && isVisible())
+ {
+ emit hideme(true);
+ }
+
+ timelapse *= 2;
+ TQTimer::singleShot(timelapse, this, TQT_SLOT(scheduleForRemoval()));
+ }
+}
+
+// return the dimension that the button wants to be for a given panel dimension (panelDim)
+int PanelButton::preferredDimension(int panelDim) const
+{
+ // determine the upper limit on the size. Normally, this is panelDim,
+ // but if conserveSpace() is true, we restrict size to comfortably fit the icon
+ if (KickerSettings::conserveSpace())
+ {
+ int newSize = preferredIconSize(panelDim);
+ if (newSize > 0)
+ {
+ return TQMIN(panelDim, newSize + (KDialog::spacingHint() * 2));
+ }
+ }
+
+ return panelDim;
+}
+
+int PanelButton::widthForHeight(int height) const
+{
+ int rc = preferredDimension(height);
+
+ // we only paint the text when horizontal, so make sure we're horizontal
+ // before adding the text in here
+ if (orientation() == Qt::Horizontal && !m_buttonText.isEmpty())
+ {
+ TQFont f(font());
+ //f.setPixelSize(KMIN(height, KMAX(int(float(height) * m_fontPercent), 16)));
+ TQFontMetrics fm(f);
+
+ rc += fm.width(m_buttonText) + ((KMIN(25, KMAX(5, fm.width('m') / 2)))/2);
+ //rc += fm.width(m_buttonText);
+ }
+
+ return rc;
+}
+
+int PanelButton::heightForWidth(int width) const
+{
+ int rc=preferredDimension(width);
+
+ return rc;
+}
+
+const TQPixmap& PanelButton::labelIcon() const
+{
+ if (m_disableHighlighting || (!KickerSettings::showMouseOverEffects()))
+ return m_icon;
+ else
+ return m_highlight ? m_iconh : m_icon;
+}
+
+const TQPixmap& PanelButton::zoomIcon() const
+{
+ return m_iconz;
+}
+
+bool PanelButton::isValid() const
+{
+ return m_valid;
+}
+
+void PanelButton::setTitle(const TQString& t)
+{
+ m_title = t;
+}
+
+void PanelButton::setIcon(const TQString& icon)
+{
+ if (icon == m_iconName)
+ {
+ return;
+ }
+
+ m_iconName = icon;
+ loadIcons();
+ update();
+ emit iconChanged();
+}
+
+TQString PanelButton::icon() const
+{
+ return m_iconName;
+}
+
+bool PanelButton::hasText() const
+{
+ return !m_buttonText.isEmpty();
+}
+
+void PanelButton::setButtonText(const TQString& text)
+{
+ m_buttonText = text;
+ update();
+}
+
+TQString PanelButton::buttonText() const
+{
+ return m_buttonText;
+}
+
+void PanelButton::setTextColor(const TQColor& c)
+{
+ m_textColor = c;
+}
+
+TQColor PanelButton::textColor() const
+{
+ return m_textColor;
+}
+
+void PanelButton::setFontPercent(double p)
+{
+ m_fontPercent = p;
+}
+
+double PanelButton::fontPercent() const
+{
+ return m_fontPercent;
+}
+
+KPanelExtension::Orientation PanelButton::orientation() const
+{
+ return m_orientation;
+}
+
+KPanelApplet::Direction PanelButton::popupDirection() const
+{
+ return m_popupDirection;
+}
+
+TQPoint PanelButton::center() const
+{
+ return mapToGlobal(rect().center());
+}
+
+TQString PanelButton::title() const
+{
+ return m_title;
+}
+
+void PanelButton::triggerDrag()
+{
+ setDown(false);
+
+ startDrag();
+}
+
+void PanelButton::startDrag()
+{
+ emit dragme(m_icon);
+}
+
+void PanelButton::enterEvent(TQEvent* e)
+{
+ if (!m_highlight && m_disableHighlighting == FALSE)
+ {
+ m_highlight = true;
+ repaint(false);
+ }
+
+ TQButton::enterEvent(e);
+}
+
+void PanelButton::leaveEvent(TQEvent* e)
+{
+ if (m_highlight)
+ {
+ m_highlight = false;
+ repaint(false);
+ }
+
+ TQButton::leaveEvent(e);
+}
+
+void PanelButton::dragEnterEvent(TQDragEnterEvent* e)
+{
+ if (e->isAccepted())
+ {
+ m_hasAcceptedDrag = true;
+ }
+
+ update();
+ TQButton::dragEnterEvent( e );
+}
+
+void PanelButton::dragLeaveEvent(TQDragLeaveEvent* e)
+{
+ m_hasAcceptedDrag = false;
+ update();
+ TQButton::dragLeaveEvent( e );
+}
+
+void PanelButton::dropEvent(TQDropEvent* e)
+{
+ m_hasAcceptedDrag = false;
+ update();
+ TQButton::dropEvent( e );
+}
+
+void PanelButton::mouseMoveEvent(TQMouseEvent *e)
+{
+ if (!m_isLeftMouseButtonDown || (e->state() & Qt::LeftButton) == 0)
+ {
+ return;
+ }
+
+ TQPoint p(e->pos() - m_lastLeftMouseButtonPress);
+ if (p.manhattanLength() <= 16)
+ {
+ // TDEGlobalSettings::dndEventDelay() is not enough!
+ return;
+ }
+
+ m_isLeftMouseButtonDown = false;
+ triggerDrag();
+}
+
+void PanelButton::mousePressEvent(TQMouseEvent *e)
+{
+ if (e->button() == Qt::LeftButton)
+ {
+ m_lastLeftMouseButtonPress = e->pos();
+ m_isLeftMouseButtonDown = true;
+ }
+ TQButton::mousePressEvent(e);
+}
+
+void PanelButton::mouseReleaseEvent(TQMouseEvent *e)
+{
+ if (e->button() == Qt::LeftButton)
+ {
+ m_isLeftMouseButtonDown = false;
+
+ TQPixmap pix = labelIcon();
+ if (KickerSettings::showIconActivationEffect() == true) {
+ TDEIconEffect::visualActivate(this, this->geometry(), &pix);
+ }
+ }
+ TQButton::mouseReleaseEvent(e);
+}
+
+void PanelButton::resizeEvent(TQResizeEvent*)
+{
+ loadTiles();
+
+ if (calculateIconSize())
+ {
+ loadIcons();
+ }
+}
+
+void PanelButton::drawButton(TQPainter *p)
+{
+ const TQPixmap& tile = (isDown() || isOn()) ? m_down : m_up;
+
+ if (m_tileColor.isValid())
+ {
+ p->fillRect(rect(), m_tileColor);
+ style().tqdrawPrimitive(TQStyle::PE_Panel, p, rect(), colorGroup());
+ }
+ else if (paletteBackgroundPixmap())
+ {
+ // Draw the background. This is always needed, even when using tiles,
+ // because they don't have to cover the entire button.
+ TQPoint offset = backgroundOffset();
+ int ox = offset.x();
+ int oy = offset.y();
+ p->drawTiledPixmap( 0, 0, width(), height(),*paletteBackgroundPixmap(), ox, oy);
+ }
+
+ if (!tile.isNull())
+ {
+ // Draw the tile.
+ p->drawPixmap(0, 0, tile);
+ }
+ else if (isDown() || isOn())
+ {
+ // Draw shapes to indicate the down state.
+ style().tqdrawPrimitive(TQStyle::PE_Panel, p, rect(), colorGroup(), TQStyle::Style_Sunken);
+ }
+
+ drawButtonLabel(p);
+
+ if (hasFocus() || m_hasAcceptedDrag)
+ {
+ int x1, y1, x2, y2;
+ TQT_TQRECT_OBJECT(rect()).coords(&x1, &y1, &x2, &y2);
+ TQRect r(x1+2, y1+2, x2-x1-3, y2-y1-3);
+ style().tqdrawPrimitive(TQStyle::PE_FocusRect, p, r, colorGroup(),
+ TQStyle::Style_Default, colorGroup().button());
+ }
+}
+
+void PanelButton::drawDeepButton(TQPainter *p)
+{
+ const TQPixmap& tile = (isDown() || isOn()) ? m_down : m_up;
+
+ if (m_tileColor.isValid())
+ {
+ p->fillRect(rect(), m_tileColor);
+ style().tqdrawPrimitive(TQStyle::PE_Panel, p, rect(), colorGroup());
+ }
+ else if (paletteBackgroundPixmap())
+ {
+ // Draw the background. This is always needed, even when using tiles,
+ // because they don't have to cover the entire button.
+ TQPoint offset = backgroundOffset();
+ int ox = offset.x();
+ int oy = offset.y();
+ p->drawTiledPixmap( 0, 0, width(), height(),*paletteBackgroundPixmap(), ox, oy);
+ }
+
+ TQRect btn_rect = TQRect(rect().x(), rect().y()+1, rect().width(), rect().height()-2);
+ if (isDown() || isOn()) {
+ style().tqdrawPrimitive(TQStyle::PE_ButtonBevel, p, btn_rect, colorGroup(), TQStyle::Style_Down);
+ }
+ else {
+ style().tqdrawPrimitive(TQStyle::PE_ButtonBevel, p, btn_rect, colorGroup(), TQStyle::Style_Raised);
+ }
+
+ drawButtonLabel(p,0,FALSE);
+
+ if (hasFocus() || m_hasAcceptedDrag)
+ {
+ int x1, y1, x2, y2;
+ TQT_TQRECT_OBJECT(rect()).coords(&x1, &y1, &x2, &y2);
+ TQRect r(x1+2, y1+2, x2-x1-3, y2-y1-3);
+ style().tqdrawPrimitive(TQStyle::PE_FocusRect, p, r, colorGroup(),
+ TQStyle::Style_Default, colorGroup().button());
+ }
+}
+
+void PanelButton::drawButtonLabel(TQPainter *p)
+{
+ drawButtonLabel(p,0,TRUE);
+}
+
+void PanelButton::drawButtonLabel(TQPainter *p, int voffset, bool drawArrow)
+{
+ TQPixmap icon = labelIcon();
+ bool active = isDown() || isOn();
+
+ int offsetX = 0;
+ int offsetY = 0;
+
+ if (active && KickerSettings::showDeepButtons())
+ {
+ offsetX = style().pixelMetric(TQStyle::PM_ButtonShiftHorizontal);
+ offsetY = style().pixelMetric(TQStyle::PM_ButtonShiftVertical);
+ }
+
+ if (active && !KickerSettings::showDeepButtons())
+ {
+ icon = TQImage(icon.convertToImage()).smoothScale(icon.width() - 2,
+ icon.height() - 2);
+ }
+
+ int y = 0;
+ if (m_iconAlignment & AlignVCenter)
+ y = (height() - icon.height()) / 2;
+ else if (m_iconAlignment & AlignBottom)
+ y = (height() - icon.height());
+
+ if (!m_buttonText.isEmpty() && orientation() == Qt::Horizontal)
+ {
+ int h = height();
+ int w = width();
+ p->save();
+ TQFont f = font();
+
+ double fontPercent = m_fontPercent;
+ if (active && !KickerSettings::showDeepButtons())
+ {
+ fontPercent *= .8;
+ }
+ //f.setPixelSize(KMIN(h, KMAX(int(float(h) * m_fontPercent), 16)));
+ TQFontMetrics fm(f);
+ p->setFont(f);
+
+ /* Draw shadowed text */
+ bool reverse = TQApplication::reverseLayout();
+ TQPainter::TextDirection rtl = reverse ? TQPainter::RTL : TQPainter::LTR;
+
+ if (!reverse && !icon.isNull())
+ {
+ /* Draw icon */
+ p->drawPixmap(offsetX+3, offsetY+y+voffset, icon);
+ }
+
+ int tX = reverse ? 3 : icon.width() + KMIN(25, KMAX(5, fm.width('m') / 2));
+ int tY = fm.ascent() + ((h - fm.height()) / 2);
+
+ TQColor shadCol = KickerLib::shadowColor(m_textColor);
+
+ // get a transparent pixmap
+ TQPainter pixPainter;
+ TQPixmap textPixmap(w, h);
+
+ textPixmap.fill(TQColor(0,0,0));
+ textPixmap.setMask(textPixmap.createHeuristicMask(true));
+
+ // draw text
+ pixPainter.begin(&textPixmap);
+ pixPainter.setPen(m_textColor);
+ pixPainter.setFont(p->font()); // get the font from the root painter
+ pixPainter.drawText(offsetX+tX, offsetY+tY, m_buttonText, -1, rtl);
+ pixPainter.end();
+
+ if (!s_textShadowEngine)
+ {
+ KShadowSettings* shadset = new KShadowSettings();
+ shadset->setOffsetX(0);
+ shadset->setOffsetY(0);
+ shadset->setThickness(1);
+ shadset->setMaxOpacity(96);
+ s_textShadowEngine = new KShadowEngine(shadset);
+ }
+
+ // draw shadow
+ TQImage img = s_textShadowEngine->makeShadow(textPixmap, shadCol);
+ p->drawImage(offsetX, offsetY, img);
+ p->save();
+ p->setPen(m_textColor);
+ p->drawText(offsetX+tX, offsetY+tY+voffset, m_buttonText, -1, rtl);
+ p->restore();
+
+ if (reverse && !icon.isNull())
+ {
+ p->drawPixmap(offsetX + w - icon.width() - 3, offsetY+y+voffset, icon);
+ }
+
+ p->restore();
+ }
+ else if (!icon.isNull())
+ {
+ int x = 0;
+ if (m_iconAlignment & AlignHCenter)
+ x = (width() - icon.width()) / 2;
+ else if (m_iconAlignment & AlignRight)
+ x = (width() - icon.width());
+ p->drawPixmap(offsetX+x, offsetY+y+voffset, icon);
+ }
+
+ if (m_drawArrow && (m_highlight || active) && drawArrow)
+ {
+ TQStyle::PrimitiveElement e = TQStyle::PE_ArrowUp;
+ int arrowSize = style().pixelMetric(TQStyle::PM_MenuButtonIndicator);
+ TQRect r((width() - arrowSize)/2, 0, arrowSize, arrowSize);
+
+ switch (m_arrowDirection)
+ {
+ case KPanelExtension::Top:
+ e = TQStyle::PE_ArrowUp;
+ break;
+ case KPanelExtension::Bottom:
+ e = TQStyle::PE_ArrowDown;
+ r.moveBy(0, height() - arrowSize);
+ break;
+ case KPanelExtension::Right:
+ e = TQStyle::PE_ArrowRight;
+ r = TQRect(width() - arrowSize, (height() - arrowSize)/2, arrowSize, arrowSize);
+ break;
+ case KPanelExtension::Left:
+ e = TQStyle::PE_ArrowLeft;
+ r = TQRect(0, (height() - arrowSize)/2, arrowSize, arrowSize);
+ break;
+ case KPanelExtension::Floating:
+ if (orientation() == Qt::Horizontal)
+ {
+ e = TQStyle::PE_ArrowDown;
+ r.moveBy(0, height() - arrowSize);
+ }
+ else if (TQApplication::reverseLayout())
+ {
+ e = TQStyle::PE_ArrowLeft;
+ r = TQRect(0, (height() - arrowSize)/2, arrowSize, arrowSize);
+ }
+ else
+ {
+ e = TQStyle::PE_ArrowRight;
+ r = TQRect(width() - arrowSize, (height() - arrowSize)/2, arrowSize, arrowSize);
+ }
+ break;
+ }
+
+ int flags = TQStyle::Style_Enabled;
+ if (active)
+ {
+ flags |= TQStyle::Style_Down;
+ }
+ style().tqdrawPrimitive(e, p, r, colorGroup(), flags);
+ }
+}
+
+// return the icon size that would be used if the panel were proposed_size
+// if proposed_size==-1, use the current panel size instead
+int PanelButton::preferredIconSize(int proposed_size) const
+{
+ // (re)calculates the icon sizes and report true if they have changed.
+ // Get sizes from icontheme. We assume they are sorted.
+ TDEIconTheme *ith = TDEGlobal::iconLoader()->theme();
+
+ if (!ith)
+ {
+ return -1; // unknown icon size
+ }
+
+ TQValueList<int> sizes = ith->querySizes(TDEIcon::Panel);
+
+ int sz = ith->defaultSize(TDEIcon::Panel);
+
+ if (proposed_size < 0)
+ {
+ proposed_size = (orientation() == Qt::Horizontal) ? height() : width();
+ }
+
+ // determine the upper limit on the size. Normally, this is panelSize,
+ // but if conserve space is requested, the max button size is used instead.
+ int upperLimit = proposed_size;
+ if (proposed_size > KickerLib::maxButtonDim() &&
+ KickerSettings::conserveSpace())
+ {
+ upperLimit = KickerLib::maxButtonDim();
+ }
+
+ //kdDebug()<<endl<<endl<<flush;
+ TQValueListConstIterator<int> i = sizes.constBegin();
+ while (i != sizes.constEnd())
+ {
+ if ((*i) + (2 * KickerSettings::iconMargin()) > upperLimit)
+ {
+ break;
+ }
+ sz = *i; // get the largest size under the limit
+ ++i;
+ }
+
+ //kdDebug()<<"Using icon sizes: "<<sz<<" "<<zoom_sz<<endl<<flush;
+ return sz;
+}
+
+void PanelButton::backedByFile(const TQString& localFilePath)
+{
+ m_backingFile = localFilePath;
+
+ if (m_backingFile.isEmpty())
+ {
+ return;
+ }
+
+ // avoid multiple connections
+ disconnect(KDirWatch::self(), TQT_SIGNAL(deleted(const TQString&)),
+ this, TQT_SLOT(checkForDeletion(const TQString&)));
+
+ if (!KDirWatch::self()->contains(m_backingFile))
+ {
+ KDirWatch::self()->addFile(m_backingFile);
+ }
+
+ connect(KDirWatch::self(), TQT_SIGNAL(deleted(const TQString&)),
+ this, TQT_SLOT(checkForDeletion(const TQString&)));
+
+}
+
+void PanelButton::setArrowDirection(KPanelExtension::Position dir)
+{
+ if (m_arrowDirection != dir)
+ {
+ m_arrowDirection = dir;
+ update();
+ }
+}
+
+void PanelButton::loadTiles()
+{
+ if (m_tileColor.isValid())
+ {
+ setBackgroundOrigin(WidgetOrigin);
+ m_up = m_down = TQPixmap();
+ }
+ else if (m_tile.isNull())
+ {
+ setBackgroundOrigin(AncestorOrigin);
+ m_up = m_down = TQPixmap();
+ }
+ else
+ {
+ setBackgroundOrigin(WidgetOrigin);
+ // If only the tiles were named a bit smarter we wouldn't have
+ // to pass the up or down argument.
+ m_up = TQPixmap(loadTile(m_tile, size(), "up"));
+ m_down = TQPixmap(loadTile(m_tile, size(), "down"));
+ }
+}
+
+void PanelButton::loadIcons()
+{
+ TDEIconLoader * ldr = TDEGlobal::iconLoader();
+ TQString nm = m_iconName;
+ TDEIcon::States defaultState = isEnabled() ? TDEIcon::DefaultState :
+ TDEIcon::DisabledState;
+ if (nm=="kmenu-suse")
+ {
+ TQString pth = locate( "data", "kicker/data/kickoff/kmenu_basic.png" );
+ if (!pth.isEmpty())
+ {
+ m_icon = TQImage(pth);
+ m_iconh = TQPixmap(m_icon);
+ m_iconz = TQPixmap(m_icon);
+ return;
+ }
+ }
+ else
+ m_icon = ldr->loadIcon(nm, TDEIcon::Panel, m_size, defaultState, 0L, true);
+
+ if (m_icon.isNull())
+ {
+ nm = defaultIcon();
+ m_icon = ldr->loadIcon(nm, TDEIcon::Panel, m_size, defaultState);
+ }
+
+ if (!isEnabled())
+ {
+ m_iconh = m_icon;
+ }
+ else
+ {
+ m_iconh = ldr->loadIcon(nm, TDEIcon::Panel, m_size,
+ TDEIcon::ActiveState, 0L, true);
+ }
+
+ m_iconz = ldr->loadIcon(nm, TDEIcon::Panel, TDEIcon::SizeHuge,
+ defaultState, 0L, true );
+}
+
+// (re)calculates the icon sizes and report true if they have changed.
+// (false if we don't know, because theme couldn't be loaded?)
+bool PanelButton::calculateIconSize()
+{
+ int size = preferredIconSize();
+
+ if (size < 0)
+ {
+ // size unknown
+ return false;
+ }
+
+ if (m_size != size)
+ {
+ // Size has changed, update
+ m_size = size;
+ return true;
+ }
+
+ return false;
+}
+
+void PanelButton::setCenterButtonInContainer(bool center) {
+ m_centerInContainer = center;
+}
+
+void PanelButton::updateKickerTip(KickerTip::Data& data)
+{
+ data.message = TQStyleSheet::escape(title());
+ data.subtext = TQStyleSheet::escape(TQToolTip::textFor(this));
+ data.icon = zoomIcon();
+ data.direction = popupDirection();
+}
+
+bool PanelButton::centerButtonInContainer()
+{
+ return m_centerInContainer;
+}
+
+//
+// PanelPopupButton class
+//
+
+PanelPopupButton::PanelPopupButton(TQWidget *parent, const char *name, bool forceStandardCursor)
+ : PanelButton(parent, name, forceStandardCursor),
+ m_popup(0),
+ m_pressedDuringPopup(false),
+ m_initialized(false)
+{
+ connect(this, TQT_SIGNAL(pressed()), TQT_SLOT(slotExecMenu()));
+}
+
+void PanelPopupButton::setPopup(TQWidget *popup)
+{
+ if (m_popup)
+ {
+ m_popup->removeEventFilter(this);
+ disconnect(m_popup, TQT_SIGNAL(aboutToHide()), this, TQT_SLOT(menuAboutToHide()));
+ }
+
+ m_popup = popup;
+ setDrawArrow(m_popup != 0);
+
+ if (m_popup)
+ {
+ m_popup->installEventFilter(this);
+ connect(m_popup, TQT_SIGNAL(aboutToHide()), this, TQT_SLOT(menuAboutToHide()));
+ }
+}
+
+TQWidget *PanelPopupButton::popup() const
+{
+ return m_popup;
+}
+
+bool PanelPopupButton::eventFilter(TQObject *, TQEvent *e)
+{
+ if (e->type() == TQEvent::MouseMove)
+ {
+ TQMouseEvent *me = TQT_TQMOUSEEVENT(e);
+ if (TQT_TQRECT_OBJECT(rect()).contains(mapFromGlobal(me->globalPos())) &&
+ ((me->state() & ControlButton) != 0 ||
+ (me->state() & ShiftButton) != 0))
+ {
+ PanelButton::mouseMoveEvent(me);
+ return true;
+ }
+ }
+ else if (e->type() == TQEvent::MouseButtonPress ||
+ e->type() == TQEvent::MouseButtonDblClick)
+ {
+ TQMouseEvent *me = TQT_TQMOUSEEVENT(e);
+ if (TQT_TQRECT_OBJECT(rect()).contains(mapFromGlobal(me->globalPos())))
+ {
+ m_pressedDuringPopup = true;
+ return true;
+ }
+ }
+ else if (e->type() == TQEvent::MouseButtonRelease)
+ {
+ TQMouseEvent *me = TQT_TQMOUSEEVENT(e);
+ if (TQT_TQRECT_OBJECT(rect()).contains(mapFromGlobal(me->globalPos())))
+ {
+ if (m_pressedDuringPopup && m_popup)
+ {
+ m_popup->hide();
+ }
+ return true;
+ }
+ }
+ return false;
+}
+
+void PanelPopupButton::showMenu()
+{
+ if (isDown())
+ {
+ if (m_popup)
+ {
+ m_popup->hide();
+ }
+
+ setDown(false);
+ return;
+ }
+
+ setDown(true);
+ update();
+ slotExecMenu();
+}
+
+void PanelPopupButton::slotExecMenu()
+{
+ if (!m_popup)
+ {
+ return;
+ }
+
+ m_pressedDuringPopup = false;
+ KickerTip::enableTipping(false);
+ kapp->syncX();
+ kapp->processEvents();
+
+ if (!m_initialized)
+ {
+ initPopup();
+ }
+
+ m_popup->adjustSize();
+ if(dynamic_cast<TQPopupMenu*>(m_popup))
+ static_cast<TQPopupMenu*>(m_popup)->exec(KickerLib::popupPosition(popupDirection(), m_popup, this));
+ // else.. hmm. some derived class has to fix it.
+}
+
+void PanelPopupButton::menuAboutToHide()
+{
+ if (!m_popup)
+ {
+ return;
+ }
+
+ if (isDown()) {
+ setDown(false);
+ KickerTip::enableTipping(true);
+ }
+}
+
+void PanelPopupButton::triggerDrag()
+{
+ if (m_popup)
+ {
+ m_popup->hide();
+ }
+
+ PanelButton::triggerDrag();
+}
+
+void PanelPopupButton::setInitialized(bool initialized)
+{
+ m_initialized = initialized;
+}
+
+
+
diff --git a/kicker/libkicker/panelbutton.h b/kicker/libkicker/panelbutton.h
new file mode 100644
index 000000000..80b26f377
--- /dev/null
+++ b/kicker/libkicker/panelbutton.h
@@ -0,0 +1,488 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#ifndef __panelbutton_h__
+#define __panelbutton_h__
+
+#include <algorithm>
+
+#include <tqbutton.h>
+
+#include <kpanelapplet.h>
+#include <kpanelextension.h>
+#include <kurldrag.h>
+
+#include "kickertip.h"
+
+class TQPopupMenu;
+class TDEConfigGroup;
+class KShadowEngine;
+
+/**
+ * PanelButton is the base class for all buttons to be
+ * placed in Kicker's panels. It inherits TQButton, and
+ * KickerTip::Client.
+ */
+class KDE_EXPORT PanelButton: public TQButton, public KickerTip::Client
+{
+ Q_OBJECT
+
+public:
+ /**
+ * Create a panel button
+ * @param parent the parent widget
+ * @param name the widget's name
+ */
+ PanelButton( TQWidget* parent, const char* name, bool forceStandardCursor = FALSE );
+
+ /**
+ * Configures this button according to the user's preferences for
+ * button tiles/colors/etc. This must be called by the container
+ * embedding the button after consturction and thereafter whenever
+ * the configuration changes to ensure it remains properly styled.
+ * Note that it is not used for configuration specific to the subclass.
+ */
+ void configure();
+
+ /**
+ * Prompts the button to save it's configuration. Subclass specific
+ * settings should be saved in this method to the TDEConfigGroup passed in.
+ */
+ virtual void saveConfig(TDEConfigGroup&) const {}
+
+ /**
+ * Reimplement this to display a properties dialog for your button.
+ */
+ virtual void properties() {}
+
+ /**
+ * Reimplement this to give Kicker a hint for the width of the button
+ * given a certain height.
+ */
+ virtual int widthForHeight(int height) const;
+
+ /**
+ * Reimplement this to give Kicker a hint for the height of the button
+ * given a certain width.
+ */
+ virtual int heightForWidth(int width) const;
+
+ /**
+ * @return the button's current icon
+ */
+ virtual const TQPixmap& labelIcon() const;
+
+ /**
+ * @return the button's zoom icon
+ */
+ virtual const TQPixmap& zoomIcon() const;
+
+ /**
+ * @return true if this button is valid.
+ */
+ bool isValid() const;
+
+ /**
+ * Changes the title for the panel button.
+ * @param t the button's title
+ */
+ void setTitle(const TQString& t);
+
+ /**
+ * @return the title of the button.
+ */
+ TQString title() const;
+
+ /**
+ * Changes the name of the panel button's tile, with
+ * optional color.
+ * @param tile the button's tile name
+ * @param color the button's tile color
+ */
+ void setTile(const TQString& tile, const TQColor& color = TQColor());
+
+ /**
+ * Set to true to draw an arrow on the button.
+ */
+ void setDrawArrow(bool drawArrow);
+
+ /**
+ * Used to set the icon for this panel button.
+ * @param icon the path to the button's icon
+ */
+ void setIcon(const TQString& icon);
+
+ /**
+ * @return the button's icon
+ */
+ TQString icon() const;
+
+ /**
+ * @return whether this button has a text label or not
+ */
+ bool hasText() const;
+
+ /**
+ * Change the button's text label
+ * @param text text for button's label
+ */
+ void setButtonText(const TQString& text);
+
+ /**
+ * @return button's text label
+ */
+ TQString buttonText() const;
+
+ /**
+ * Change the button's text label color
+ * @param c the new text label color
+ */
+ void setTextColor(const TQColor& c);
+
+ /**
+ * @return the button's text label color
+ */
+ TQColor textColor() const;
+
+ /**
+ * Change the button's text scale
+ * @param p font scale (in percent)
+ */
+ void setFontPercent(double p);
+
+ /**
+ * @return the button's text scale (in percent)
+ */
+ double fontPercent() const;
+
+ /**
+ * @return the orientation of the button
+ */
+ Orientation orientation() const;
+
+ /**
+ * @return the button's popup direction (read from parent KPanelApplet)
+ */
+ KPanelApplet::Direction popupDirection() const;
+
+ /**
+ * @return global position of the center of the button
+ */
+ TQPoint center() const;
+
+ /**
+ * Used to load the graphical tile of the button
+ * @param name path/name of button's tile
+ * @param size size of the tile
+ * @param state used if button has multiple states (null by default)
+ */
+ static TQImage loadTile(const TQString& name, const TQSize&,
+ const TQString& state = TQString::null);
+
+ /**
+ * Update the contents of the button's KickerTip
+ * @param data new KickerTip data
+ */
+ void updateKickerTip(KickerTip::Data& data);
+
+ /**
+ * @return true if the button should be centered in its parent container, false if not
+ */
+ bool centerButtonInContainer();
+
+signals:
+ /**
+ * Emitted when the button's icon is changed.
+ */
+ void iconChanged();
+
+ /**
+ * Emitted to notify parent containers to save config
+ */
+ void requestSave();
+
+ /**
+ * Emitted when the button needs to be removed from it's container
+ * @see KickerSettings::removeButtonsWhenBroken()
+ */
+ void removeme();
+
+ /**
+ * Emitted when the button may need to be removed, but that removal depends
+ * on as-yet-uncertain future events and therefore ought to be hidden from
+ * view, though not deleted quite yet.
+ * @see KickerSettings::removeButtonsWhenBroken()
+ */
+ void hideme(bool hide);
+
+ /**
+ * Emitted when button initiates a drag
+ */
+ void dragme(const TQPixmap);
+
+ /**
+ * Overloads dragme to support panel button's with a list of KURL's ([url/servicemenu/browser]button)
+ */
+ void dragme(const KURL::List, const TQPixmap);
+
+public slots:
+ /**
+ * Set to true to enable the button.
+ */
+ void setEnabled(bool enable);
+
+ /**
+ * Sets the orientation of the button (ie. which direction the icon will rotate).
+ */
+ void setOrientation(Orientation o);
+
+ /**
+ * Sets the direction to pop up the contents of the button.
+ */
+ virtual void setPopupDirection(KPanelApplet::Direction d);
+
+protected:
+
+ void setIconAlignment(TQ_Alignment align);
+ /**
+ * Subclasses must implement this to define the name of the button which is
+ * used to identify this button for saving and loading. It must be unique
+ * to the subclass, should not be i18n'd and is never made user visible.
+ * KDE4: remove this and use the classname directly instead.
+ */
+ virtual TQString tileName() = 0;
+
+ /**
+ * @return the default icon for the button
+ */
+ virtual TQString defaultIcon() const { return "unknown"; };
+
+ /**
+ * Called right before drag occurs.
+ */
+ virtual void triggerDrag();
+
+ /**
+ * Emits a signal to drag the button. Reimplement this if, for example,
+ * if you need the button to call dragme(KURL::List, const TQPixmap)
+ * instead of dragme(const TQPixmap)
+ */
+ virtual void startDrag();
+
+ virtual void enterEvent(TQEvent *);
+ virtual void leaveEvent(TQEvent *);
+ virtual void dragEnterEvent(TQDragEnterEvent *);
+ virtual void dragLeaveEvent(TQDragLeaveEvent *);
+ virtual void dropEvent(TQDropEvent *);
+ virtual void mouseMoveEvent(TQMouseEvent *);
+ virtual void mousePressEvent(TQMouseEvent *);
+ virtual void mouseReleaseEvent(TQMouseEvent *);
+ virtual void resizeEvent(TQResizeEvent*);
+ virtual void drawButton(TQPainter *);
+ virtual void drawDeepButton(TQPainter *);
+ virtual void drawButtonLabel(TQPainter *);
+ virtual void drawButtonLabel(TQPainter *, int voffset, bool drawArrow);
+
+ /**
+ * @return the preferred icon size.
+ */
+ virtual int preferredIconSize(int proposed_size = -1) const;
+
+ /**
+ * @return the preferred dimensions for the button
+ */
+ virtual int preferredDimension(int panelDim) const;
+
+ /**
+ * if the button represents a local file, it tells PanelButton
+ * what file that is and it starts to watch it. if the file is
+ * deleted, it is disabled and then checked for one second later
+ * to see if has returned (e.g. a reinstall occurred) by calling
+ * checkForBackingFile(). if that returns false, then the button
+ * is removed from kicker.
+ * TODO: implement a heuristic that checks back in intervals for
+ * the reappearance of the file and returns the button to the panel
+ */
+ virtual bool checkForBackingFile();
+
+ /**
+ * Set the file backing this button (See @ref checkForBackingFile()),
+ * you shouldn't need to use this, currently it's only used in [url/service]button
+ */
+ void backedByFile(const TQString& localFilePath);
+
+ /**
+ * Sets the button's arrow direction.
+ * @param dir the arrow direction
+ */
+ void setArrowDirection(KPanelExtension::Position dir);
+
+ /**
+ * Loads the tiles for the button
+ */
+ void loadTiles();
+
+ /**
+ * Loads the icons for the button
+ */
+ void loadIcons();
+
+ /**
+ * (Re)Calculate icon sizes and return true if they have changed.
+ */
+ bool calculateIconSize();
+
+ /**
+ * @param center true if the button should be centered in its parent container, false if not
+ */
+ void setCenterButtonInContainer(bool center);
+
+ bool m_valid;
+ TQPixmap m_icon;
+
+protected slots:
+ /**
+ * Called from TDEApplication when global icon settings have changed.
+ * @param group the new group
+ */
+ void updateIcon(int group);
+
+ /**
+ * Called from TDEApplication when global settings have changed.
+ * @param category the settings category, see TDEApplication::SettingsCategory
+ */
+ void updateSettings(int category);
+
+ /**
+ * Used for backedByFile, to check if the file backing this button
+ * has been deleted.
+ * @param path path to backing file
+ */
+ void checkForDeletion(const TQString& path);
+
+ /**
+ * Called to prepare the button for removal from the Kicker
+ */
+ void scheduleForRemoval();
+
+private:
+ TQPoint m_lastLeftMouseButtonPress;
+ bool m_isLeftMouseButtonDown;
+ bool m_drawArrow;
+ bool m_highlight;
+ bool m_changeCursorOverItem;
+ bool m_hasAcceptedDrag;
+ bool m_centerInContainer;
+ TQColor m_textColor;
+ TQColor m_tileColor;
+ TQString m_buttonText;
+ TQString m_tile;
+ TQString m_title;
+ TQString m_iconName;
+ TQString m_backingFile;
+ TQPixmap m_up;
+ TQPixmap m_down;
+ TQPixmap m_iconh; // hover
+ TQPixmap m_iconz; // mouse over
+ KPanelExtension::Position m_arrowDirection;
+ KPanelApplet::Direction m_popupDirection;
+ TQ_Alignment m_iconAlignment;
+ Orientation m_orientation;
+ int m_size;
+ double m_fontPercent;
+ bool m_forceStandardCursor;
+ static KShadowEngine* s_textShadowEngine;
+
+ class PanelPopupPrivate;
+ PanelPopupPrivate* d;
+};
+
+/**
+ * Base class for panelbuttons which popup a menu
+ */
+class KDE_EXPORT PanelPopupButton : public PanelButton
+{
+ Q_OBJECT
+
+public:
+ /**
+ * Create a panel button that pops up a menu.
+ * @param parent the parent widget
+ * @param name the widget's name
+ */
+ PanelPopupButton(TQWidget *parent=0, const char *name=0, bool forceStandardCursor = FALSE);
+
+ /**
+ * Sets the button's popup menu.
+ * @param popup the menu to pop up
+ */
+ void setPopup(TQWidget *popup);
+
+ /**
+ * @return the button's popup menu
+ */
+ TQWidget *popup() const;
+
+ bool eventFilter(TQObject *, TQEvent *);
+ virtual void showMenu();
+
+protected:
+ /**
+ * Called each time the button is clicked and the popup
+ * is displayed. Reimplement for dynamic popup menus.
+ */
+ virtual void initPopup() {};
+
+ /**
+ * Called before drag occurs. Reimplement to do any
+ * necessary setup before the button is dragged.
+ */
+ virtual void triggerDrag();
+
+ /**
+ * Marks the menu as initialized.
+ */
+ void setInitialized(bool initialized);
+
+protected slots:
+ /**
+ * Connected to the button's pressed() signal, this is
+ * the code that actually displays the menu. Reimplement if
+ * you need to take care of any tasks before the popup is
+ * displayed (eg. KickerTip)
+ */
+ virtual void slotExecMenu();
+
+private slots:
+ void menuAboutToHide();
+
+protected:
+ TQWidget *m_popup;
+ bool m_pressedDuringPopup;
+ bool m_initialized;
+
+ class PanelPopupButtonPrivate;
+ PanelPopupButtonPrivate* d;
+};
+
+#endif // __panelbutton_h__
diff --git a/kicker/libkicker/paneldrag.cpp b/kicker/libkicker/paneldrag.cpp
new file mode 100644
index 000000000..1fb6b9ce6
--- /dev/null
+++ b/kicker/libkicker/paneldrag.cpp
@@ -0,0 +1,180 @@
+/*****************************************************************
+Copyright (c) 2004 Aaron J. Seigo <[email protected]>
+ 2004 Stephen Depooter <[email protected]>
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#include <sys/types.h>
+#include <unistd.h>
+
+#include <tqbuffer.h>
+
+#include "paneldrag.h"
+
+#define PANELDRAG_BUFSIZE sizeof(BaseContainer*) + sizeof(pid_t)
+
+PanelDrag::PanelDrag(BaseContainer* container, TQWidget* dragSource)
+ : TQDragObject(dragSource, 0)
+{
+ pid_t source_pid = getpid();
+
+ a.resize(PANELDRAG_BUFSIZE);
+ memcpy(a.data(), &container, sizeof(BaseContainer*));
+ memcpy(a.data() + sizeof(BaseContainer*), &source_pid, sizeof(pid_t));
+}
+
+PanelDrag::~PanelDrag()
+{
+}
+
+bool PanelDrag::decode(const TQMimeSource* e, BaseContainer** container)
+{
+ TQByteArray a = e->encodedData("application/basecontainerptr");
+
+ if (a.size() != PANELDRAG_BUFSIZE)
+ {
+ return false;
+ }
+
+ pid_t target_pid = getpid();
+ pid_t source_pid;
+ memcpy(&source_pid, a.data() + sizeof(TQObject*), sizeof(pid_t));
+
+ if (source_pid == target_pid)
+ {
+ memcpy(container, a.data(), sizeof(TQObject*));
+ return true;
+ }
+
+ return false;
+}
+
+bool PanelDrag::canDecode(const TQMimeSource *e)
+{
+ if (!e->provides("application/basecontainerptr"))
+ {
+ return false;
+ }
+
+ TQByteArray a = e->encodedData("application/basecontainerptr");
+ if (a.size() != PANELDRAG_BUFSIZE)
+ {
+ return false;
+ }
+
+/* pid_t target_pid = getpid();
+ pid_t source_pid;
+ memcpy(&source_pid, a.data() + sizeof(void*), sizeof(pid_t));
+
+ if (source_pid != target_pid)
+ {
+ return true;
+ } */
+
+ return true;
+}
+
+TQByteArray PanelDrag::encodedData(const char * mimeType) const
+{
+ if (TQString("application/basecontainerptr") == mimeType &&
+ a.size() == PANELDRAG_BUFSIZE)
+ {
+ return a;
+ }
+
+ return TQByteArray();
+}
+
+const char * PanelDrag::format(int i) const
+{
+ if (i == 0)
+ {
+ return "application/basecontainerptr";
+ }
+
+ return 0;
+}
+
+
+AppletInfoDrag::AppletInfoDrag(const AppletInfo& info, TQWidget *dragSource)
+ : TQDragObject(dragSource, 0)
+{
+ TQBuffer buff(a);
+ buff.open(IO_WriteOnly);
+ TQDataStream s(&buff);
+ s << info.desktopFile() << info.configFile() << info.type();
+}
+
+AppletInfoDrag::~AppletInfoDrag()
+{
+}
+
+const char * AppletInfoDrag::format(int i) const
+{
+ if (i == 0)
+ {
+ return "application/appletinfo";
+ }
+
+ return 0;
+}
+
+TQByteArray AppletInfoDrag::encodedData(const char* mimeType) const
+{
+ if (TQString("application/appletinfo") == mimeType)
+ {
+ return a;
+ }
+
+ return TQByteArray();
+}
+
+bool AppletInfoDrag::canDecode(const TQMimeSource * e)
+{
+ if (!e->provides("application/appletinfo"))
+ {
+ return false;
+ }
+
+ return true;
+}
+
+bool AppletInfoDrag::decode(const TQMimeSource* e, AppletInfo& container)
+{
+ TQByteArray a = e->encodedData("application/appletinfo");
+
+ if (a.isEmpty())
+ {
+ return false;
+ }
+
+ TQBuffer buff(a);
+ buff.open(IO_ReadOnly);
+ TQDataStream s(&buff);
+
+ TQString desktopFile;
+ TQString configFile;
+ int type;
+ s >> desktopFile >> configFile >> type;
+ AppletInfo info(desktopFile, configFile, (AppletInfo::AppletType)type);
+ container = info;
+ return true;
+}
+
diff --git a/kicker/libkicker/paneldrag.h b/kicker/libkicker/paneldrag.h
new file mode 100644
index 000000000..6684c32c6
--- /dev/null
+++ b/kicker/libkicker/paneldrag.h
@@ -0,0 +1,68 @@
+/*****************************************************************
+Copyright (c) 2004 Aaron J. Seigo <[email protected]>
+ 2004 Stephen Depooter <[email protected]>
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#ifndef _paneldrag_h_
+#define _paneldrag_h_
+
+#include <tqdragobject.h>
+
+#include <kdemacros.h>
+
+#include "appletinfo.h"
+
+class BaseContainer;
+
+class KDE_EXPORT PanelDrag : public TQDragObject
+{
+ public:
+ PanelDrag(BaseContainer* container, TQWidget *dragSource);
+ ~PanelDrag();
+
+ virtual const char * format(int i = 0) const;
+ virtual TQByteArray encodedData(const char *) const;
+
+ static bool canDecode(const TQMimeSource * e);
+ static bool decode(const TQMimeSource* e, BaseContainer** container);
+
+ private:
+ TQByteArray a;
+};
+
+class KDE_EXPORT AppletInfoDrag : public TQDragObject
+{
+ public:
+ AppletInfoDrag(const AppletInfo& container, TQWidget *dragSource);
+ ~AppletInfoDrag();
+
+ virtual const char * format(int i = 0) const;
+ virtual TQByteArray encodedData(const char *) const;
+
+ static bool canDecode(const TQMimeSource * e);
+ static bool decode(const TQMimeSource* e, AppletInfo& container);
+
+ private:
+ TQByteArray a;
+};
+
+#endif
+
diff --git a/kicker/libkicker/panner.cpp b/kicker/libkicker/panner.cpp
new file mode 100644
index 000000000..ec06b30c9
--- /dev/null
+++ b/kicker/libkicker/panner.cpp
@@ -0,0 +1,396 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#include <tqlayout.h>
+#include <tqtooltip.h>
+#include <tqtimer.h>
+#include <tqpainter.h>
+#include <tqstyle.h>
+
+#include <tdeglobal.h>
+#include <tdelocale.h>
+#include <kdebug.h>
+
+#include "simplebutton.h"
+#include "panner.h"
+#include "panner.moc"
+
+Panner::Panner( TQWidget* parent, const char* name )
+ : TQWidget( parent, name ),
+ _luSB(0),
+ _rdSB(0),
+ _cwidth(0), _cheight(0),
+ _cx(0), _cy(0)
+{
+ TDEGlobal::locale()->insertCatalogue("libkicker");
+ setBackgroundOrigin( AncestorOrigin );
+
+ _updateScrollButtonsTimer = new TQTimer(this);
+ connect(_updateScrollButtonsTimer, TQT_SIGNAL(timeout()), this, TQT_SLOT(reallyUpdateScrollButtons()));
+
+ _clipper = new TQWidget(this);
+ _clipper->setBackgroundOrigin(AncestorOrigin);
+ _clipper->installEventFilter( this );
+ _viewport = new TQWidget(_clipper);
+ _viewport->setBackgroundOrigin(AncestorOrigin);
+
+ // layout
+ _layout = new TQBoxLayout(this, TQBoxLayout::LeftToRight);
+ _layout->addWidget(_clipper, 1);
+ setOrientation(Qt::Horizontal);
+}
+
+Panner::~Panner()
+{
+}
+
+void Panner::createScrollButtons()
+{
+ if (_luSB)
+ {
+ return;
+ }
+
+ // left/up scroll button
+ _luSB = new SimpleArrowButton(this);
+ _luSB->installEventFilter(this);
+ //_luSB->setAutoRepeat(true);
+ _luSB->setMinimumSize(12, 12);
+ _luSB->hide();
+ _layout->addWidget(_luSB);
+ connect(_luSB, TQT_SIGNAL(pressed()), TQT_SLOT(startScrollLeftUp()));
+ connect(_luSB, TQT_SIGNAL(released()), TQT_SLOT(stopScroll()));
+
+ // right/down scroll button
+ _rdSB = new SimpleArrowButton(this);
+ _rdSB->installEventFilter(this);
+ //_rdSB->setAutoRepeat(true);
+ _rdSB->setMinimumSize(12, 12);
+ _rdSB->hide();
+ _layout->addWidget(_rdSB);
+ connect(_rdSB, TQT_SIGNAL(pressed()), TQT_SLOT(startScrollRightDown()));
+ connect(_rdSB, TQT_SIGNAL(released()), TQT_SLOT(stopScroll()));
+
+ // set up the buttons
+ setupButtons();
+}
+
+void Panner::setupButtons()
+{
+ if (orientation() == Qt::Horizontal)
+ {
+ if (_luSB)
+ {
+ _luSB->setArrowType(Qt::LeftArrow);
+ _rdSB->setArrowType(Qt::RightArrow);
+ _luSB->setSizePolicy(TQSizePolicy(TQSizePolicy::Minimum, TQSizePolicy::Expanding));
+ _rdSB->setSizePolicy(TQSizePolicy(TQSizePolicy::Minimum, TQSizePolicy::Expanding));
+ TQToolTip::add(_luSB, i18n("Scroll left"));
+ TQToolTip::add(_rdSB, i18n("Scroll right"));
+ setMinimumSize(24, 0);
+ }
+ _layout->setDirection(TQBoxLayout::LeftToRight);
+ }
+ else
+ {
+ if (_luSB)
+ {
+ _luSB->setArrowType(Qt::UpArrow);
+ _rdSB->setArrowType(Qt::DownArrow);
+ _luSB->setSizePolicy(TQSizePolicy(TQSizePolicy::Expanding, TQSizePolicy::Minimum));
+ _rdSB->setSizePolicy(TQSizePolicy(TQSizePolicy::Expanding, TQSizePolicy::Minimum));
+ TQToolTip::add(_luSB, i18n("Scroll up"));
+ TQToolTip::add(_rdSB, i18n("Scroll down"));
+ setMinimumSize(0, 24);
+ }
+ _layout->setDirection(TQBoxLayout::TopToBottom);
+ }
+
+ if (isVisible())
+ {
+ // we need to manually redo the layout if we are visible
+ // otherwise let the toolkit decide when to do this
+ _layout->activate();
+ }
+}
+
+void Panner::setOrientation(Orientation o)
+{
+ _orient = o;
+ setupButtons();
+ reallyUpdateScrollButtons();
+}
+
+void Panner::resizeEvent( TQResizeEvent* )
+{
+ //TQScrollView::resizeEvent( e );
+ //updateScrollButtons();
+}
+
+void Panner::scrollRightDown()
+{
+ if(orientation() == Qt::Horizontal) // scroll right
+ scrollBy( _step, 0 );
+ else // scroll down
+ scrollBy( 0, _step );
+ if (_step < 64)
+ _step++;
+}
+
+void Panner::scrollLeftUp()
+{
+ if(orientation() == Qt::Horizontal) // scroll left
+ scrollBy( -_step, 0 );
+ else // scroll up
+ scrollBy( 0, -_step );
+ if (_step < 64)
+ _step++;
+}
+
+void Panner::startScrollRightDown()
+{
+ _scrollTimer = new TQTimer(this);
+ connect(_scrollTimer, TQT_SIGNAL(timeout()), TQT_SLOT(scrollRightDown()));
+ _scrollTimer->start(50);
+ _step = 8;
+ scrollRightDown();
+}
+
+void Panner::startScrollLeftUp()
+{
+ _scrollTimer = new TQTimer(this);
+ connect(_scrollTimer, TQT_SIGNAL(timeout()), TQT_SLOT(scrollLeftUp()));
+ _scrollTimer->start(50);
+ _step = 8;
+ scrollLeftUp();
+}
+
+void Panner::stopScroll()
+{
+ delete _scrollTimer;
+ _scrollTimer = 0;
+}
+
+void Panner::reallyUpdateScrollButtons()
+{
+ int delta = 0;
+
+ _updateScrollButtonsTimer->stop();
+
+ if (orientation() == Qt::Horizontal)
+ {
+ delta = contentsWidth() - width();
+ }
+ else
+ {
+ delta = contentsHeight() - height();
+ }
+
+ if (delta >= 1)
+ {
+ createScrollButtons();
+
+ // since the buttons may be visible but of the wrong size
+ // we need to do this every single time
+ _luSB->show();
+ _rdSB->show();
+ }
+ else if (_luSB && _luSB->isVisibleTo(this))
+ {
+ _luSB->hide();
+ _rdSB->hide();
+ }
+}
+
+void Panner::updateScrollButtons()
+{
+ _updateScrollButtonsTimer->start(200, true);
+}
+
+void Panner::setContentsPos(int x, int y)
+{
+ if (x < 0)
+ x = 0;
+ else if (x > (contentsWidth() - visibleWidth()))
+ x = contentsWidth() - visibleWidth();
+
+ if (y < 0)
+ y = 0;
+ else if (y > (contentsHeight() - visibleHeight()))
+ y = contentsHeight() - visibleHeight();
+
+ if (x == contentsX() && y == contentsY())
+ return;
+
+ _viewport->move(-x, -y);
+ emit contentsMoving(x, y);
+}
+
+void Panner::scrollBy(int dx, int dy)
+{
+ setContentsPos(contentsX() + dx, contentsY() + dy);
+}
+
+void Panner::resizeContents( int w, int h )
+{
+ _viewport->resize(w, h);
+ setContentsPos(contentsX(), contentsY());
+ updateScrollButtons();
+}
+
+TQPoint Panner::contentsToViewport( const TQPoint& p ) const
+{
+ return TQPoint(p.x() - contentsX() - _clipper->x(), p.y() - contentsY() - _clipper->y());
+}
+
+TQPoint Panner::viewportToContents( const TQPoint& vp ) const
+{
+ return TQPoint(vp.x() + contentsX() + _clipper->x(), vp.y() + contentsY() + _clipper->y());
+}
+
+void Panner::contentsToViewport( int x, int y, int& vx, int& vy ) const
+{
+ const TQPoint v = contentsToViewport(TQPoint(x,y));
+ vx = v.x();
+ vy = v.y();
+}
+
+void Panner::viewportToContents( int vx, int vy, int& x, int& y ) const
+{
+ const TQPoint c = viewportToContents(TQPoint(vx,vy));
+ x = c.x();
+ y = c.y();
+}
+
+void Panner::ensureVisible( int x, int y )
+{
+ ensureVisible(x, y, 50, 50);
+}
+
+void Panner::ensureVisible( int x, int y, int xmargin, int ymargin )
+{
+ int pw=visibleWidth();
+ int ph=visibleHeight();
+
+ int cx=-contentsX();
+ int cy=-contentsY();
+ int cw=contentsWidth();
+ int ch=contentsHeight();
+
+ if ( pw < xmargin*2 )
+ xmargin=pw/2;
+ if ( ph < ymargin*2 )
+ ymargin=ph/2;
+
+ if ( cw <= pw ) {
+ xmargin=0;
+ cx=0;
+ }
+ if ( ch <= ph ) {
+ ymargin=0;
+ cy=0;
+ }
+
+ if ( x < -cx+xmargin )
+ cx = -x+xmargin;
+ else if ( x >= -cx+pw-xmargin )
+ cx = -x+pw-xmargin;
+
+ if ( y < -cy+ymargin )
+ cy = -y+ymargin;
+ else if ( y >= -cy+ph-ymargin )
+ cy = -y+ph-ymargin;
+
+ if ( cx > 0 )
+ cx=0;
+ else if ( cx < pw-cw && cw>pw )
+ cx=pw-cw;
+
+ if ( cy > 0 )
+ cy=0;
+ else if ( cy < ph-ch && ch>ph )
+ cy=ph-ch;
+
+ setContentsPos( -cx, -cy );
+}
+
+bool Panner::eventFilter( TQObject *obj, TQEvent *e )
+{
+ if ( TQT_BASE_OBJECT(obj) == TQT_BASE_OBJECT(_viewport) || TQT_BASE_OBJECT(obj) == TQT_BASE_OBJECT(_clipper) )
+ {
+ switch ( e->type() )
+ {
+ case TQEvent::Resize:
+ viewportResizeEvent((TQResizeEvent *)e);
+ break;
+ case TQEvent::MouseButtonPress:
+ viewportMousePressEvent( (TQMouseEvent*)e );
+ if ( ((TQMouseEvent*)e)->isAccepted() )
+ return true;
+ break;
+ case TQEvent::MouseButtonRelease:
+ viewportMouseReleaseEvent( (TQMouseEvent*)e );
+ if ( ((TQMouseEvent*)e)->isAccepted() )
+ return true;
+ break;
+ case TQEvent::MouseButtonDblClick:
+ viewportMouseDoubleClickEvent( (TQMouseEvent*)e );
+ if ( ((TQMouseEvent*)e)->isAccepted() )
+ return true;
+ break;
+ case TQEvent::MouseMove:
+ viewportMouseMoveEvent( (TQMouseEvent*)e );
+ if ( ((TQMouseEvent*)e)->isAccepted() )
+ return true;
+ break;
+ default:
+ break;
+ }
+ }
+
+ return TQWidget::eventFilter( obj, e ); // always continue with standard event processing
+}
+
+void Panner::viewportResizeEvent( TQResizeEvent* )
+{
+}
+
+void Panner::viewportMousePressEvent( TQMouseEvent* e)
+{
+ e->ignore();
+}
+
+void Panner::viewportMouseReleaseEvent( TQMouseEvent* e )
+{
+ e->ignore();
+}
+
+void Panner::viewportMouseDoubleClickEvent( TQMouseEvent* e )
+{
+ e->ignore();
+}
+
+void Panner::viewportMouseMoveEvent( TQMouseEvent* e )
+{
+ e->ignore();
+}
diff --git a/kicker/libkicker/panner.h b/kicker/libkicker/panner.h
new file mode 100644
index 000000000..7ae68d096
--- /dev/null
+++ b/kicker/libkicker/panner.h
@@ -0,0 +1,115 @@
+/*****************************************************************
+
+Copyright (c) 1996-2000 the kicker authors. See file AUTHORS.
+
+Permission is hereby granted, free of charge, to any person obtaining a copy
+of this software and associated documentation files (the "Software"), to deal
+in the Software without restriction, including without limitation the rights
+to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+copies of the Software, and to permit persons to whom the Software is
+furnished to do so, subject to the following conditions:
+
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
+AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
+CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+******************************************************************/
+
+#ifndef __panner_h__
+#define __panner_h__
+
+#include <tqwidget.h>
+
+#include "simplebutton.h"
+
+class TQBoxLayout;
+class TQTimer;
+
+class KDE_EXPORT Panner : public TQWidget
+{
+ Q_OBJECT
+
+public:
+ Panner( TQWidget* parent, const char* name = 0 );
+ ~Panner();
+
+ TQSize minimumSizeHint() const { return TQWidget::minimumSizeHint(); }
+
+ Qt::Orientation orientation() const { return _orient; }
+ virtual void setOrientation(Qt::Orientation orientation);
+
+ TQWidget *viewport() const { return _viewport; }
+
+ TQRect contentsRect() const { return TQRect(0, 0, width(), height()); }
+
+ int contentsX() const { return _viewport ? -_viewport->x() : 0; }
+ int contentsY() const { return _viewport ? -_viewport->y() : 0; }
+ int contentsWidth() const { return _viewport ? _viewport->width() : 0; }
+ int contentsHeight() const { return _viewport ? _viewport->height() : 0; }
+ void setContentsPos(int x, int y);
+
+ int visibleWidth() const { return _clipper->width(); }
+ int visibleHeight() const { return _clipper->height(); }
+
+ void contentsToViewport( int x, int y, int& vx, int& vy ) const;
+ void viewportToContents( int vx, int vy, int& x, int& y ) const;
+ TQPoint contentsToViewport( const TQPoint& ) const;
+ TQPoint viewportToContents( const TQPoint& ) const;
+
+ void addChild(TQWidget *child) { child->show(); }
+ void removeChild(TQWidget *child) { child->hide(); }
+ int childX(TQWidget *child) const { return child->x(); }
+ int childY(TQWidget *child) const { return child->y(); }
+ void moveChild(TQWidget *child, int x, int y) { child->move(x, y); }
+
+ void ensureVisible( int x, int y );
+ void ensureVisible( int x, int y, int xmargin, int ymargin );
+
+public slots:
+ virtual void resizeContents( int w, int h );
+ void startScrollRightDown();
+ void startScrollLeftUp();
+ void stopScroll();
+ void scrollRightDown();
+ void scrollLeftUp();
+ void reallyUpdateScrollButtons();
+ void scrollBy(int dx, int dy);
+
+signals:
+ void contentsMoving(int x, int y);
+
+protected:
+ virtual bool eventFilter( TQObject *obj, TQEvent *e );
+ virtual void resizeEvent(TQResizeEvent *ev);
+ virtual void viewportResizeEvent( TQResizeEvent* );
+ virtual void viewportMousePressEvent( TQMouseEvent* );
+ virtual void viewportMouseReleaseEvent( TQMouseEvent* );
+ virtual void viewportMouseDoubleClickEvent( TQMouseEvent* );
+ virtual void viewportMouseMoveEvent( TQMouseEvent* );
+
+private:
+ void setupButtons();
+ void createScrollButtons();
+ void updateScrollButtons();
+
+ Orientation _orient;
+ TQBoxLayout *_layout;
+ SimpleArrowButton *_luSB; // Left Scroll Button
+ SimpleArrowButton *_rdSB; // Right Scroll Button
+ TQTimer *_updateScrollButtonsTimer;
+ TQTimer *_scrollTimer;
+
+ TQWidget *_clipper;
+ TQWidget *_viewport;
+ int _cwidth, _cheight;
+ int _cx, _cy;
+ int _step;
+};
+
+#endif
diff --git a/kicker/libkicker/simplebutton.cpp b/kicker/libkicker/simplebutton.cpp
new file mode 100644
index 000000000..67c90b81a
--- /dev/null
+++ b/kicker/libkicker/simplebutton.cpp
@@ -0,0 +1,289 @@
+/* This file is part of the KDE project
+ Copyright (C) 2003-2004 Nadeem Hasan <[email protected]>
+ Copyright (C) 2004-2005 Aaron J. Seigo <[email protected]>
+
+ 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; see the file COPYING. If not, write to
+ the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ Boston, MA 02110-1301, USA.
+*/
+
+#include "simplebutton.h"
+
+#include <tqpainter.h>
+#include <tqstyle.h>
+
+#include <tdeapplication.h>
+#include <kcursor.h>
+#include <kdialog.h>
+#include <tdeglobalsettings.h>
+#include <kiconeffect.h>
+#include <kicontheme.h>
+#include <kipc.h>
+#include <kstandarddirs.h>
+
+#include "kickerSettings.h"
+
+#define BUTTON_MARGIN KDialog::spacingHint()
+
+// For now link these two
+#define m_disableHighlighting m_forceStandardCursor
+
+SimpleButton::SimpleButton(TQWidget *parent, const char *name, bool forceStandardCursor)
+ : TQButton(parent, name),
+ m_highlight(false),
+ m_orientation(Qt::Horizontal),
+ m_forceStandardCursor(forceStandardCursor)
+{
+ setBackgroundOrigin( AncestorOrigin );
+
+ connect( kapp, TQT_SIGNAL( settingsChanged( int ) ),
+ TQT_SLOT( slotSettingsChanged( int ) ) );
+ connect( kapp, TQT_SIGNAL( iconChanged( int ) ),
+ TQT_SLOT( slotIconChanged( int ) ) );
+
+ kapp->addKipcEventMask( KIPC::SettingsChanged );
+ kapp->addKipcEventMask( KIPC::IconChanged );
+
+ slotSettingsChanged( TDEApplication::SETTINGS_MOUSE );
+}
+
+void SimpleButton::setPixmap(const TQPixmap &pix)
+{
+ TQButton::setPixmap(pix);
+ generateIcons();
+ update();
+}
+
+void SimpleButton::setOrientation(Qt::Orientation orientation)
+{
+ m_orientation = orientation;
+ update();
+}
+
+TQSize SimpleButton::sizeHint() const
+{
+ const TQPixmap* pm = pixmap();
+
+ if (!pm)
+ return TQButton::sizeHint();
+ else
+ return TQSize(pm->width() + BUTTON_MARGIN, pm->height() + BUTTON_MARGIN);
+}
+
+TQSize SimpleButton::minimumSizeHint() const
+{
+ const TQPixmap* pm = pixmap();
+
+ if (!pm)
+ return TQButton::minimumSizeHint();
+ else
+ return TQSize(pm->width(), pm->height());
+}
+
+void SimpleButton::drawButton( TQPainter *p )
+{
+ TQRect r(0, 0, width(), height());
+
+ if (m_disableHighlighting == TRUE) {
+ if (m_highlight || isDown() || isOn()) {
+ int flags = TQStyle::Style_Default | TQStyle::Style_Enabled;
+ if (isDown() || isOn()) flags |= TQStyle::Style_Down;
+ style().tqdrawPrimitive(TQStyle::PE_ButtonTool, p, r, colorGroup(), flags);
+ }
+ }
+
+ drawButtonLabel(p);
+}
+
+void SimpleButton::drawButtonLabel( TQPainter *p )
+{
+ if (!pixmap())
+ {
+ return;
+ }
+
+ TQPixmap pix = isEnabled() ? ((m_highlight&&(!m_disableHighlighting))? m_activeIcon : m_normalIcon) : m_disabledIcon;
+
+ if ((isOn() || isDown()) && (m_disableHighlighting == FALSE))
+ {
+ pix = TQImage(pix.convertToImage()).smoothScale(pix.width() - 2,
+ pix.height() - 2);
+ }
+
+ if (m_disableHighlighting == TRUE) {
+ pix = TQImage(pix.convertToImage()).smoothScale(pix.width() - 4,
+ pix.height() - 4);
+ }
+
+ int h = height();
+ int w = width();
+ int ph = pix.height();
+ int pw = pix.width();
+ int margin = BUTTON_MARGIN;
+ TQPoint origin(margin / 2, margin / 2);
+
+ if (ph < (h - margin))
+ {
+ origin.setY((h - ph) / 2);
+ }
+
+ if (pw < (w - margin))
+ {
+ origin.setX((w - pw) / 2);
+ }
+
+ p->drawPixmap(origin, pix);
+}
+
+void SimpleButton::generateIcons()
+{
+ if (!pixmap())
+ {
+ return;
+ }
+
+ TQImage image = pixmap()->convertToImage();
+ TDEIconEffect effect;
+
+ m_normalIcon = effect.apply(image, TDEIcon::Panel, TDEIcon::DefaultState);
+ m_activeIcon = effect.apply(image, TDEIcon::Panel, TDEIcon::ActiveState);
+ m_disabledIcon = effect.apply(image, TDEIcon::Panel, TDEIcon::DisabledState);
+
+ updateGeometry();
+}
+
+void SimpleButton::slotSettingsChanged(int category)
+{
+ if (category != TDEApplication::SETTINGS_MOUSE)
+ {
+ return;
+ }
+
+ bool changeCursor;
+ if (m_forceStandardCursor == FALSE)
+ changeCursor = TDEGlobalSettings::changeCursorOverIcon();
+ else
+ changeCursor = FALSE;
+
+ if (changeCursor)
+ {
+ setCursor(KCursor::handCursor());
+ }
+ else
+ {
+ unsetCursor();
+ }
+}
+
+void SimpleButton::slotIconChanged( int group )
+{
+ if (group != TDEIcon::Panel)
+ {
+ return;
+ }
+
+ generateIcons();
+ update();
+}
+
+void SimpleButton::enterEvent( TQEvent *e )
+{
+ if (KickerSettings::showMouseOverEffects())
+ m_highlight = true;
+
+ repaint( false );
+ TQButton::enterEvent( e );
+}
+
+void SimpleButton::leaveEvent( TQEvent *e )
+{
+ m_highlight = false;
+
+ repaint( false );
+ TQButton::enterEvent( e );
+}
+
+void SimpleButton::resizeEvent( TQResizeEvent * )
+{
+ generateIcons();
+}
+
+
+SimpleArrowButton::SimpleArrowButton(TQWidget *parent, Qt::ArrowType arrow, const char *name, bool forceStandardCursor)
+ : SimpleButton(parent, name, forceStandardCursor),
+ m_forceStandardCursor(forceStandardCursor)
+{
+ setBackgroundOrigin(AncestorOrigin);
+ _arrow = arrow;
+ _inside = false;
+}
+
+TQSize SimpleArrowButton::sizeHint() const
+{
+ return TQSize( 12, 12 );
+}
+
+void SimpleArrowButton::setArrowType(Qt::ArrowType a)
+{
+ if (_arrow != a)
+ {
+ _arrow = a;
+ update();
+ }
+}
+
+Qt::ArrowType SimpleArrowButton::arrowType() const
+{
+ return _arrow;
+}
+
+void SimpleArrowButton::drawButton( TQPainter *p )
+{
+ TQRect r(1, 1, width() - 2, height() - 2);
+
+ TQStyle::PrimitiveElement pe = TQStyle::PE_ArrowLeft;
+ switch (_arrow)
+ {
+ case Qt::LeftArrow: pe = TQStyle::PE_ArrowLeft; break;
+ case Qt::RightArrow: pe = TQStyle::PE_ArrowRight; break;
+ case Qt::UpArrow: pe = TQStyle::PE_ArrowUp; break;
+ case Qt::DownArrow: pe = TQStyle::PE_ArrowDown; break;
+ }
+
+ int flags = TQStyle::Style_Default | TQStyle::Style_Enabled;
+ if (isDown() || isOn()) flags |= TQStyle::Style_Down;
+ style().tqdrawPrimitive(pe, p, r, colorGroup(), flags);
+
+ if (m_forceStandardCursor) {
+ SimpleButton::drawButton(p);
+ }
+}
+
+void SimpleArrowButton::enterEvent( TQEvent *e )
+{
+ _inside = true;
+ SimpleButton::enterEvent( e );
+ update();
+}
+
+void SimpleArrowButton::leaveEvent( TQEvent *e )
+{
+ _inside = false;
+ SimpleButton::leaveEvent( e );
+ update();
+}
+
+#include "simplebutton.moc"
+
+// vim:ts=4:sw=4:et
diff --git a/kicker/libkicker/simplebutton.h b/kicker/libkicker/simplebutton.h
new file mode 100644
index 000000000..bbfcbd79d
--- /dev/null
+++ b/kicker/libkicker/simplebutton.h
@@ -0,0 +1,91 @@
+/* This file is part of the KDE project
+ Copyright (C) 2003-2004 Nadeem Hasan <[email protected]>
+ Copyright (C) 2004-2005 Aaron J. Seigo <[email protected]>
+
+ 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; see the file COPYING. If not, write to
+ the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ Boston, MA 02110-1301, USA.
+*/
+
+#ifndef SIMPLEBUTTON_H
+#define SIMPLEBUTTON_H
+
+#include <tqbutton.h>
+#include <tqpixmap.h>
+
+#include <kdemacros.h>
+
+class KDE_EXPORT SimpleButton : public TQButton
+{
+ Q_OBJECT
+
+ public:
+ SimpleButton(TQWidget *parent, const char *name = 0, bool forceStandardCursor = FALSE);
+ void setPixmap(const TQPixmap &pix);
+ void setOrientation(Qt::Orientation orientaton);
+ TQSize sizeHint() const;
+ TQSize minimumSizeHint() const;
+
+ protected:
+ void drawButton( TQPainter *p );
+ void drawButtonLabel( TQPainter *p );
+ void generateIcons();
+
+ void enterEvent( TQEvent *e );
+ void leaveEvent( TQEvent *e );
+ void resizeEvent( TQResizeEvent *e );
+
+ protected slots:
+ virtual void slotSettingsChanged( int category );
+ virtual void slotIconChanged( int group );
+
+ private:
+ bool m_highlight;
+ TQPixmap m_normalIcon;
+ TQPixmap m_activeIcon;
+ TQPixmap m_disabledIcon;
+ Qt::Orientation m_orientation;
+ bool m_forceStandardCursor;
+ class SimpleButtonPrivate;
+ SimpleButtonPrivate* d;
+};
+
+class KDE_EXPORT SimpleArrowButton: public SimpleButton
+{
+ Q_OBJECT
+
+ public:
+ SimpleArrowButton(TQWidget *parent = 0, Qt::ArrowType arrow = Qt::UpArrow, const char *name = 0, bool forceStandardCursor = FALSE);
+ virtual ~SimpleArrowButton() {};
+ TQSize sizeHint() const;
+
+ protected:
+ virtual void enterEvent( TQEvent *e );
+ virtual void leaveEvent( TQEvent *e );
+ virtual void drawButton(TQPainter *p);
+ Qt::ArrowType arrowType() const;
+
+ public slots:
+ void setArrowType(Qt::ArrowType a);
+
+ private:
+ Qt::ArrowType _arrow;
+ bool m_forceStandardCursor;
+ bool _inside;
+};
+
+
+#endif // HIDEBUTTON_H
+
+// vim:ts=4:sw=4:et