summaryrefslogtreecommitdiffstats
path: root/kicker/applets/menu
diff options
context:
space:
mode:
authortoma <toma@283d02a7-25f6-0310-bc7c-ecb5cbfe19da>2009-11-25 17:56:58 +0000
committertoma <toma@283d02a7-25f6-0310-bc7c-ecb5cbfe19da>2009-11-25 17:56:58 +0000
commit4aed2c8219774f5d797760606b8489a92ddc5163 (patch)
tree3f8c130f7d269626bf6a9447407ef6c35954426a /kicker/applets/menu
downloadtdebase-4aed2c8219774f5d797760606b8489a92ddc5163.tar.gz
tdebase-4aed2c8219774f5d797760606b8489a92ddc5163.zip
Copy the KDE 3.5 branch to branches/trinity for new KDE 3.5 features.
BUG:215923 git-svn-id: svn://anonsvn.kde.org/home/kde/branches/trinity/kdebase@1054174 283d02a7-25f6-0310-bc7c-ecb5cbfe19da
Diffstat (limited to 'kicker/applets/menu')
-rw-r--r--kicker/applets/menu/Makefile.am20
-rw-r--r--kicker/applets/menu/menuapplet.cpp511
-rw-r--r--kicker/applets/menu/menuapplet.desktop128
-rw-r--r--kicker/applets/menu/menuapplet.h258
4 files changed, 917 insertions, 0 deletions
diff --git a/kicker/applets/menu/Makefile.am b/kicker/applets/menu/Makefile.am
new file mode 100644
index 000000000..5bfaeee18
--- /dev/null
+++ b/kicker/applets/menu/Makefile.am
@@ -0,0 +1,20 @@
+INCLUDES = $(all_includes)
+
+kde_module_LTLIBRARIES = menu_panelapplet.la
+
+menu_panelapplet_la_SOURCES = menuapplet.cpp menuapplet.skel
+
+noinst_HEADERS = menuapplet.h
+
+menu_panelapplet_la_METASOURCES = AUTO
+
+lnkdir = $(kde_datadir)/kicker/applets
+lnk_DATA = menuapplet.desktop
+
+EXTRA_DIST = $(lnk_DATA)
+
+menu_panelapplet_la_LDFLAGS = -module $(KDE_PLUGIN) $(all_libraries)
+menu_panelapplet_la_LIBADD = $(LIB_KDEUI)
+
+messages:
+ $(XGETTEXT) *.cpp *.h -o $(podir)/kmenuapplet.pot
diff --git a/kicker/applets/menu/menuapplet.cpp b/kicker/applets/menu/menuapplet.cpp
new file mode 100644
index 000000000..ae10614c6
--- /dev/null
+++ b/kicker/applets/menu/menuapplet.cpp
@@ -0,0 +1,511 @@
+/*****************************************************************
+
+Copyright (c) 2002 Siegfried Nijssen <snijssen@liacs.nl>
+Copyright (c) 2003 Lubos Lunak <l.lunak@suse.cz>
+
+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.
+
+******************************************************************/
+
+#define _MENUAPPLET_CPP_
+
+#include "menuapplet.h"
+
+#include <qlayout.h>
+#include <qtooltip.h>
+#include <qvariant.h> // avoid X11 #define's
+
+#include <kapplication.h>
+#include <kconfig.h>
+#include <kdebug.h>
+#include <kglobal.h>
+#include <klocale.h>
+#include <kwin.h>
+#include <kwinmodule.h>
+
+#include <netwm.h>
+
+#include <X11/Xlib.h>
+
+/*
+
+ KMenuBar from KDE3.1 and older won't work very well with this applet.
+ This is because QMenuBar tries really hard to keep its preffered size,
+ se even if the X window for the menubar has the size enforced by this
+ applet, Qt thinks it has the size Qt wants. This results in parts
+ of the menubar not being repainted. Also, old KMenuBar always forced
+ with to be the width of the screen, so even if the menubar has only
+ few entries, this applet will still indicate the menubar doesn't
+ fit completely in it. There's no way to fix this, besides upgrading
+ to KDE3.2.
+
+*/
+
+
+extern Time qt_x_time;
+
+extern "C"
+{
+ KDE_EXPORT KPanelApplet* init( QWidget* parent_P, const QString& configFile_P )
+ {
+ KGlobal::locale()->insertCatalogue("kmenuapplet");
+ return new KickerMenuApplet::Applet( configFile_P, parent_P );
+ }
+}
+
+namespace KickerMenuApplet
+{
+
+static const int MOVE_DIFF = 100; // size increment for left/right menu moving
+static const int GROW_WIDTH = 10; // width of grow buttons
+
+const long SUPPORTED_WINDOW_TYPES = NET::NormalMask | NET::DesktopMask | NET::DockMask
+ | NET::ToolbarMask | NET::MenuMask | NET::DialogMask | NET::OverrideMask
+ | NET::TopMenuMask | NET::UtilityMask | NET::SplashMask;
+
+Applet::Applet( const QString& configFile_P, QWidget* parent_P )
+ : KPanelApplet( configFile_P, Normal, 0, parent_P, "menuapplet" ),
+ DCOPObject( "menuapplet" ),
+ module( NULL ),
+ active_menu( NULL ),
+ selection( NULL ),
+ selection_watcher( NULL ),
+ desktop_menu( false ),
+ topEdgeOffset( 0 )
+ {
+ setBackgroundOrigin(AncestorOrigin);
+ dcopclient.registerAs( "menuapplet", false );
+ // toolbarAppearanceChanged(int) is sent when changing macstyle
+ connect( kapp, SIGNAL( toolbarAppearanceChanged( int )),
+ this, SLOT( readSettings()));
+ claimSelection();
+ readSettings();
+ updateTopEdgeOffset();
+ }
+
+Applet::~Applet()
+ {
+ lostSelection(); // release all menu's before really loosing the selection
+ delete selection;
+ delete selection_watcher;
+ delete module;
+ KGlobal::locale()->removeCatalogue("kmenuapplet");
+ }
+
+void Applet::windowAdded( WId w_P )
+ {
+ NETWinInfo info( qt_xdisplay(), w_P, qt_xrootwin(), NET::WMWindowType );
+ if( info.windowType( SUPPORTED_WINDOW_TYPES ) != NET::TopMenu )
+ return;
+// kdDebug() << "embedding:" << w_P << endl;
+ Window transient_for = KWin::transientFor( w_P );
+ if( transient_for == None )
+ return;
+ MenuEmbed* embed;
+ if( transient_for == qt_xrootwin())
+ {
+ embed = new MenuEmbed( transient_for, true, this );
+ }
+ else
+ {
+ KWin::WindowInfo info2 = KWin::windowInfo( transient_for, NET::WMWindowType );
+ embed = new MenuEmbed( transient_for,
+ info2.windowType( SUPPORTED_WINDOW_TYPES ) == NET::Desktop, this );
+ }
+ embed->hide();
+ embed->move( 0, -topEdgeOffset );
+ embed->resize( embed->width(), height() + topEdgeOffset );
+ embed->embed( w_P );
+ if( embed->embeddedWinId() == None )
+ {
+ delete embed;
+ return;
+ }
+ menus.append( embed );
+ // in case the app mapped its menu after its mainwindow, check which menu should be shown
+ activeWindowChanged( module->activeWindow());
+ }
+
+// - if the active window has its topmenu -> show the menu
+// - if desktop menu is enabled (i.e. explicitly in kdesktop) :
+// - show it
+// - otherwise show nothing
+void Applet::activeWindowChanged( WId w_P )
+ {
+// kdDebug() << "active:" << w_P << endl;
+ for( WId window = w_P;
+ window != None;
+ window = tryTransientFor( window ))
+ {
+ for( QValueList< MenuEmbed* >::ConstIterator it = menus.begin();
+ it != menus.end();
+ ++it )
+ {
+ if( window == (*it)->mainWindow())
+ {
+ activateMenu( *it );
+ return;
+ }
+ }
+ }
+// kdDebug() << "no active" << endl;
+ // No menu for active window found - if desktop menu
+ // (in kdesktoprc) is enabled, use kdesktop's menu instead of none.
+ bool try_desktop = desktop_menu;
+ if( !try_desktop && w_P != None )
+ { // also use the desktop menu if the active window is desktop
+ KWin::WindowInfo info = KWin::windowInfo( w_P, NET::WMWindowType );
+ if( info.windowType( SUPPORTED_WINDOW_TYPES ) == NET::Desktop )
+ try_desktop = true;
+ }
+ if( try_desktop )
+ {
+ for( QValueList< MenuEmbed* >::ConstIterator it = menus.begin();
+ it != menus.end();
+ ++it )
+ {
+ if( (*it)->isDesktopMenu())
+ {
+ activateMenu( *it );
+ return;
+ }
+ }
+ }
+ activateMenu( NULL );
+ }
+
+void Applet::activateMenu( MenuEmbed* embed_P )
+ {
+ if( embed_P != active_menu )
+ {
+// kdDebug() << "activate:" << embed_P << endl;
+ if( active_menu != NULL )
+ active_menu->hide();
+ active_menu = embed_P;
+ if( active_menu != NULL )
+ {
+ active_menu->show();
+ //if (embed->isDesktopMenu())
+ {
+ active_menu->setMinimumSize( width(), height() + topEdgeOffset );
+ }
+ }
+ emit updateLayout();
+ }
+
+ setBackground();
+ }
+
+void Applet::updateMenuGeometry( MenuEmbed* embed )
+ {
+ if( embed == active_menu )
+ emit updateLayout();
+ }
+
+// If there's no menu for the window, try finding menu for its mainwindow
+// (where the window's WM_TRANSIENT_FOR property points).
+// If the window is modal (_NET_WM_STATE_MODAL), stop.
+WId Applet::tryTransientFor( WId w_P )
+ {
+ KWin::WindowInfo info = KWin::windowInfo( w_P, NET::WMState );
+ if( info.state() & NET::Modal )
+ return None;
+ WId ret = KWin::transientFor( w_P );
+ if( ret == qt_xrootwin())
+ ret = None;
+ return ret;
+ }
+
+void Applet::menuLost( MenuEmbed* embed )
+ {
+ for( QValueList< MenuEmbed* >::Iterator it = menus.begin();
+ it != menus.end();
+ ++it )
+ {
+ if( *it == embed )
+ {
+ menus.remove( it );
+ embed->deleteLater();
+// kdDebug() << "deleting:" << (*it)->mainWindow() << endl;
+ if( embed == active_menu )
+ {
+ active_menu = NULL;
+ // trigger selecting new active menu
+ activeWindowChanged( module->activeWindow());
+ }
+ return;
+ }
+ }
+ }
+
+void Applet::positionChange( Position )
+ {
+ updateTopEdgeOffset();
+ }
+
+// Detect mouse movement at the top screen edge also if the menubar
+// has a popup open - in such case, Qt has a grab, and this avoids
+// Kicker's FittsLawFrame. Therefore move the menubar a bit higher,
+// so that it actually is positioned exactly at the screen edge
+// (i.e. at a negative y coordinate within this applet, due to
+// Kicker's frame).
+void Applet::updateTopEdgeOffset()
+ {
+ QPoint p = topLevelWidget()->mapToGlobal( QPoint( 0, 0 ));
+ if( p.y() <= 2 ) // 2 = work also when running in appletproxy
+ topEdgeOffset = mapToGlobal( QPoint( 0, 0 )).y() - p.y();
+ else
+ topEdgeOffset = 0;
+ if( active_menu != NULL )
+ active_menu->move( active_menu->x(), -topEdgeOffset );
+ }
+
+void Applet::paletteChange(const QPalette & /* oldPalette */)
+{
+ setBackground();
+}
+
+void Applet::moveEvent( QMoveEvent* )
+{
+ setBackground();
+}
+
+void Applet::setBackground()
+{
+ if (active_menu)
+ active_menu->setBackground();
+}
+
+void Applet::claimSelection()
+ {
+ assert( selection == NULL );
+ selection = new KSelectionOwner( makeSelectionAtom(), DefaultScreen( qt_xdisplay()));
+// force taking the selection, but don't kill previous owner
+ if( selection->claim( true, false ))
+ {
+ delete selection_watcher;
+ selection_watcher = NULL;
+ connect( selection, SIGNAL( lostOwnership()), SLOT( lostSelection()));
+ module = new KWinModule;
+ connect( module, SIGNAL( windowAdded( WId )), this, SLOT( windowAdded( WId )));
+ connect( module, SIGNAL( activeWindowChanged( WId )),
+ this, SLOT( activeWindowChanged( WId )));
+ QValueList< WId > windows = module->windows();
+ for( QValueList< WId >::ConstIterator it = windows.begin();
+ it != windows.end();
+ ++it )
+ windowAdded( *it );
+ activeWindowChanged( module->activeWindow());
+ }
+ else
+ lostSelection();
+ }
+
+void Applet::lostSelection()
+ {
+ if( selection == NULL )
+ return;
+// kdDebug() << "lost selection" << endl;
+ for( QValueList< MenuEmbed* >::ConstIterator it = menus.begin();
+ it != menus.end();
+ ++it )
+ delete (*it); // delete all MenuEmbed's = release all menus
+ menus.clear();
+ active_menu = NULL;
+ if( selection_watcher == NULL )
+ {
+ selection_watcher = new KSelectionWatcher( makeSelectionAtom(), DefaultScreen( qt_xdisplay()));
+ connect( selection_watcher, SIGNAL( lostOwner()), this, SLOT( claimSelection()));
+ }
+ delete module;
+ module = NULL;
+ selection->deleteLater();
+ selection = NULL;
+ // selection_watcher stays
+ }
+
+void Applet::readSettings()
+ {
+ KConfig cfg( "kdesktoprc", true );
+ cfg.setGroup( "Menubar" );
+ desktop_menu = cfg.readBoolEntry( "ShowMenubar", false );
+ cfg.setGroup( "KDE" );
+ if( cfg.readBoolEntry( "macStyle", false ) || desktop_menu )
+ QToolTip::remove( this );
+ else
+ QToolTip::add( this, i18n(
+ "You do not appear to have enabled the standalone menubar; "
+ "enable it in the Behavior control module for desktop." ));
+ if( !isDisabled() && active_menu == NULL )
+ activeWindowChanged( module->activeWindow()); //enforce desktop_menu
+ }
+
+void Applet::configure()
+ {
+ readSettings();
+ }
+
+int Applet::widthForHeight( int ) const
+ {
+ if (active_menu)
+ return active_menu->width();
+ return 0; // we're stretch applet
+ }
+
+int Applet::heightForWidth( int ) const
+ {
+ // *shrug* running this applet in vertical mode is a bad idea anyway
+ return 50;
+ }
+
+static Atom selection_atom = None;
+static Atom msg_type_atom = None;
+
+static
+void initAtoms()
+ {
+ char nm[ 100 ];
+ sprintf( nm, "_KDE_TOPMENU_OWNER_S%d", DefaultScreen( qt_xdisplay()));
+ char nm2[] = "_KDE_TOPMENU_MINSIZE";
+ char* names[ 2 ] = { nm, nm2 };
+ Atom atoms[ 2 ];
+ XInternAtoms( qt_xdisplay(), names, 2, False, atoms );
+ selection_atom = atoms[ 0 ];
+ msg_type_atom = atoms[ 1 ];
+ }
+
+Atom Applet::makeSelectionAtom()
+ {
+ if( selection_atom == None )
+ initAtoms();
+ return selection_atom;
+ }
+
+MenuEmbed::MenuEmbed( WId mainwindow_P, bool desktop_P,
+ QWidget* parent_P, const char* name_P )
+ : QXEmbed( parent_P, name_P ),
+ main_window( mainwindow_P ),
+ desktop( desktop_P )
+ {
+ setAutoDelete( false );
+ }
+
+void MenuEmbed::windowChanged( WId w_P )
+ {
+ if( w_P == None )
+ static_cast< Applet* >( parent())->menuLost( this );
+ }
+
+bool MenuEmbed::x11Event( XEvent* ev_P )
+ {
+ if( ev_P->type == ConfigureRequest
+ && ev_P->xconfigurerequest.window == embeddedWinId()
+ && ev_P->xconfigurerequest.value_mask & ( CWWidth | CWHeight ))
+ {
+ XConfigureRequestEvent& ev = ev_P->xconfigurerequest;
+ QSize new_size = size();
+ if( ev.value_mask & CWWidth )
+ new_size.setWidth( ev.width );
+ if( ev.value_mask & CWHeight )
+ new_size.setHeight( ev.height );
+ // resize when the embedded window resizes (still obey min size)
+// kdDebug() << "RES:" << embeddedWinId() << ":" << ev.width << ":" << ev.height << endl;
+ if( ev.width != width() || ev.height != height())
+ {
+ resize( ev.width, ev.height );
+ static_cast< Applet* >( parent())->updateMenuGeometry( this );
+ }
+ sendSyntheticConfigureNotifyEvent();
+// int x, y;
+// unsigned int w, h, d, b;
+// Window root;
+// XGetGeometry( qt_xdisplay(), embeddedWinId(), &root, &x, &y, &w, &h, &b, &d );
+// kdDebug() << "RES3:" << width() << ":" << height() << ":" << w << ":" << h << endl;
+ return true;
+ }
+ return QXEmbed::x11Event( ev_P );
+ }
+
+void MenuEmbed::sendSyntheticConfigureNotifyEvent()
+{
+ QPoint globalPos = mapToGlobal(QPoint(0,0));
+ if (embeddedWinId()) {
+ XConfigureEvent c;
+ memset(&c, 0, sizeof(c));
+ c.type = ConfigureNotify;
+ c.display = qt_xdisplay();
+ c.send_event = True;
+ c.event = embeddedWinId();
+ c.window = winId();
+ c.x = globalPos.x();
+ c.y = globalPos.y();
+ c.width = width();
+ c.height = height();
+ c.border_width = 0;
+ c.above = None;
+ c.override_redirect = 0;
+ XSendEvent(qt_xdisplay(), c.event, true, StructureNotifyMask, (XEvent*)&c);
+ }
+}
+
+void MenuEmbed::setMinimumSize( int w, int h )
+{
+ QXEmbed::setMinimumSize( w, h );
+ // tell the menubar also the allowed minimum size
+ // the applet won't allow resizing to smaller size
+ if( embeddedWinId() != None )
+ {
+// kdDebug() << "RES2:" << width() << ":" << height() << ":" << minimumWidth() << ":" << minimumHeight() << endl;
+ XEvent ev;
+ ev.xclient.display = qt_xdisplay();
+ ev.xclient.type = ClientMessage;
+ ev.xclient.window = embeddedWinId();
+ assert( msg_type_atom != None );
+ ev.xclient.message_type = msg_type_atom;
+ ev.xclient.format = 32;
+ ev.xclient.data.l[0] = qt_x_time;
+ ev.xclient.data.l[1] = minimumWidth();
+ ev.xclient.data.l[2] = minimumHeight();
+ ev.xclient.data.l[3] = 0;
+ ev.xclient.data.l[4] = 0;
+ XSendEvent( qt_xdisplay(), embeddedWinId(), False, NoEventMask, &ev );
+ }
+}
+
+void MenuEmbed::setBackground()
+{
+ const QPixmap *pbg = parentWidget()->backgroundPixmap();
+
+ if (pbg)
+ {
+ QPixmap bg(width(), height());
+ bg.fill(parentWidget(), pos());
+ setPaletteBackgroundPixmap(bg);
+ setBackgroundOrigin(WidgetOrigin);
+ }
+ else
+ unsetPalette();
+
+ hide();
+ show();
+ //XClearArea(x11Display(), embeddedWinId(), 0, 0, 0, 0, True);
+}
+
+} // namespace
+
+#include "menuapplet.moc"
diff --git a/kicker/applets/menu/menuapplet.desktop b/kicker/applets/menu/menuapplet.desktop
new file mode 100644
index 000000000..741c2ae29
--- /dev/null
+++ b/kicker/applets/menu/menuapplet.desktop
@@ -0,0 +1,128 @@
+[Desktop Entry]
+Hidden=true
+Type=Plugin
+Name=Menu
+Name[af]=Kieslys
+Name[ar]=قائمة
+Name[be]=Меню
+Name[bg]=Меню
+Name[bn]=মেনু
+Name[br]=Meuziad
+Name[bs]=Meni
+Name[ca]=Menú
+Name[cs]=Nabídka
+Name[cy]=Dewislen
+Name[de]=Menü
+Name[el]=Μενού
+Name[eo]=Menuo
+Name[es]=Menú
+Name[et]=Menüü
+Name[eu]=Menua
+Name[fa]=گزینگان
+Name[fi]=Valikko
+Name[ga]=Roghchlár
+Name[he]=תפריט
+Name[hi]=मेन्यू
+Name[hr]=Izbornik
+Name[hu]=Menü
+Name[is]=Valmynd
+Name[ja]=メニュー
+Name[ka]=მენიუ
+Name[kk]=Мәзір
+Name[km]=ម៉ឺនុយ
+Name[lt]=Meniu
+Name[lv]=Izvēlne
+Name[mk]=Мени
+Name[mn]=Цэс
+Name[nb]=Meny
+Name[nds]=Menü
+Name[ne]=मेनु
+Name[nn]=Meny
+Name[pa]=ਮੇਨੂ
+Name[ro]=Meniu
+Name[ru]=Меню
+Name[rw]=Ibikubiyemo
+Name[sl]=Meni
+Name[sr]=Мени
+Name[sr@Latn]=Meni
+Name[sv]=Meny
+Name[ta]=பட்டி
+Name[te]=పట్టి
+Name[tg]=Меню
+Name[th]=เมนู
+Name[tr]=Menü
+Name[tt]=Saylaq
+Name[uk]=Меню
+Name[uz]=Menyu
+Name[uz@cyrillic]=Меню
+Name[vi]=Thực đơn
+Name[wa]=Dressêye
+Name[zh_CN]=菜单
+Name[zh_TW]=選單
+Comment=Applet embedding standalone menubars
+Comment[ar]=بريمج يضمّن أشرطة قوائم منفردة بذاتها
+Comment[be]=Аплет з убудаваным меню
+Comment[bg]=Системен панел за вграждане на самостоятелни менюта
+Comment[bn]=আলাদা মেনুবার ধারণ করার উপযোগী অ্যাপলেট
+Comment[bs]=Applet koji uvezuje samostalne menije
+Comment[ca]=Un applet encastat estàndard per a les barres de menú
+Comment[cs]=Applet pohlcující samostatné lišty s nabídkami
+Comment[csb]=Aplet zbiérający ùwòlnioné lëstwë menu
+Comment[cy]=Rhaglennig sy'n mewn-adeiladu bariau dewislen unigol
+Comment[da]=Applet der indlejrer alenestående menulinjer
+Comment[de]=Programm zur Einbettung einzelner Menüleisten
+Comment[el]=Μικροεφαρμογή που ενσωματώνει αυτόνομες γραμμές μενού
+Comment[eo]=Aplikaĵeniganta solfunkcia menuzono
+Comment[es]=Una miniaplicación que incluye barras de menú autónomas
+Comment[et]=Aplett, mis põimib endasse isseisvaid menüüribasid
+Comment[eu]=Menu-barrak txertaturik dituen appleta
+Comment[fa]=میله گزینگان خوداتکای نهفتۀ برنامک
+Comment[fi]=Sovelma, joka pystyy upottamaan yksittäisiä valikkorivejä
+Comment[fr]=Une applet intégrant les barres de menu externes
+Comment[fy]=Een applet die lossteande menubalken ynslút
+Comment[gl]=Barras de menu estándar con incrustamento de applets
+Comment[he]=שורת תפריטים משובצת יישומונים העומדת בפני עצמה
+Comment[hi]=ऐपलेट एम्बेडिंग स्टैंडअलोन मेन्यूबार्स
+Comment[hr]=Samostalne trake izbornika s ugrađenim apletima
+Comment[hu]=Kisalkalmazásokat tartalmazni képes önálló menüsorok
+Comment[is]=Smáforrit sem byggir inn sjálfstæðar valmyndastikur
+Comment[it]=Applet per inglobare le barre dei menu
+Comment[ja]=単独のメニューバーに組み込むアプレット
+Comment[ka]=აპლეტი, რომელიც ამატებს ავტონომიურ პანელებს
+Comment[kk]=Бөлек мәзір панельдерді құру апплеті
+Comment[km]=របារ​ម៉ឺនុយ​នៅ​តែ​ឯង​ដែល​បង្កប់​ក្នុង​អាប់ភ្លេត
+Comment[lt]=Įskiepis, rodantis atskiras meniu dalis
+Comment[lv]=Sīklietotne, kas iegulda pastāvīgas izvēlnes
+Comment[mk]=Аплет кој ги вгнездува самостојните менија
+Comment[ms]=Menu bar tersendiri pembenaman aplet
+Comment[mt]=Applet li fiha menubars indipendenti
+Comment[nb]=Et panelprogram som bygger inn frittstående menylinjer
+Comment[nds]=Lüttprogramm för't Inbetten vun enkelte Warktüüchbalkens
+Comment[ne]=एप्लेट सम्मिलित गर्ने स्ट्यान्डअलोन मेनुपट्टी
+Comment[nl]=Een applet die losstaande menubalken insluit
+Comment[nn]=Eit panelprogram som kan innehalda frittståande menylinjer
+Comment[pa]=ਇੱਕਲੀ ਮੇਨੂਪੱਟੀ ਐਪਲਿਟ
+Comment[pl]=Aplet zbierający uwolnione paski menu
+Comment[pt]=Uma 'applet' que incorpora barras de menu autónomas
+Comment[pt_BR]=Mini-aplicativo para embutir barras de menu ao painel
+Comment[ro]=O miniaplicație ce înglobează bare de meniu
+Comment[ru]=Аплет, встраивающий автономные панели меню
+Comment[rw]=Apuleti zifitemo umwanya-ibikubiyemo wigenga
+Comment[se]=Prográmmaš mii vuojuha oktanas fálloholggaid
+Comment[sk]=Applet pre samostatné pruhy menu
+Comment[sl]=Vstavek, ki vključuje samostojne menijske vrstice
+Comment[sr]=Аплет за уграђивање самосталних менија
+Comment[sr@Latn]=Aplet za ugrađivanje samostalnih menija
+Comment[sv]=Miniprogram för inbäddning av fristående menyer
+Comment[ta]=குறுநிரல் பொதிந்த தனியான மெனுபட்டிகள்
+Comment[th]=แอพเพล็ตสำหรับฝังแถบเมนูลงพาเนล
+Comment[tr]=Yalnız menü çubuklarını gömen uygulamacık 
+Comment[tt]=Ayırım torğan saylaq-tirälär berläşterüçe applet
+Comment[uk]=Аплет вбудовних окремих смужок меню
+Comment[vi]=Tiểu ứng dụng nhúng các thanh thực đơn đứng riêng
+Comment[wa]=Aplikete po fé ravaler des bårs di dressêye totes seules
+Comment[zh_CN]=嵌入独立菜单栏的小程序
+Comment[zh_TW]=單獨置於面板中的選單列
+
+X-KDE-Library=menu_panelapplet
+X-KDE-UniqueApplet=true
diff --git a/kicker/applets/menu/menuapplet.h b/kicker/applets/menu/menuapplet.h
new file mode 100644
index 000000000..8374e897b
--- /dev/null
+++ b/kicker/applets/menu/menuapplet.h
@@ -0,0 +1,258 @@
+/*****************************************************************
+
+Copyright (c) 2002 Siegfried Nijssen <snijssen@liacs.nl>
+Copyright (c) 2003 Lubos Lunak <l.lunak@suse.cz>
+
+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 _MENUAPPLET_H_
+#define _MENUAPPLET_H_
+
+#include <assert.h>
+
+#include <qvaluelist.h>
+#include <qevent.h>
+#include <qxembed.h>
+
+#include <kpanelapplet.h>
+#include <kmanagerselection.h>
+
+#include <dcopobject.h>
+#include <dcopclient.h>
+
+#include <karrowbutton.h>
+
+class KWinModule;
+
+namespace KickerMenuApplet
+{
+
+class MenuEmbed;
+
+/**
+ * @short A central menu bar
+ *
+ * @description All status change, such as when an window is activated,
+ * a new window popped up, etc, is received via @ref KWin::WindowInfo and @ref
+ * NETWinInfo. Status changes for X selections are done via KSelectionWatcher.
+ *
+ * How it works in broad terms: KickerMenuApplet gets notified as soon a window
+ * changes(a new pops up etc.) and accordingly updates the list @ref menus,
+ * which contains all known menus. When a new window gains focus, it looks up the
+ * correct MenuEmbed in @ref menus, and then switches to that one.
+ *
+ * The documentation is a bit rusty -- read it with a critical eye.
+ *
+ * @author Siegfried Nijssen <snijssen@liacs.nl>
+ * @author Lubos Lunak <l.lunak@suse.cz>
+ */
+
+class Applet : public KPanelApplet, public DCOPObject
+{
+ Q_OBJECT
+ K_DCOP
+
+k_dcop:
+
+ /**
+ * Called by the Kicker configuration(KCM). Does in turn call
+ * readSettings().
+ */
+ ASYNC configure();
+
+public:
+ Applet( const QString& configFile, QWidget *parent );
+ virtual ~Applet();
+ virtual int widthForHeight( int height ) const;
+ virtual int heightForWidth( int width ) const;
+
+ /**
+ * Looks up @param embed in @ref menus, and removes it.
+ */
+ void menuLost( MenuEmbed* embed );
+ void updateMenuGeometry( MenuEmbed* embed );
+ void setBackground();
+
+protected:
+
+ virtual void paletteChange(const QPalette& );
+ virtual void positionChange( Position p );
+ virtual void moveEvent(QMoveEvent *);
+
+private slots:
+
+ /**
+ * Called each time a window is added. When the selection is
+ * initially claimed, it is called for every window. It does the big
+ * work, and does the embedding with MenuEmbed.
+ */
+ void windowAdded( WId w );
+
+ /**
+ * Finds @p w's menubar in @see menus, and then activates it.
+ *
+ * @param w the activated window.
+ */
+ void activeWindowChanged( WId w );
+
+ /**
+ * Called when the selection(selection_atom) is lost. Deletes the
+ * embedded menus, and starts listening for the selection again.
+ *
+ */
+ void lostSelection();
+
+ /**
+ * Reads whether a central menu bar should be used or not, basically.
+ */
+ void readSettings();
+ void claimSelection();
+
+private:
+
+ /**
+ * Returns true if the selection is Not owned. That is, the menu applet
+ * isn't "running" and is listening for the selection to be released.
+ */
+ bool isDisabled() const;
+
+ WId tryTransientFor( WId w );
+
+ /**
+ * Does some sanity checks, and then sets active_menu to @param embed.
+ */
+ void activateMenu( MenuEmbed* embed );
+
+ /**
+ * Creates msg_type_atom and selection_atom, and returns the latter.
+ */
+ static Atom makeSelectionAtom();
+ void updateTopEdgeOffset();
+ KWinModule* module;
+
+ /**
+ * List of all known menus.
+ */
+ QValueList< MenuEmbed* > menus;
+
+ /**
+ * A pointer to the current active menu, which is member
+ * of @ref menus.
+ */
+ MenuEmbed* active_menu;
+
+ KSelectionOwner* selection;
+
+ /**
+ * Only the messenger. Dispatches signals to claimSelection().
+ */
+ KSelectionWatcher* selection_watcher;
+
+ /**
+ * Whether the Desktop menu should be used, when a window
+ * with no menu is used.
+ */
+ bool desktop_menu;
+ DCOPClient dcopclient;
+
+ /**
+ * The distance to the top of the screen.
+ */
+ int topEdgeOffset;
+};
+
+/**
+ *
+ * @author Siegfried Nijssen <snijssen@liacs.nl>
+ * @author Lubos Lunak <l.lunak@suse.cz>
+ */
+class MenuEmbed
+ : public QXEmbed
+{
+ Q_OBJECT
+
+public:
+
+ /**
+ * Default constructor
+ *
+ * @param mainwindow window ID for the window to be plugged
+ * @param desktop true if @p mainwindow is the desktop
+ */
+ MenuEmbed( WId mainwindow, bool desktop,
+ QWidget* parent = NULL, const char* name = NULL );
+
+ void setBackground();
+
+ /**
+ * @returns the window ID for the handled window.
+ */
+ WId mainWindow() const;
+
+ /**
+ */
+ bool isDesktopMenu() const;
+ virtual void setMinimumSize( int w, int h );
+ void setMinimumSize( const QSize& s ) { setMinimumSize( s.width(), s.height()); }
+
+protected:
+
+ /**
+ * When @p w is None, that is the embedded window was lost, it calls
+ * menuLost() such that the this is deleted from @ref menus list.
+ */
+ virtual void windowChanged( WId w );
+
+ virtual bool x11Event( XEvent* ev );
+
+private:
+
+ void sendSyntheticConfigureNotifyEvent();
+ WId main_window;
+
+ /**
+ * If the window is the desktop window.
+ */
+ bool desktop;
+};
+
+inline
+bool Applet::isDisabled() const
+{
+ assert( ( selection == NULL && selection_watcher != NULL )
+ || ( selection != NULL && selection_watcher == NULL ));
+ return selection == NULL;
+}
+
+inline
+WId MenuEmbed::mainWindow() const
+{
+ return main_window;
+}
+
+inline
+bool MenuEmbed::isDesktopMenu() const
+{
+ return desktop;
+}
+
+} // namespace
+
+#endif