summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLuboš Luňák <l.lunak@suse.cz>2011-04-08 21:43:11 +0200
committerLuboš Luňák <l.lunak@suse.cz>2011-04-08 22:01:25 +0200
commitb2d1508fd2dfd22113b343914cb382be092fd628 (patch)
tree584d771966466551e455afd6cb930e2144d6dfcc
parentc15593ad44e736f55b26f5c117b07fd86be65178 (diff)
rework KDE4 popup menu drawing to avoid various glitches
-rw-r--r--vcl/unx/kde4/KDESalGraphics.cxx78
1 files changed, 49 insertions, 29 deletions
diff --git a/vcl/unx/kde4/KDESalGraphics.cxx b/vcl/unx/kde4/KDESalGraphics.cxx
index e0f736b00a..8e9aad8a5c 100644
--- a/vcl/unx/kde4/KDESalGraphics.cxx
+++ b/vcl/unx/kde4/KDESalGraphics.cxx
@@ -160,10 +160,10 @@ sal_Bool KDESalGraphics::IsNativeControlSupported( ControlType type, ControlPart
/// helper drawing methods
namespace
{
- void draw( QStyle::ControlElement element, QStyleOption* option, QImage* image, QStyle::State state )
+ void draw( QStyle::ControlElement element, QStyleOption* option, QImage* image, QStyle::State state, QRect rect = QRect())
{
option->state |= state;
- option->rect = image->rect();
+ option->rect = !rect.isNull() ? rect : image->rect();
QPainter painter(image);
kapp->style()->drawControl(element, option, &painter);
@@ -323,43 +323,63 @@ sal_Bool KDESalGraphics::drawNativeControl( ControlType type, ControlPart part,
}
else if (type == CTRL_MENU_POPUP)
{
- if (part == PART_MENU_ITEM)
+ if( part == PART_MENU_ITEM )
{
QStyleOptionMenuItem option;
- draw( QStyle::CE_MenuItem, &option, m_image,
+ // this is painted after popup frame, so highlight would be painted
+ // over popup border
+ int fw = kapp->style()->pixelMetric( QStyle::PM_MenuPanelWidth );
+ clipRegion = new QRegion( widgetRect.adjusted( fw, fw, -fw, -fw ));
+ draw( QStyle::CE_MenuItem, &option, m_image,
vclStateValue2StateFlag(nControlState, value) );
}
- else if (part == PART_MENU_ITEM_CHECK_MARK)
+ else if( part == PART_MENU_SEPARATOR )
{
- m_image->fill(Qt::transparent);
- if(nControlState & CTRL_STATE_PRESSED) // at least Oxygen paints always as checked
- {
- QStyleOptionButton option;
- draw( QStyle::PE_IndicatorMenuCheckMark, &option, m_image,
- vclStateValue2StateFlag(nControlState, value));
- }
+ QStyleOptionMenuItem option;
+ option.menuItemType = QStyleOptionMenuItem::Separator;
+ // Painting the whole menu item area results in different background
+ // with at least Plastique style, so clip only to the separator itself
+ // (QSize( 2, 2 ) is hardcoded in Qt)
+ option.rect = m_image->rect();
+ QSize size = kapp->style()->sizeFromContents( QStyle::CT_MenuItem, &option, QSize( 2, 2 ));
+ QRect rect = m_image->rect();
+ QPoint center = rect.center();
+ rect.setHeight( size.height());
+ rect.moveCenter( center );
+ // don't paint over popup frame border
+ int fw = kapp->style()->pixelMetric( QStyle::PM_MenuPanelWidth );
+ clipRegion = new QRegion( rect.translated( widgetRect.topLeft()).adjusted( fw, 0, -fw, 0 ));
+ draw( QStyle::CE_MenuItem, &option, m_image,
+ vclStateValue2StateFlag(nControlState, value), rect );
}
- else if (part == PART_MENU_ITEM_RADIO_MARK)
+ else if( part == PART_MENU_ITEM_CHECK_MARK || part == PART_MENU_ITEM_RADIO_MARK )
{
- m_image->fill(Qt::transparent);
- QStyleOptionButton option;
- // we get always passed BUTTONVALUE_DONTKNOW in 'value', and the checked
- // state is actually CTRL_STATE_PRESSED
- QStyle::State set = ( nControlState & CTRL_STATE_PRESSED ) ? QStyle::State_On : QStyle::State_Off;
- draw( QStyle::PE_IndicatorRadioButton, &option, m_image,
- vclStateValue2StateFlag(nControlState, value) | set );
+ QStyleOptionMenuItem option;
+ option.checkType = ( part == PART_MENU_ITEM_CHECK_MARK )
+ ? QStyleOptionMenuItem::NonExclusive : QStyleOptionMenuItem::Exclusive;
+ option.checked = ( nControlState & CTRL_STATE_PRESSED );
+ // widgetRect is now the rectangle for the checkbox/radiobutton itself, but Qt
+ // paints the whole menu item, so translate position (and it'll be clipped);
+ // it is also necessary to fill the background transparently first, as this
+ // is painted after menuitem highlight, otherwise there would be a grey area
+ const MenupopupValue* menuVal = static_cast<const MenupopupValue*>(&value);
+ QRect menuItemRect( region2QRect( menuVal->maItemRect ));
+ QRect rect( menuItemRect.topLeft() - widgetRect.topLeft(),
+ widgetRect.size().expandedTo( menuItemRect.size()));
+ m_image->fill( Qt::transparent );
+ draw( QStyle::CE_MenuItem, &option, m_image,
+ vclStateValue2StateFlag(nControlState, value), rect );
}
- else
+ else if( part == PART_ENTIRE_CONTROL )
{
- #if ( QT_VERSION >= QT_VERSION_CHECK( 4, 5, 0 ) )
- QStyleOptionFrameV3 option;
- option.frameShape = QFrame::StyledPanel;
- #else
- QStyleOptionFrameV2 option;
- #endif
- draw( QStyle::PE_FrameMenu, &option, m_image,
- vclStateValue2StateFlag(nControlState, value) );
+ QStyleOptionMenuItem option;
+ draw( QStyle::PE_PanelMenu, &option, m_image, vclStateValue2StateFlag( nControlState, value ));
+ QStyleOptionFrame frame;
+ frame.lineWidth = kapp->style()->pixelMetric( QStyle::PM_MenuPanelWidth );
+ draw( QStyle::PE_FrameMenu, &frame, m_image, vclStateValue2StateFlag( nControlState, value ));
}
+ else
+ returnVal = false;
}
else if ( (type == CTRL_TOOLBAR) && (part == PART_BUTTON) )
{