another approach: here i use the old math panel (the one that works for everyone)
and draw a tear-off widget ourselves works fine for me so am seeking volunteers (esp mac and linux)! any takers? ;-)
Index: src/frontends/qt4/IconPalette.cpp =================================================================== --- src/frontends/qt4/IconPalette.cpp (revision 18822) +++ src/frontends/qt4/IconPalette.cpp (working copy) @@ -25,99 +25,82 @@ #include <QStyle> #include <QStyleOptionFrame> #include <QMouseEvent> +#include <QVBoxLayout> namespace lyx { namespace frontend { -#if QT_VERSION >= 0x040200 - - -class MathButton : public QToolButton +TearOff::TearOff(QWidget * parent) + : QWidget(parent) { -public: - MathButton(QWidget * parent = 0) {} - void mouseReleaseEvent(QMouseEvent *event); - void mousePressEvent(QMouseEvent *event); -}; + highlighted_ = false; + //setMinimumHeight(QStyle::PM_MenuTearoffHeight); + setMinimumHeight(10); + setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Minimum); +} -void MathButton::mouseReleaseEvent(QMouseEvent *event) +void TearOff::mouseReleaseEvent ( QMouseEvent * event ) { - QToolButton::mouseReleaseEvent(event); - event->ignore(); + // signal + tearOff(); } -void MathButton::mousePressEvent(QMouseEvent *event) +void TearOff::enterEvent(QEvent * event) { - QToolButton::mousePressEvent(event); + highlighted_ = true; + update(); event->ignore(); } -IconPalette::IconPalette(QWidget * parent) - : QWidgetAction(parent), size_(QSize(22, 22)) +void TearOff::leaveEvent(QEvent * event) { + highlighted_ = false; + update(); + event->ignore(); } - -void IconPalette::addButton(QAction * action) +void TearOff::paintEvent(QPaintEvent * event) { - actions_.push_back(action); -} + QPainter p(this); + QRegion emptyArea = QRegion(rect()); - -QWidget * IconPalette::createWidget(QWidget * parent) -{ - QWidget * widget = new QWidget(parent); - QGridLayout * layout = new QGridLayout(widget); - layout->setSpacing(0); - - for (int i = 0; i < actions_.size(); ++i) { - MathButton * tb = new MathButton(widget); - tb->setAutoRaise(true); - tb->setDefaultAction(actions_.at(i)); - tb->setIconSize(size_); - connect(this, SIGNAL(iconSizeChanged(const QSize &)), - tb, SLOT(setIconSize(const QSize &))); - - int const row = i/qMin(6, i + 1) + 1; - int const col = qMax(1, i + 1 - (row - 1) * 6); - layout->addWidget(tb, row, col); - } - - return widget; + const int fw = style()->pixelMetric(QStyle::PM_MenuPanelWidth, 0, this); + QStyleOptionMenuItem menuOpt; + menuOpt.initFrom(this); + menuOpt.palette = palette(); + menuOpt.state = QStyle::State_None; + menuOpt.checkType = QStyleOptionMenuItem::NotCheckable; + menuOpt.menuRect = rect(); + menuOpt.maxIconWidth = 0; + menuOpt.tabWidth = 0; + menuOpt.menuItemType = QStyleOptionMenuItem::TearOff; + menuOpt.rect.setRect(fw, fw, width() - (fw * 2), + style()->pixelMetric(QStyle::PM_MenuTearoffHeight, 0, this)); + emptyArea -= QRegion(menuOpt.rect); + p.setClipRect(menuOpt.rect); + menuOpt.state = QStyle::State_None; + if (highlighted_) + menuOpt.state |= QStyle::State_Selected; + style()->drawControl(QStyle::CE_MenuTearoff, &menuOpt, &p, this); } - -void IconPalette::setIconSize(const QSize & size) -{ - size_ = size; - // signal - iconSizeChanged(size); -} - - -void IconPalette::updateParent() -{ - bool enable = false; - for (int i = 0; i < actions_.size(); ++i) - if (actions_.at(i)->isEnabled()) { - enable = true; - break; - } - // signal - enabled(enable); -} - -#else // QT_VERSION >= 0x040200 - IconPalette::IconPalette(QWidget * parent) : QWidget(parent, Qt::Popup) { - layout_ = new QGridLayout(this); + tornoff_ = false; + QVBoxLayout * v = new QVBoxLayout(this); + v->setMargin(0); + layout_ = new QGridLayout; layout_->setSpacing(0); - layout_->setMargin(3); + layout_->setMargin(2); + tearoffwidget_ = new TearOff(this); + connect(tearoffwidget_, SIGNAL(tearOff()), this, SLOT(tearOff())); + tearoffwidget_->setMaximumSize(QSize(16777215, 10)); + v->addWidget(tearoffwidget_); + v->addLayout(layout_); } @@ -141,10 +124,20 @@ } +void IconPalette::tearOff() +{ + setWindowFlags(Qt::Tool); + tornoff_ = true; + tearoffwidget_->setVisible(!tornoff_); + show(); +} + + void IconPalette::clicked(QAction * action) { triggered(action); - setVisible(false); + if (!tornoff_) + setVisible(false); } @@ -191,6 +184,9 @@ void IconPalette::hideEvent(QHideEvent * event ) { visible(false); + setWindowFlags(Qt::Popup); + tornoff_ = false; + tearoffwidget_->setVisible(!tornoff_); QWidget::hideEvent(event); } @@ -234,7 +230,6 @@ // draw the rest (buttons) QWidget::paintEvent(event); } -#endif // QT_VERSION >= 0x040200 ButtonMenu::ButtonMenu(const QString & title, QWidget * parent) Index: src/frontends/qt4/IconPalette.h =================================================================== --- src/frontends/qt4/IconPalette.h (revision 18822) +++ src/frontends/qt4/IconPalette.h (working copy) @@ -17,40 +17,32 @@ #include <QLayout> #include "Action.h" -// FIXME: this can go when we move to Qt 4.3 -#define QT_VERSION_CHECK(major, minor, patch) ((major<<16)|(minor<<8)|(patch)) -#if QT_VERSION >= QT_VERSION_CHECK(4, 2, 0) -#include <QWidgetAction> -#endif - namespace lyx { namespace frontend { /** - * For holding an arbitrary set of icons. - */ -#if QT_VERSION >= QT_VERSION_CHECK(4, 2, 0) - -class IconPalette : public QWidgetAction { + * tear-off widget + */ +class TearOff : public QWidget { Q_OBJECT public: - IconPalette(QWidget * parent); - void addButton(QAction *); - QWidget * createWidget(QWidget * parent); -public Q_SLOTS: - void updateParent(); - void setIconSize(const QSize &); + TearOff(QWidget * parent); + void enterEvent(QEvent *); + void leaveEvent(QEvent *); + void mouseReleaseEvent (QMouseEvent *); Q_SIGNALS: - void enabled(bool); - void iconSizeChanged(const QSize &); + void tearOff(); +protected: + void paintEvent(QPaintEvent *); private: - QList<QAction *> actions_; - QSize size_; + bool highlighted_; }; -#else +/** + * For holding an arbitrary set of icons. + */ class IconPalette : public QWidget { Q_OBJECT public: @@ -70,14 +62,16 @@ void paintEvent(QPaintEvent * event); private Q_SLOTS: + void tearOff(); virtual void clicked(QAction *); private: QGridLayout * layout_; QList<QAction *> actions_; + bool tornoff_; + TearOff * tearoffwidget_; }; -#endif // QT_VERSION >= QT_VERSION_CHECK(4, 2, 0) /** * Popup menu for a toolbutton. Index: src/frontends/qt4/QLToolbar.cpp =================================================================== --- src/frontends/qt4/QLToolbar.cpp (revision 18822) +++ src/frontends/qt4/QLToolbar.cpp (working copy) @@ -212,15 +212,8 @@ connect(this, SIGNAL(iconSizeChanged(const QSize &)), tb, SLOT(setIconSize(const QSize &))); -#if QT_VERSION >= 0x040200 - IconPalette * panel = new IconPalette(&owner_); - connect(panel, SIGNAL(enabled(bool)), - tb, SLOT(setEnabled(bool))); - connect(this, SIGNAL(iconSizeChanged(const QSize &)), - panel, SLOT(setIconSize(const QSize &))); -#else IconPalette * panel = new IconPalette(tb); -#endif + connect(this, SIGNAL(updated()), panel, SLOT(updateParent())); ToolbarInfo const & tbinfo = toolbarbackend.getToolbar(item.name_); ToolbarInfo::item_iterator it = tbinfo.items.begin(); @@ -239,18 +232,10 @@ tb->setIcon(QPixmap(getIcon(it->func_).c_str())); } -#if QT_VERSION >= 0x040200 - QMenu * m = new QMenu(tb); - m->addAction(panel); - m->setTearOffEnabled(true); - m->setWindowTitle(qt_(to_ascii(item.label_))); - tb->setPopupMode(QToolButton::InstantPopup); - tb->setMenu(m); -#else + tb->setCheckable(true); connect(tb, SIGNAL(clicked(bool)), panel, SLOT(setVisible(bool))); connect(panel, SIGNAL(visible(bool)), tb, SLOT(setChecked(bool))); -#endif // QT_VERSION >= 0x040200 addWidget(tb); break;