LCOV - code coverage report
Current view: top level - vcl/unx/gtk/gdi - salnativewidgets-gtk.cxx (source / functions) Hit Total Coverage
Test: commit 10e77ab3ff6f4314137acd6e2702a6e5c1ce1fae Lines: 0 2150 0.0 %
Date: 2014-11-03 Functions: 0 102 0.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include <config_version.h>
      21             : 
      22             : #include "vcl/svapp.hxx"
      23             : 
      24             : #include "unx/gtk/gtkframe.hxx"
      25             : #include "unx/gtk/gtkdata.hxx"
      26             : #include "unx/gtk/gtkinst.hxx"
      27             : #include "unx/gtk/gtkgdi.hxx"
      28             : 
      29             : #include "unx/saldata.hxx"
      30             : #include "unx/saldisp.hxx"
      31             : 
      32             : #include <cstdio>
      33             : #include <cmath>
      34             : #include <vector>
      35             : #include <algorithm>
      36             : #include <boost/unordered_map.hpp>
      37             : 
      38             : #include "vcl/vclenum.hxx"
      39             : #include <vcl/settings.hxx>
      40             : #include "fontmanager.hxx"
      41             : #include <vcl/decoview.hxx>
      42             : 
      43             : typedef struct _cairo_font_options cairo_font_options_t;
      44             : const char* const tabPrelitDataName="libreoffice-tab-is-prelit";
      45             : 
      46             : // initialize statics
      47             : bool GtkSalGraphics::bThemeChanged = true;
      48             : bool GtkSalGraphics::bNeedPixmapPaint = false;
      49             : 
      50           0 : GtkSalGraphics::GtkSalGraphics( GtkSalFrame *pFrame, GtkWidget *pWindow )
      51             :     : X11SalGraphics(),
      52             :       m_pWindow( pWindow ),
      53           0 :       m_aClipRegion(true)
      54             : {
      55             :     Init( pFrame, GDK_WINDOW_XID( widget_get_window( pWindow ) ),
      56             :           SalX11Screen( gdk_x11_screen_get_screen_number(
      57           0 :                                 gtk_widget_get_screen( pWindow ) ) ) );
      58           0 : }
      59             : 
      60           0 : GtkSalGraphics::GtkSalGraphics( GtkSalFrame *pFrame, GtkWidget *pWindow,
      61             :                                 SalX11Screen nXScreen )
      62             :     : X11SalGraphics(),
      63             :       m_pWindow( pWindow ),
      64           0 :       m_aClipRegion(true)
      65             : {
      66           0 :     Init( pFrame, GDK_WINDOW_XID( widget_get_window( pWindow ) ), nXScreen );
      67           0 : }
      68             : 
      69           0 : GtkSalGraphics::~GtkSalGraphics()
      70             : {
      71           0 : }
      72             : 
      73             : /*************************************
      74             :  * Cached native widget objects
      75             :  *************************************/
      76             : class NWPixmapCacheList;
      77             : class NWPixmapCache;
      78             : struct NWFWidgetData
      79             : {
      80             :     GtkWidget *  gCacheWindow;
      81             :     GtkWidget *  gDumbContainer;
      82             : 
      83             :     GtkWidget *  gBtnWidget;
      84             :     GtkWidget *  gRadioWidget;
      85             :     GtkWidget *  gRadioWidgetSibling;
      86             :     GtkWidget *  gCheckWidget;
      87             :     GtkWidget *  gScrollHorizWidget;
      88             :     GtkWidget *  gScrollVertWidget;
      89             :     GtkWidget *  gArrowWidget;
      90             :     GtkWidget *  gDropdownWidget;
      91             :     GtkWidget *  gEditBoxWidget;
      92             :     GtkWidget *  gSpinButtonWidget;
      93             :     GtkWidget *  gNotebookWidget;
      94             :     GtkWidget *  gOptionMenuWidget;
      95             :     GtkWidget *  gComboWidget;
      96             :     GtkWidget *  gScrolledWindowWidget;
      97             :     GtkWidget *  gToolbarWidget;
      98             :     GtkWidget *  gToolbarButtonWidget;
      99             :     GtkWidget *  gHandleBoxWidget;
     100             :     GtkWidget *  gMenubarWidget;
     101             :     GtkWidget *  gMenuItemMenubarWidget;
     102             :     GtkWidget *  gMenuWidget;
     103             :     GtkWidget *  gMenuItemMenuWidget;
     104             :     GtkWidget *  gMenuItemCheckMenuWidget;
     105             :     GtkWidget *  gMenuItemRadioMenuWidget;
     106             :     GtkWidget *  gMenuItemSeparatorMenuWidget;
     107             :     GtkWidget *  gImageMenuItem;
     108             :     GtkWidget *  gTooltipPopup;
     109             :     GtkWidget *  gProgressBar;
     110             :     GtkWidget *  gTreeView;
     111             :     GtkWidget *  gHScale;
     112             :     GtkWidget *  gVScale;
     113             :     GtkWidget *  gSeparator;
     114             :     GtkWidget *  gDialog;
     115             :     GtkWidget *  gFrame;
     116             : 
     117             :     NWPixmapCacheList* gNWPixmapCacheList;
     118             :     NWPixmapCache* gCacheTabItems;
     119             :     NWPixmapCache* gCacheTabPages;
     120             : 
     121           0 :     NWFWidgetData() :
     122             :         gCacheWindow( NULL ),
     123             :         gDumbContainer( NULL ),
     124             :         gBtnWidget( NULL ),
     125             :         gRadioWidget( NULL ),
     126             :         gRadioWidgetSibling( NULL ),
     127             :         gCheckWidget( NULL ),
     128             :         gScrollHorizWidget( NULL ),
     129             :         gScrollVertWidget( NULL ),
     130             :         gArrowWidget( NULL ),
     131             :         gDropdownWidget( NULL ),
     132             :         gEditBoxWidget( NULL ),
     133             :         gSpinButtonWidget( NULL ),
     134             :         gNotebookWidget( NULL ),
     135             :         gOptionMenuWidget( NULL ),
     136             :         gComboWidget( NULL ),
     137             :         gScrolledWindowWidget( NULL ),
     138             :         gToolbarWidget( NULL ),
     139             :         gToolbarButtonWidget( NULL ),
     140             :         gHandleBoxWidget( NULL ),
     141             :         gMenubarWidget( NULL ),
     142             :         gMenuItemMenubarWidget( NULL ),
     143             :         gMenuWidget( NULL ),
     144             :         gMenuItemMenuWidget( NULL ),
     145             :         gMenuItemCheckMenuWidget( NULL ),
     146             :         gMenuItemRadioMenuWidget( NULL ),
     147             :         gMenuItemSeparatorMenuWidget( NULL ),
     148             :         gImageMenuItem( NULL ),
     149             :         gTooltipPopup( NULL ),
     150             :         gProgressBar( NULL ),
     151             :         gTreeView( NULL ),
     152             :         gHScale( NULL ),
     153             :         gVScale( NULL ),
     154             :         gSeparator( NULL ),
     155             :         gDialog( NULL ),
     156             :         gFrame( NULL ),
     157             :         gNWPixmapCacheList( NULL ),
     158             :         gCacheTabItems( NULL ),
     159           0 :         gCacheTabPages( NULL )
     160           0 :     {}
     161             : };
     162             : 
     163             : // Keep a hash table of Widgets->default flags so that we can
     164             : // easily and quickly reset each to a default state before using
     165             : // them
     166           0 : static boost::unordered_map<long, guint>    gWidgetDefaultFlags;
     167           0 : class WidgetDataVector
     168             : {
     169             : private:
     170             :     std::vector<NWFWidgetData> mData;
     171             : 
     172             : public:
     173           0 :     WidgetDataVector(size_t nElems = 0) : mData( nElems ) {}
     174           0 :     size_t size() const { return mData.size(); }
     175           0 :     NWFWidgetData &operator [](size_t i) { return mData.at(i); }
     176           0 :     NWFWidgetData &operator [](const SalX11Screen &s) { return mData.at(s.getXScreen()); }
     177             : };
     178           0 : static WidgetDataVector gWidgetData;
     179             : 
     180             : static const GtkBorder aDefDefBorder        = { 1, 1, 1, 1 };
     181             : 
     182             : // Some GTK defaults
     183             : #define MIN_ARROW_SIZE                    11
     184             : #define BTN_CHILD_SPACING                1
     185             : #define MIN_SPIN_ARROW_WIDTH                6
     186             : 
     187             : static void NWEnsureGTKRadio             ( SalX11Screen nScreen );
     188             : static void NWEnsureGTKButton            ( SalX11Screen nScreen );
     189             : static void NWEnsureGTKCheck             ( SalX11Screen nScreen );
     190             : static void NWEnsureGTKScrollbars        ( SalX11Screen nScreen );
     191             : static void NWEnsureGTKArrow             ( SalX11Screen nScreen );
     192             : static void NWEnsureGTKEditBox           ( SalX11Screen nScreen );
     193             : static void NWEnsureGTKSpinButton        ( SalX11Screen nScreen );
     194             : static void NWEnsureGTKNotebook          ( SalX11Screen nScreen );
     195             : static void NWEnsureGTKOptionMenu        ( SalX11Screen nScreen );
     196             : static void NWEnsureGTKCombo             ( SalX11Screen nScreen );
     197             : static void NWEnsureGTKScrolledWindow    ( SalX11Screen nScreen );
     198             : static void NWEnsureGTKToolbar           ( SalX11Screen nScreen );
     199             : static void NWEnsureGTKMenubar           ( SalX11Screen nScreen );
     200             : static void NWEnsureGTKMenu              ( SalX11Screen nScreen );
     201             : static void NWEnsureGTKTooltip           ( SalX11Screen nScreen );
     202             : static void NWEnsureGTKDialog            ( SalX11Screen nScreen );
     203             : static void NWEnsureGTKFrame             ( SalX11Screen nScreen );
     204             : static void NWEnsureGTKProgressBar       ( SalX11Screen nScreen );
     205             : static void NWEnsureGTKTreeView          ( SalX11Screen nScreen );
     206             : static void NWEnsureGTKSlider            ( SalX11Screen nScreen );
     207             : 
     208             : static void NWConvertVCLStateToGTKState( ControlState nVCLState, GtkStateType* nGTKState, GtkShadowType* nGTKShadow );
     209             : static void NWAddWidgetToCacheWindow( GtkWidget* widget, SalX11Screen nScreen );
     210             : static void NWSetWidgetState( GtkWidget* widget, ControlState nState, GtkStateType nGtkState );
     211             : 
     212             : static void NWCalcArrowRect( const Rectangle& rButton, Rectangle& rArrow );
     213             : 
     214             : /*
     215             :  * Individual helper functions
     216             :  *
     217             :  */
     218             : 
     219             : static Rectangle NWGetButtonArea( SalX11Screen nScreen, ControlType nType, ControlPart nPart, Rectangle aAreaRect, ControlState nState,
     220             :                                 const ImplControlValue& aValue, const OUString& rCaption );
     221             : 
     222             : static Rectangle NWGetTabItemRect( SalX11Screen nScreen, Rectangle aAreaRect );
     223             : 
     224             : static Rectangle NWGetEditBoxPixmapRect( SalX11Screen nScreen, ControlType nType, ControlPart nPart, Rectangle aAreaRect, ControlState nState,
     225             :                             const ImplControlValue& aValue, const OUString& rCaption );
     226             : 
     227             : static void NWPaintOneEditBox( SalX11Screen nScreen, GdkDrawable * gdkDrawable, GdkRectangle *gdkRect,
     228             :                                ControlType nType, ControlPart nPart, Rectangle aEditBoxRect,
     229             :                                ControlState nState, const ImplControlValue& aValue,
     230             :                                const OUString& rCaption );
     231             : 
     232             : static Rectangle NWGetSpinButtonRect( SalX11Screen nScreen, ControlType nType, ControlPart nPart, Rectangle aAreaRect, ControlState nState,
     233             :                             const ImplControlValue& aValue, const OUString& rCaption );
     234             : 
     235             : static void NWPaintOneSpinButton( SalX11Screen nScreen, GdkPixmap * pixmap, ControlType nType, ControlPart nPart, Rectangle aAreaRect,
     236             :                             ControlState nState, const ImplControlValue& aValue,
     237             :                             const OUString& rCaption );
     238             : 
     239             : static Rectangle NWGetComboBoxButtonRect( SalX11Screen nScreen, ControlType nType, ControlPart nPart, Rectangle aAreaRect, ControlState nState,
     240             :                             const ImplControlValue& aValue, const OUString& rCaption );
     241             : 
     242             : static Rectangle NWGetListBoxButtonRect( SalX11Screen nScreen, ControlType nType, ControlPart nPart, Rectangle aAreaRect, ControlState nState,
     243             :                             const ImplControlValue& aValue, const OUString& rCaption );
     244             : 
     245             : static Rectangle NWGetListBoxIndicatorRect( SalX11Screen nScreen, ControlType nType, ControlPart nPart, Rectangle aAreaRect, ControlState nState,
     246             :                             const ImplControlValue& aValue, const OUString& rCaption );
     247             : 
     248             : static Rectangle NWGetToolbarRect( SalX11Screen nScreen,
     249             :                                    ControlType nType,
     250             :                                    ControlPart nPart,
     251             :                                    Rectangle aAreaRect,
     252             :                                    ControlState nState,
     253             :                                    const ImplControlValue& aValue,
     254             :                                    const OUString& rCaption );
     255             : 
     256             : static int getFrameWidth(GtkWidget* widget);
     257             : 
     258             : static Rectangle NWGetScrollButtonRect(    SalX11Screen nScreen, ControlPart nPart, Rectangle aAreaRect );
     259             : 
     260             : /*********************************************************
     261             :  * PixmapCache
     262             :  *********************************************************/
     263             : 
     264             : // as some native widget drawing operations are pretty slow
     265             : // with certain themes (eg tabpages)
     266             : // this cache can be used to cache the corresponding pixmap
     267             : // see NWPaintGTKTabItem
     268             : 
     269             : class NWPixmapCacheData
     270             : {
     271             : public:
     272             :     ControlType m_nType;
     273             :     ControlState m_nState;
     274             :     Rectangle   m_pixmapRect;
     275             :     GdkPixmap*  m_pixmap;
     276             : 
     277           0 :     NWPixmapCacheData() : m_nType(0), m_nState(0), m_pixmap(0) {}
     278           0 :     ~NWPixmapCacheData()
     279           0 :         { SetPixmap( NULL ); };
     280             :     void SetPixmap( GdkPixmap* pPixmap );
     281             : };
     282             : 
     283             : class NWPixmapCache
     284             : {
     285             :     int m_size;
     286             :     int m_idx;
     287             :     int m_screen;
     288             :     NWPixmapCacheData* pData;
     289             : public:
     290             :     NWPixmapCache( SalX11Screen nScreen );
     291             :     ~NWPixmapCache();
     292             : 
     293           0 :     void SetSize( int n)
     294           0 :         { delete [] pData; m_idx = 0; m_size = n; pData = new NWPixmapCacheData[m_size]; }
     295           0 :     int GetSize() const { return m_size; }
     296             : 
     297             :     bool Find( ControlType aType, ControlState aState, const Rectangle& r_pixmapRect, GdkPixmap** pPixmap );
     298             :     void Fill( ControlType aType, ControlState aState, const Rectangle& r_pixmapRect, GdkPixmap* pPixmap );
     299             : 
     300             :     void ThemeChanged();
     301             : };
     302             : 
     303           0 : class NWPixmapCacheList
     304             : {
     305             : public:
     306             :     ::std::vector< NWPixmapCache* > mCaches;
     307             : 
     308             :     void AddCache( NWPixmapCache *pCache );
     309             :     void RemoveCache( NWPixmapCache *pCache );
     310             :     void ThemeChanged();
     311             : };
     312             : 
     313             : // --- implementation ---
     314             : 
     315           0 : void NWPixmapCacheData::SetPixmap( GdkPixmap* pPixmap )
     316             : {
     317           0 :     if( m_pixmap )
     318           0 :         g_object_unref( m_pixmap );
     319             : 
     320           0 :     m_pixmap = pPixmap;
     321             : 
     322           0 :     if( m_pixmap )
     323           0 :         g_object_ref( m_pixmap );
     324           0 : }
     325             : 
     326           0 : NWPixmapCache::NWPixmapCache( SalX11Screen nScreen )
     327             : {
     328           0 :     m_idx = 0;
     329           0 :     m_size = 0;
     330           0 :     m_screen = nScreen.getXScreen();
     331           0 :     pData = NULL;
     332           0 :     if( gWidgetData[m_screen].gNWPixmapCacheList )
     333           0 :         gWidgetData[m_screen].gNWPixmapCacheList->AddCache(this);
     334           0 : }
     335           0 : NWPixmapCache::~NWPixmapCache()
     336             : {
     337           0 :     if( gWidgetData[m_screen].gNWPixmapCacheList )
     338           0 :         gWidgetData[m_screen].gNWPixmapCacheList->RemoveCache(this);
     339           0 :     delete[] pData;
     340           0 : }
     341           0 : void NWPixmapCache::ThemeChanged()
     342             : {
     343             :     // throw away cached pixmaps
     344             :     int i;
     345           0 :     for(i=0; i<m_size; i++)
     346           0 :         pData[i].SetPixmap( NULL );
     347           0 : }
     348             : 
     349           0 : bool  NWPixmapCache::Find( ControlType aType, ControlState aState, const Rectangle& r_pixmapRect, GdkPixmap** pPixmap )
     350             : {
     351           0 :     aState &= ~CTRL_CACHING_ALLOWED; // mask clipping flag
     352             :     int i;
     353           0 :     for(i=0; i<m_size; i++)
     354             :     {
     355           0 :         if( pData[i].m_nType == aType &&
     356           0 :             pData[i].m_nState == aState &&
     357           0 :             pData[i].m_pixmapRect.GetWidth() == r_pixmapRect.GetWidth() &&
     358           0 :             pData[i].m_pixmapRect.GetHeight() == r_pixmapRect.GetHeight() &&
     359           0 :             pData[i].m_pixmap != NULL )
     360             :         {
     361           0 :             *pPixmap = pData[i].m_pixmap;
     362           0 :             return true;
     363             :         }
     364             :     }
     365           0 :     return false;
     366             : }
     367             : 
     368           0 : void NWPixmapCache::Fill( ControlType aType, ControlState aState, const Rectangle& r_pixmapRect, GdkPixmap* pPixmap )
     369             : {
     370           0 :     if( !(aState & CTRL_CACHING_ALLOWED) )
     371           0 :         return;
     372             : 
     373           0 :     aState &= ~CTRL_CACHING_ALLOWED; // mask clipping flag
     374           0 :     m_idx = (m_idx+1) % m_size; // just wrap
     375           0 :     pData[m_idx].m_nType = aType;
     376           0 :     pData[m_idx].m_nState = aState;
     377           0 :     pData[m_idx].m_pixmapRect = r_pixmapRect;
     378           0 :     pData[m_idx].SetPixmap( pPixmap );
     379             : }
     380             : 
     381           0 : void NWPixmapCacheList::AddCache( NWPixmapCache* pCache )
     382             : {
     383           0 :     mCaches.push_back( pCache );
     384           0 : }
     385           0 : void NWPixmapCacheList::RemoveCache( NWPixmapCache* pCache )
     386             : {
     387           0 :     ::std::vector< NWPixmapCache* >::iterator p;
     388           0 :     p = ::std::find( mCaches.begin(), mCaches.end(), pCache );
     389           0 :     if( p != mCaches.end() )
     390           0 :         mCaches.erase( p );
     391           0 : }
     392           0 : void NWPixmapCacheList::ThemeChanged( )
     393             : {
     394           0 :     ::std::vector< NWPixmapCache* >::iterator p = mCaches.begin();
     395           0 :     while( p != mCaches.end() )
     396             :     {
     397           0 :         (*p)->ThemeChanged();
     398           0 :         ++p;
     399             :     }
     400           0 : }
     401             : 
     402             : /*********************************************************
     403             :  * Make border manipulation easier
     404             :  *********************************************************/
     405           0 : inline void NW_gtk_border_set_from_border( GtkBorder& aDst, const GtkBorder * pSrc )
     406             : {
     407           0 :     aDst.left        = pSrc->left;
     408           0 :     aDst.top        = pSrc->top;
     409           0 :     aDst.right    = pSrc->right;
     410           0 :     aDst.bottom    = pSrc->bottom;
     411           0 : }
     412             : 
     413             : /*********************************************************
     414             :  * Initialize GTK and local stuff
     415             :  *********************************************************/
     416           0 : void GtkData::initNWF( void )
     417             : {
     418           0 :     ImplSVData* pSVData = ImplGetSVData();
     419             : 
     420             :     // draw no border for popup menus (NWF draws its own)
     421           0 :     pSVData->maNWFData.mbFlatMenu = true;
     422             : 
     423             :     // draw separate buttons for toolbox dropdown items
     424           0 :     pSVData->maNWFData.mbToolboxDropDownSeparate = true;
     425             : 
     426             :     // draw toolbars in separate lines
     427           0 :     pSVData->maNWFData.mbDockingAreaSeparateTB = true;
     428             : 
     429             :     // open first menu on F10
     430           0 :     pSVData->maNWFData.mbOpenMenuOnF10 = true;
     431             : 
     432             :     // omit GetNativeControl while painting (see brdwin.cxx)
     433           0 :     pSVData->maNWFData.mbCanDrawWidgetAnySize = true;
     434             : 
     435           0 :     pSVData->maNWFData.mbDDListBoxNoTextArea = true;
     436             : 
     437           0 :     int nScreens = GetGtkSalData()->GetGtkDisplay()->GetXScreenCount();
     438           0 :     gWidgetData = WidgetDataVector( nScreens );
     439           0 :     for( int i = 0; i < nScreens; i++ )
     440           0 :         gWidgetData[i].gNWPixmapCacheList = new NWPixmapCacheList;
     441             : 
     442             :     // small extra border around menu items
     443           0 :     NWEnsureGTKMenu( SalX11Screen( 0 ) );
     444           0 :     gint horizontal_padding = 1;
     445           0 :     gint vertical_padding = 1;
     446           0 :     gtk_widget_style_get( gWidgetData[0].gMenuWidget,
     447             :             "horizontal-padding", &horizontal_padding,
     448           0 :             (char *)NULL);
     449           0 :     gtk_widget_style_get( gWidgetData[0].gMenuWidget,
     450             :             "vertical-padding", &vertical_padding,
     451           0 :             (char *)NULL);
     452           0 :     gint xthickness = gWidgetData[0].gMenuWidget->style->xthickness;
     453           0 :     gint ythickness = gWidgetData[0].gMenuWidget->style->ythickness;
     454           0 :     pSVData->maNWFData.mnMenuFormatBorderX = xthickness + horizontal_padding;
     455           0 :     pSVData->maNWFData.mnMenuFormatBorderY = ythickness + vertical_padding;
     456             : 
     457           0 :     if( SalGetDesktopEnvironment() == "KDE" )
     458             :     {
     459             :         // #i97196# ensure a widget exists and the style engine was loaded
     460           0 :         NWEnsureGTKButton( SalX11Screen( 0 ) );
     461           0 :         if( g_type_from_name( "QtEngineStyle" ) )
     462             :         {
     463             :             // KDE 3.3 invented a bug in the qt<->gtk theme engine
     464             :             // that makes direct rendering impossible: they totally
     465             :             // ignore the clip rectangle passed to the paint methods
     466           0 :             GtkSalGraphics::bNeedPixmapPaint = true;
     467             :         }
     468             :     }
     469           0 :     static const char* pEnv = getenv( "SAL_GTK_USE_PIXMAPPAINT" );
     470           0 :     if( pEnv && *pEnv )
     471           0 :         GtkSalGraphics::bNeedPixmapPaint = true;
     472             : 
     473             :     #if OSL_DEBUG_LEVEL > 1
     474             :     std::fprintf( stderr, "GtkPlugin: using %s NWF\n",
     475             :              GtkSalGraphics::bNeedPixmapPaint ? "offscreen" : "direct" );
     476             :     #endif
     477           0 : }
     478             : 
     479             : /*********************************************************
     480             :  * Release GTK and local stuff
     481             :  *********************************************************/
     482           0 : void GtkData::deInitNWF( void )
     483             : {
     484           0 :     for( unsigned int i = 0; i < gWidgetData.size(); i++ )
     485             :     {
     486             :         // free up global widgets
     487             :         // gtk_widget_destroy will in turn destroy the child hierarchy
     488             :         // so only destroy disjunct hierarchies
     489           0 :         if( gWidgetData[i].gCacheWindow )
     490           0 :             gtk_widget_destroy( gWidgetData[i].gCacheWindow );
     491           0 :         if( gWidgetData[i].gMenuWidget )
     492           0 :             g_object_unref (gWidgetData[i].gMenuWidget);
     493           0 :         if( gWidgetData[i].gTooltipPopup )
     494           0 :             gtk_widget_destroy( gWidgetData[i].gTooltipPopup );
     495           0 :         if( gWidgetData[i].gDialog )
     496           0 :             gtk_widget_destroy( gWidgetData[i].gDialog );
     497           0 :         delete gWidgetData[i].gCacheTabPages;
     498           0 :         gWidgetData[i].gCacheTabPages = NULL;
     499           0 :         delete gWidgetData[i].gCacheTabItems;
     500           0 :         gWidgetData[i].gCacheTabItems = NULL;
     501           0 :         delete gWidgetData[i].gNWPixmapCacheList;
     502           0 :         gWidgetData[i].gNWPixmapCacheList = NULL;
     503             :     }
     504           0 : }
     505             : 
     506             : /**********************************************************
     507             :  * track clip region
     508             :  **********************************************************/
     509           0 : void GtkSalGraphics::ResetClipRegion()
     510             : {
     511           0 :     m_aClipRegion.SetNull();
     512           0 :     X11SalGraphics::ResetClipRegion();
     513           0 : }
     514             : 
     515           0 : bool GtkSalGraphics::setClipRegion( const vcl::Region& i_rClip )
     516             : {
     517           0 :     m_aClipRegion = i_rClip;
     518           0 :     bool bRet = X11SalGraphics::setClipRegion( m_aClipRegion );
     519           0 :     if( m_aClipRegion.IsEmpty() )
     520           0 :         m_aClipRegion.SetNull();
     521           0 :     return bRet;
     522             : }
     523             : 
     524           0 : void GtkSalGraphics::copyBits( const SalTwoRect& rPosAry,
     525             :                                SalGraphics* pSrcGraphics )
     526             : {
     527           0 :     GtkSalFrame* pFrame = GetGtkFrame();
     528           0 :     ::Window aWin = None;
     529           0 :     if( pFrame && m_pWindow )
     530             :     {
     531             :         /* #i64117# some themes set the background pixmap VERY frequently */
     532           0 :         GdkWindow* pWin = GTK_WIDGET(m_pWindow)->window;
     533           0 :         if( pWin )
     534             :         {
     535           0 :             aWin = GDK_WINDOW_XWINDOW(pWin);
     536           0 :             if( aWin != None )
     537           0 :                 XSetWindowBackgroundPixmap( pFrame->getDisplay()->GetDisplay(),
     538             :                                             aWin,
     539           0 :                                             None );
     540             :         }
     541             :     }
     542           0 :     X11SalGraphics::copyBits( rPosAry, pSrcGraphics );
     543           0 :     if( pFrame && pFrame->getBackgroundPixmap() != None )
     544           0 :         XSetWindowBackgroundPixmap( pFrame->getDisplay()->GetDisplay(),
     545             :                                     aWin,
     546           0 :                                     pFrame->getBackgroundPixmap() );
     547           0 : }
     548             : 
     549             : /*
     550             :  * IsNativeControlSupported()
     551             :  *
     552             :  *  Returns true if the platform supports native
     553             :  *  drawing of the control defined by nPart
     554             :  */
     555           0 : bool GtkSalGraphics::IsNativeControlSupported( ControlType nType, ControlPart nPart )
     556             : {
     557           0 :     switch(nType)
     558             :     {
     559             :         case CTRL_PUSHBUTTON:
     560             :         case CTRL_RADIOBUTTON:
     561             :         case CTRL_CHECKBOX:
     562             :         case CTRL_TOOLTIP:
     563             :         case CTRL_PROGRESS:
     564             :         case CTRL_LISTNODE:
     565             :         case CTRL_LISTNET:
     566           0 :             if(nPart==PART_ENTIRE_CONTROL)
     567           0 :                 return true;
     568           0 :             break;
     569             : 
     570             :         case CTRL_SCROLLBAR:
     571           0 :             if(nPart==PART_DRAW_BACKGROUND_HORZ || nPart==PART_DRAW_BACKGROUND_VERT ||
     572           0 :                nPart==PART_ENTIRE_CONTROL       || nPart==HAS_THREE_BUTTONS)
     573           0 :                 return true;
     574           0 :             break;
     575             : 
     576             :         case CTRL_EDITBOX:
     577             :         case CTRL_MULTILINE_EDITBOX:
     578             :         case CTRL_COMBOBOX:
     579           0 :             if(nPart==PART_ENTIRE_CONTROL || nPart==HAS_BACKGROUND_TEXTURE)
     580           0 :                 return true;
     581           0 :             break;
     582             : 
     583             :         case CTRL_SPINBOX:
     584           0 :             if(nPart==PART_ENTIRE_CONTROL || nPart==PART_ALL_BUTTONS || nPart==HAS_BACKGROUND_TEXTURE)
     585           0 :                 return true;
     586           0 :             break;
     587             : 
     588             :         case CTRL_SPINBUTTONS:
     589           0 :             if(nPart==PART_ENTIRE_CONTROL || nPart==PART_ALL_BUTTONS)
     590           0 :                 return true;
     591           0 :             break;
     592             : 
     593             :         case CTRL_FRAME:
     594             :         case CTRL_WINDOW_BACKGROUND:
     595           0 :             return true;
     596             : 
     597             :         case CTRL_TAB_ITEM:
     598             :         case CTRL_TAB_PANE:
     599             :         case CTRL_TAB_BODY:
     600           0 :             if(nPart==PART_ENTIRE_CONTROL || nPart==PART_TABS_DRAW_RTL)
     601           0 :                 return true;
     602           0 :             break;
     603             : 
     604             :         case CTRL_LISTBOX:
     605           0 :             if(nPart==PART_ENTIRE_CONTROL || nPart==PART_WINDOW || nPart==HAS_BACKGROUND_TEXTURE)
     606           0 :                 return true;
     607           0 :             break;
     608             : 
     609             :         case CTRL_TOOLBAR:
     610           0 :             if( nPart==PART_ENTIRE_CONTROL
     611           0 :                 ||  nPart==PART_DRAW_BACKGROUND_HORZ
     612           0 :                 ||  nPart==PART_DRAW_BACKGROUND_VERT
     613           0 :                 ||  nPart==PART_THUMB_HORZ
     614           0 :                 ||  nPart==PART_THUMB_VERT
     615           0 :                 ||  nPart==PART_BUTTON
     616           0 :                 ||  nPart==PART_SEPARATOR_HORZ
     617           0 :                 ||  nPart==PART_SEPARATOR_VERT
     618             :                 )
     619           0 :                 return true;
     620           0 :             break;
     621             : 
     622             :         case CTRL_MENUBAR:
     623           0 :             if(nPart==PART_ENTIRE_CONTROL || nPart==PART_MENU_ITEM)
     624           0 :                 return true;
     625           0 :             break;
     626             : 
     627             :         case CTRL_MENU_POPUP:
     628           0 :             if (nPart==PART_ENTIRE_CONTROL
     629           0 :                 ||  nPart==PART_MENU_ITEM
     630           0 :                 ||  nPart==PART_MENU_ITEM_CHECK_MARK
     631           0 :                 ||  nPart==PART_MENU_ITEM_RADIO_MARK
     632           0 :                 ||  nPart==PART_MENU_SEPARATOR
     633           0 :                 ||  nPart==PART_MENU_SUBMENU_ARROW
     634             :             )
     635           0 :                 return true;
     636           0 :             break;
     637             : 
     638             :         case CTRL_SLIDER:
     639           0 :             if(nPart == PART_TRACK_HORZ_AREA || nPart == PART_TRACK_VERT_AREA)
     640           0 :                 return true;
     641           0 :             break;
     642             : 
     643             :         case CTRL_FIXEDLINE:
     644           0 :             if(nPart == PART_SEPARATOR_VERT || nPart == PART_SEPARATOR_HORZ)
     645           0 :                 return true;
     646           0 :             break;
     647             : 
     648             :         case CTRL_LISTHEADER:
     649           0 :             if(nPart == PART_BUTTON || nPart == PART_ARROW)
     650           0 :                 return true;
     651           0 :             break;
     652             :     }
     653             : 
     654           0 :     return false;
     655             : }
     656             : 
     657             : /*
     658             :  * HitTestNativeControl()
     659             :  *
     660             :  *  bIsInside is set to true if aPos is contained within the
     661             :  *  given part of the control, whose bounding region is
     662             :  *  given by rControlRegion (in VCL frame coordinates).
     663             :  *
     664             :  *  returns whether bIsInside was really set.
     665             :  */
     666           0 : bool GtkSalGraphics::hitTestNativeControl( ControlType        nType,
     667             :                                 ControlPart        nPart,
     668             :                                 const Rectangle&        rControlRegion,
     669             :                                 const Point&        aPos,
     670             :                                 bool&            rIsInside )
     671             : {
     672           0 :     if ( ( nType == CTRL_SCROLLBAR ) &&
     673           0 :          ( ( nPart == PART_BUTTON_UP ) ||
     674           0 :            ( nPart == PART_BUTTON_DOWN ) ||
     675           0 :            ( nPart == PART_BUTTON_LEFT ) ||
     676             :            ( nPart == PART_BUTTON_RIGHT ) ) )
     677             :     {
     678           0 :         NWEnsureGTKScrollbars( m_nXScreen );
     679             : 
     680             :         // Grab some button style attributes
     681             :         gboolean has_forward;
     682             :         gboolean has_forward2;
     683             :         gboolean has_backward;
     684             :         gboolean has_backward2;
     685             : 
     686           0 :         gtk_widget_style_get( gWidgetData[m_nXScreen].gScrollHorizWidget,
     687             :                               "has-forward-stepper", &has_forward,
     688             :                               "has-secondary-forward-stepper", &has_forward2,
     689             :                               "has-backward-stepper", &has_backward,
     690             :                               "has-secondary-backward-stepper", &has_backward2,
     691           0 :                               (char *)NULL );
     692           0 :         Rectangle aForward;
     693           0 :         Rectangle aBackward;
     694             : 
     695           0 :         rIsInside = false;
     696             : 
     697           0 :         ControlPart nCounterPart = 0;
     698           0 :         if ( nPart == PART_BUTTON_UP )
     699           0 :             nCounterPart = PART_BUTTON_DOWN;
     700           0 :         else if ( nPart == PART_BUTTON_DOWN )
     701           0 :             nCounterPart = PART_BUTTON_UP;
     702           0 :         else if ( nPart == PART_BUTTON_LEFT )
     703           0 :             nCounterPart = PART_BUTTON_RIGHT;
     704           0 :         else if ( nPart == PART_BUTTON_RIGHT )
     705           0 :             nCounterPart = PART_BUTTON_LEFT;
     706             : 
     707           0 :         aBackward = NWGetScrollButtonRect( m_nXScreen, nPart, rControlRegion );
     708           0 :         aForward = NWGetScrollButtonRect( m_nXScreen, nCounterPart, rControlRegion );
     709             : 
     710           0 :         if ( has_backward && has_forward2 )
     711             :         {
     712           0 :             Size aSize( aBackward.GetSize() );
     713           0 :             if ( ( nPart == PART_BUTTON_UP ) || ( nPart == PART_BUTTON_DOWN ) )
     714           0 :                 aSize.setHeight( aBackward.GetHeight() / 2 );
     715             :             else
     716           0 :                 aSize.setWidth( aBackward.GetWidth() / 2 );
     717           0 :             aBackward.SetSize( aSize );
     718             : 
     719           0 :             if ( nPart == PART_BUTTON_DOWN )
     720           0 :                 aBackward.Move( 0, aBackward.GetHeight() / 2 );
     721           0 :             else if ( nPart == PART_BUTTON_RIGHT )
     722           0 :                 aBackward.Move( aBackward.GetWidth() / 2, 0 );
     723             :         }
     724             : 
     725           0 :         if ( has_backward2 && has_forward )
     726             :         {
     727           0 :             Size aSize( aForward.GetSize() );
     728           0 :             if ( ( nPart == PART_BUTTON_UP ) || ( nPart == PART_BUTTON_DOWN ) )
     729           0 :                 aSize.setHeight( aForward.GetHeight() / 2 );
     730             :             else
     731           0 :                 aSize.setWidth( aForward.GetWidth() / 2 );
     732           0 :             aForward.SetSize( aSize );
     733             : 
     734           0 :             if ( nPart == PART_BUTTON_DOWN )
     735           0 :                 aForward.Move( 0, aForward.GetHeight() / 2 );
     736           0 :             else if ( nPart == PART_BUTTON_RIGHT )
     737           0 :                 aForward.Move( aForward.GetWidth() / 2, 0 );
     738             :         }
     739             : 
     740           0 :         if ( ( nPart == PART_BUTTON_UP ) || ( nPart == PART_BUTTON_LEFT ) )
     741             :         {
     742           0 :             if ( has_backward )
     743           0 :                 rIsInside |= aBackward.IsInside( aPos );
     744           0 :             if ( has_backward2 )
     745           0 :                 rIsInside |= aForward.IsInside( aPos );
     746             :         }
     747             :         else
     748             :         {
     749           0 :             if ( has_forward )
     750           0 :                 rIsInside |= aBackward.IsInside( aPos );
     751           0 :             if ( has_forward2 )
     752           0 :                 rIsInside |= aForward.IsInside( aPos );
     753             :         }
     754           0 :         return true;
     755             :     }
     756             : 
     757           0 :     if( IsNativeControlSupported(nType, nPart) )
     758             :     {
     759           0 :         rIsInside = rControlRegion.IsInside( aPos );
     760           0 :         return true;
     761             :     }
     762             :     else
     763             :     {
     764           0 :         return false;
     765             :     }
     766             : }
     767             : 
     768             : /*
     769             :  * DrawNativeControl()
     770             :  *
     771             :  *  Draws the requested control described by nPart/nState.
     772             :  *
     773             :  *  rControlRegion:    The bounding region of the complete control in VCL frame coordinates.
     774             :  *  aValue:          An optional value (tristate/numerical/string)
     775             :  *  rCaption:      A caption or title string (like button text etc)
     776             :  */
     777           0 : bool GtkSalGraphics::drawNativeControl(    ControlType nType,
     778             :                             ControlPart nPart,
     779             :                             const Rectangle& rControlRegion,
     780             :                             ControlState nState,
     781             :                             const ImplControlValue& aValue,
     782             :                             const OUString& rCaption )
     783             : {
     784             :     // get a GC with current clipping region set
     785           0 :     GetFontGC();
     786             : 
     787             :     // theme changed ?
     788           0 :     if( GtkSalGraphics::bThemeChanged )
     789             :     {
     790             :         // invalidate caches
     791           0 :         for( unsigned int i = 0; i < gWidgetData.size(); i++ )
     792           0 :             if( gWidgetData[i].gNWPixmapCacheList )
     793           0 :                 gWidgetData[i].gNWPixmapCacheList->ThemeChanged();
     794           0 :         GtkSalGraphics::bThemeChanged = false;
     795             :     }
     796             : 
     797           0 :     Rectangle aCtrlRect( rControlRegion );
     798           0 :     vcl::Region aClipRegion( m_aClipRegion );
     799           0 :     if( aClipRegion.IsNull() )
     800           0 :         aClipRegion = aCtrlRect;
     801             : 
     802           0 :     clipList aClip;
     803           0 :     GdkDrawable* gdkDrawable = GDK_DRAWABLE( GetGdkWindow() );
     804           0 :     GdkPixmap* pixmap = NULL;
     805           0 :     Rectangle aPixmapRect;
     806           0 :     if( ( bNeedPixmapPaint )
     807           0 :         && nType != CTRL_SCROLLBAR
     808           0 :         && nType != CTRL_SPINBOX
     809           0 :         && nType != CTRL_TAB_ITEM
     810           0 :         && nType != CTRL_TAB_PANE
     811           0 :         && nType != CTRL_PROGRESS
     812           0 :         && ! (nType == CTRL_TOOLBAR && (nPart == PART_THUMB_HORZ || nPart == PART_THUMB_VERT) )
     813             :         )
     814             :     {
     815             :         // make pixmap a little larger since some themes draw decoration
     816             :         // outside the rectangle, see e.g. checkbox
     817           0 :         aPixmapRect = Rectangle( Point( aCtrlRect.Left()-1, aCtrlRect.Top()-1 ),
     818           0 :                                  Size( aCtrlRect.GetWidth()+2, aCtrlRect.GetHeight()+2) );
     819           0 :         pixmap = NWGetPixmapFromScreen( aPixmapRect );
     820           0 :         if( ! pixmap )
     821           0 :             return false;
     822           0 :         gdkDrawable = GDK_DRAWABLE( pixmap );
     823           0 :         aCtrlRect = Rectangle( Point(1,1), aCtrlRect.GetSize() );
     824           0 :         aClip.push_back( aCtrlRect );
     825             :     }
     826             :     else
     827             :     {
     828           0 :         RectangleVector aRectangles;
     829           0 :         aClipRegion.GetRegionRectangles(aRectangles);
     830             : 
     831           0 :         for(RectangleVector::const_iterator aRectIter(aRectangles.begin()); aRectIter != aRectangles.end(); ++aRectIter)
     832             :         {
     833           0 :             Rectangle aPaintRect = aCtrlRect.GetIntersection(*aRectIter);
     834           0 :             if( aPaintRect.IsEmpty() )
     835           0 :                 continue;
     836           0 :             aClip.push_back( aPaintRect );
     837           0 :         }
     838             :     }
     839             : 
     840             :     assert(gdkDrawable && "rhbz#1050162");
     841           0 :     if (gdkDrawable == 0)
     842           0 :         return false;
     843             : 
     844           0 :     bool            returnVal = false;
     845           0 :     if ( (nType==CTRL_PUSHBUTTON) && (nPart==PART_ENTIRE_CONTROL) )
     846             :     {
     847           0 :         returnVal = NWPaintGTKButton( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     848             :     }
     849           0 :     else if ( (nType==CTRL_RADIOBUTTON) && (nPart==PART_ENTIRE_CONTROL) )
     850             :     {
     851           0 :         returnVal = NWPaintGTKRadio( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     852             :     }
     853           0 :     else if ( (nType==CTRL_CHECKBOX) && (nPart==PART_ENTIRE_CONTROL) )
     854             :     {
     855           0 :         returnVal = NWPaintGTKCheck( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     856             :     }
     857           0 :     else if ( (nType==CTRL_SCROLLBAR) && ((nPart==PART_DRAW_BACKGROUND_HORZ) || (nPart==PART_DRAW_BACKGROUND_VERT)) )
     858             :     {
     859           0 :         returnVal = NWPaintGTKScrollbar( nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     860             :     }
     861           0 :     else if ( ((nType==CTRL_EDITBOX) && ((nPart==PART_ENTIRE_CONTROL) || (nPart==HAS_BACKGROUND_TEXTURE)) )
     862           0 :         || ((nType==CTRL_SPINBOX) && (nPart==HAS_BACKGROUND_TEXTURE))
     863           0 :     || ((nType==CTRL_COMBOBOX) && (nPart==HAS_BACKGROUND_TEXTURE))
     864           0 :     || ((nType==CTRL_LISTBOX) && (nPart==HAS_BACKGROUND_TEXTURE)) )
     865             :     {
     866           0 :         returnVal = NWPaintGTKEditBox( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     867             :     }
     868           0 :     else if ( ((nType==CTRL_MULTILINE_EDITBOX) && ((nPart==PART_ENTIRE_CONTROL) || (nPart==HAS_BACKGROUND_TEXTURE)) ) )
     869             :     {
     870           0 :         returnVal = NWPaintGTKEditBox( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     871             :     }
     872           0 :     else if ( ((nType==CTRL_SPINBOX) || (nType==CTRL_SPINBUTTONS))
     873           0 :         && ((nPart==PART_ENTIRE_CONTROL) || (nPart==PART_ALL_BUTTONS)) )
     874             :     {
     875           0 :         returnVal = NWPaintGTKSpinBox( nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     876             :     }
     877           0 :     else if ( (nType == CTRL_COMBOBOX) &&
     878             :         ( (nPart==PART_ENTIRE_CONTROL)
     879           0 :         ||(nPart==PART_BUTTON_DOWN)
     880             :         ) )
     881             :     {
     882           0 :         returnVal = NWPaintGTKComboBox( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     883             :     }
     884           0 :     else if ( (nType==CTRL_TAB_ITEM) || (nType==CTRL_TAB_PANE) || (nType==CTRL_TAB_BODY) )
     885             :     {
     886           0 :         if ( nType == CTRL_TAB_BODY )
     887           0 :             returnVal = true;
     888             :         else
     889           0 :             returnVal = NWPaintGTKTabItem( nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption);
     890             :     }
     891           0 :     else if ( (nType==CTRL_LISTBOX) && ((nPart==PART_ENTIRE_CONTROL) || (nPart==PART_WINDOW)) )
     892             :     {
     893           0 :         returnVal = NWPaintGTKListBox( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     894             :     }
     895           0 :     else if ( nType== CTRL_TOOLBAR )
     896             :     {
     897           0 :         returnVal = NWPaintGTKToolbar( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     898             :     }
     899           0 :     else if ( nType== CTRL_MENUBAR )
     900             :     {
     901           0 :         returnVal = NWPaintGTKMenubar( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     902             :     }
     903           0 :     else if(    (nType == CTRL_MENU_POPUP)
     904           0 :         && (  (nPart == PART_ENTIRE_CONTROL)
     905           0 :     || (nPart == PART_MENU_ITEM)
     906           0 :     || (nPart == PART_MENU_ITEM_CHECK_MARK)
     907           0 :     || (nPart == PART_MENU_ITEM_RADIO_MARK)
     908           0 :     || (nPart == PART_MENU_SEPARATOR)
     909           0 :     || (nPart == PART_MENU_SUBMENU_ARROW)
     910             :     )
     911             :     )
     912             :     {
     913           0 :         returnVal = NWPaintGTKPopupMenu( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     914             :     }
     915           0 :     else if( (nType == CTRL_TOOLTIP) && (nPart == PART_ENTIRE_CONTROL) )
     916             :     {
     917           0 :         returnVal = NWPaintGTKTooltip( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     918             :     }
     919           0 :     else if( (nType == CTRL_PROGRESS) && (nPart == PART_ENTIRE_CONTROL) )
     920             :     {
     921           0 :         returnVal = NWPaintGTKProgress( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     922             :     }
     923           0 :     else if( (nType == CTRL_LISTNODE) && (nPart == PART_ENTIRE_CONTROL) )
     924             :     {
     925           0 :         returnVal = NWPaintGTKListNode( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     926             :     }
     927           0 :     else if( (nType == CTRL_LISTNET) && (nPart == PART_ENTIRE_CONTROL) )
     928             :     {
     929             :         // don't actually draw anything; gtk treeviews do not draw lines
     930           0 :         returnVal = TRUE;
     931             :     }
     932           0 :     else if( nType == CTRL_SLIDER )
     933             :     {
     934           0 :         returnVal = NWPaintGTKSlider( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     935             :     }
     936           0 :     else if( nType == CTRL_WINDOW_BACKGROUND )
     937             :     {
     938           0 :         returnVal = NWPaintGTKWindowBackground( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     939             :     }
     940           0 :     else if( nType == CTRL_FIXEDLINE )
     941             :     {
     942           0 :         returnVal = NWPaintGTKFixedLine( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     943             :     }
     944           0 :     else if(nType==CTRL_FRAME)
     945             :     {
     946           0 :         returnVal = NWPaintGTKFrame( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption);
     947             :     }
     948           0 :     else if(nType==CTRL_LISTHEADER)
     949             :     {
     950           0 :         if(nPart == PART_BUTTON)
     951           0 :             returnVal = NWPaintGTKListHeader( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     952           0 :         else if(nPart == PART_ARROW)
     953           0 :             returnVal = NWPaintGTKArrow( gdkDrawable, nType, nPart, aCtrlRect, aClip, nState, aValue, rCaption );
     954             :     }
     955             : 
     956           0 :     if( pixmap )
     957             :     {
     958           0 :         returnVal = NWRenderPixmapToScreen( pixmap, aPixmapRect ) && returnVal;
     959           0 :         g_object_unref( pixmap );
     960             :     }
     961             : 
     962           0 :     return( returnVal );
     963             : }
     964             : 
     965             : /*
     966             :  * GetNativeControlRegion()
     967             :  *
     968             :  *  If the return value is true, rNativeBoundingRegion
     969             :  *  contains the true bounding region covered by the control
     970             :  *  including any adornment, while rNativeContentRegion contains the area
     971             :  *  within the control that can be safely drawn into without drawing over
     972             :  *  the borders of the control.
     973             :  *
     974             :  *  rControlRegion:    The bounding region of the control in VCL frame coordinates.
     975             :  *  aValue:        An optional value (tristate/numerical/string)
     976             :  *  rCaption:        A caption or title string (like button text etc)
     977             :  */
     978           0 : bool GtkSalGraphics::getNativeControlRegion(  ControlType nType,
     979             :                                 ControlPart nPart,
     980             :                                 const Rectangle& rControlRegion,
     981             :                                 ControlState nState,
     982             :                                 const ImplControlValue& aValue,
     983             :                                 const OUString& rCaption,
     984             :                                 Rectangle &rNativeBoundingRegion,
     985             :                                 Rectangle &rNativeContentRegion )
     986             : {
     987           0 :     bool returnVal = false;
     988             : 
     989           0 :     if ( (nType==CTRL_PUSHBUTTON) && (nPart==PART_ENTIRE_CONTROL)
     990           0 :         && (rControlRegion.GetWidth() > 16)
     991           0 :     && (rControlRegion.GetHeight() > 16) )
     992             :     {
     993             :         rNativeBoundingRegion = NWGetButtonArea( m_nXScreen, nType, nPart, rControlRegion,
     994           0 :         nState, aValue, rCaption );
     995           0 :         rNativeContentRegion = rControlRegion;
     996             : 
     997           0 :         returnVal = true;
     998             :     }
     999           0 :     if (nType == CTRL_TAB_ITEM && nPart == PART_ENTIRE_CONTROL)
    1000             :     {
    1001           0 :         rNativeBoundingRegion = NWGetTabItemRect(m_nXScreen, rControlRegion);
    1002           0 :         rNativeContentRegion = rNativeBoundingRegion;
    1003           0 :         returnVal = true;
    1004             :     }
    1005           0 :     if ( (nType==CTRL_COMBOBOX) && ((nPart==PART_BUTTON_DOWN) || (nPart==PART_SUB_EDIT)) )
    1006             :     {
    1007             :         rNativeBoundingRegion = NWGetComboBoxButtonRect( m_nXScreen, nType, nPart, rControlRegion, nState,
    1008           0 :         aValue, rCaption );
    1009           0 :         rNativeContentRegion = rNativeBoundingRegion;
    1010             : 
    1011           0 :         returnVal = true;
    1012             :     }
    1013           0 :     if ( (nType==CTRL_SPINBOX) && ((nPart==PART_BUTTON_UP) || (nPart==PART_BUTTON_DOWN) || (nPart==PART_SUB_EDIT)) )
    1014             :     {
    1015             : 
    1016             :         rNativeBoundingRegion = NWGetSpinButtonRect( m_nXScreen, nType, nPart, rControlRegion, nState,
    1017           0 :         aValue, rCaption );
    1018           0 :         rNativeContentRegion = rNativeBoundingRegion;
    1019             : 
    1020           0 :         returnVal = true;
    1021             :     }
    1022           0 :     if ( (nType==CTRL_LISTBOX) && ((nPart==PART_BUTTON_DOWN) || (nPart==PART_SUB_EDIT)) )
    1023             :     {
    1024             :         rNativeBoundingRegion = NWGetListBoxButtonRect( m_nXScreen, nType, nPart, rControlRegion, nState,
    1025           0 :         aValue, rCaption );
    1026           0 :         rNativeContentRegion = rNativeBoundingRegion;
    1027             : 
    1028           0 :         returnVal = true;
    1029             :     }
    1030           0 :     if ( (nType==CTRL_TOOLBAR) &&
    1031           0 :         ((nPart==PART_DRAW_BACKGROUND_HORZ)    ||
    1032           0 :         (nPart==PART_DRAW_BACKGROUND_VERT)    ||
    1033           0 :         (nPart==PART_THUMB_HORZ)            ||
    1034           0 :         (nPart==PART_THUMB_VERT)            ||
    1035             :         (nPart==PART_BUTTON)
    1036             :         ))
    1037             :     {
    1038           0 :         rNativeBoundingRegion = NWGetToolbarRect( m_nXScreen, nType, nPart, rControlRegion, nState, aValue, rCaption );
    1039           0 :         rNativeContentRegion = rNativeBoundingRegion;
    1040           0 :         returnVal = true;
    1041             :     }
    1042           0 :     if ( (nType==CTRL_SCROLLBAR) && ((nPart==PART_BUTTON_LEFT) || (nPart==PART_BUTTON_RIGHT) ||
    1043           0 :         (nPart==PART_BUTTON_UP) || (nPart==PART_BUTTON_DOWN)  ) )
    1044             :     {
    1045           0 :         rNativeBoundingRegion = NWGetScrollButtonRect( m_nXScreen, nPart, rControlRegion );
    1046           0 :         rNativeContentRegion = rNativeBoundingRegion;
    1047             : 
    1048             :         //See fdo#33523, possibly makes sense to do this test for all return values
    1049           0 :         if (!rNativeContentRegion.GetWidth())
    1050           0 :             rNativeContentRegion.Right() = rNativeContentRegion.Left() + 1;
    1051           0 :         if (!rNativeContentRegion.GetHeight())
    1052           0 :             rNativeContentRegion.Bottom() = rNativeContentRegion.Top() + 1;
    1053           0 :         returnVal = true;
    1054             :     }
    1055           0 :     if( (nType == CTRL_MENUBAR) && (nPart == PART_ENTIRE_CONTROL) )
    1056             :     {
    1057           0 :         NWEnsureGTKMenubar( m_nXScreen );
    1058             :         GtkRequisition aReq;
    1059           0 :         gtk_widget_size_request( gWidgetData[m_nXScreen].gMenubarWidget, &aReq );
    1060           0 :         Rectangle aMenuBarRect = rControlRegion;
    1061             :         aMenuBarRect = Rectangle( aMenuBarRect.TopLeft(),
    1062           0 :                                   Size( aMenuBarRect.GetWidth(), aReq.height+1 ) );
    1063           0 :         rNativeBoundingRegion = aMenuBarRect;
    1064           0 :         rNativeContentRegion = rNativeBoundingRegion;
    1065           0 :         returnVal = true;
    1066             :     }
    1067           0 :     if( nType == CTRL_MENU_POPUP )
    1068             :     {
    1069           0 :         if( (nPart == PART_MENU_ITEM_CHECK_MARK) ||
    1070             :             (nPart == PART_MENU_ITEM_RADIO_MARK) )
    1071             :         {
    1072           0 :             NWEnsureGTKMenu( m_nXScreen );
    1073             : 
    1074           0 :             gint indicator_size = 0;
    1075             :             GtkWidget* pWidget = (nPart == PART_MENU_ITEM_CHECK_MARK) ?
    1076           0 :                 gWidgetData[m_nXScreen].gMenuItemCheckMenuWidget : gWidgetData[m_nXScreen].gMenuItemRadioMenuWidget;
    1077             :             gtk_widget_style_get( pWidget,
    1078             :                                   "indicator_size", &indicator_size,
    1079           0 :                                   (char *)NULL );
    1080           0 :             rNativeBoundingRegion = rControlRegion;
    1081             :             Rectangle aIndicatorRect( Point( 0,
    1082           0 :                                              (rControlRegion.GetHeight()-indicator_size)/2),
    1083           0 :                                       Size( indicator_size, indicator_size ) );
    1084           0 :             rNativeContentRegion = aIndicatorRect;
    1085           0 :             returnVal = true;
    1086             :         }
    1087           0 :         else if( nPart == PART_MENU_SUBMENU_ARROW )
    1088             :         {
    1089           0 :             GtkWidget* widget = gWidgetData[m_nXScreen].gMenuItemMenuWidget;
    1090             :             GtkWidget* child;
    1091             :             PangoContext *context;
    1092             :             PangoFontMetrics *metrics;
    1093             :             gint arrow_size;
    1094             :             gint arrow_extent;
    1095             :             guint horizontal_padding;
    1096           0 :             gfloat arrow_scaling = 0.4; // Default for early GTK versions
    1097             : 
    1098             :             gtk_widget_style_get( widget,
    1099             :                                   "horizontal-padding", &horizontal_padding,
    1100           0 :                                   NULL );
    1101             : 
    1102             :             // Use arrow-scaling property if available (2.15+), avoid warning otherwise
    1103           0 :             if ( gtk_widget_class_find_style_property( GTK_WIDGET_GET_CLASS( widget ),
    1104           0 :                                                        "arrow-scaling" ) )
    1105             :             {
    1106             :                 gtk_widget_style_get( widget,
    1107             :                                       "arrow-scaling", &arrow_scaling,
    1108           0 :                                       NULL );
    1109             :             }
    1110             : 
    1111           0 :             child = GTK_BIN( widget )->child;
    1112             : 
    1113           0 :             context = gtk_widget_get_pango_context( child );
    1114             :             metrics = pango_context_get_metrics( context,
    1115             :                                                  child->style->font_desc,
    1116           0 :                                                  pango_context_get_language( context ) );
    1117             : 
    1118           0 :             arrow_size = ( PANGO_PIXELS( pango_font_metrics_get_ascent( metrics ) +
    1119           0 :                                          pango_font_metrics_get_descent( metrics ) ));
    1120             : 
    1121           0 :             pango_font_metrics_unref( metrics );
    1122             : 
    1123           0 :             arrow_extent = static_cast<gint>(arrow_size * arrow_scaling);
    1124             : 
    1125             :             rNativeContentRegion = Rectangle( Point( 0, 0 ),
    1126           0 :                                               Size( arrow_extent, arrow_extent ));
    1127             :             rNativeBoundingRegion = Rectangle( Point( 0, 0 ),
    1128           0 :                                                Size( arrow_extent + horizontal_padding, arrow_extent ));
    1129           0 :             returnVal = true;
    1130             :         }
    1131             :     }
    1132           0 :     if( (nType == CTRL_RADIOBUTTON || nType == CTRL_CHECKBOX) )
    1133             :     {
    1134           0 :         NWEnsureGTKRadio( m_nXScreen );
    1135           0 :         NWEnsureGTKCheck( m_nXScreen );
    1136           0 :         GtkWidget* widget = (nType == CTRL_RADIOBUTTON) ? gWidgetData[m_nXScreen].gRadioWidget : gWidgetData[m_nXScreen].gCheckWidget;
    1137             :         gint indicator_size, indicator_spacing, focusPad, focusWidth;
    1138             :         gtk_widget_style_get( widget,
    1139             :                               "indicator_size", &indicator_size,
    1140             :                               "indicator_spacing", &indicator_spacing,
    1141             :                               "focus-line-width", &focusWidth,
    1142             :                               "focus-padding", &focusPad,
    1143           0 :                               (char *)NULL);
    1144           0 :         indicator_size += 2*indicator_spacing + 2*(focusWidth + focusWidth);
    1145           0 :         rNativeBoundingRegion = rControlRegion;
    1146             :         Rectangle aIndicatorRect( Point( 0,
    1147           0 :                                          (rControlRegion.GetHeight()-indicator_size)/2),
    1148           0 :                                   Size( indicator_size, indicator_size ) );
    1149           0 :         rNativeContentRegion = aIndicatorRect;
    1150           0 :         returnVal = true;
    1151             :     }
    1152           0 :     if( (nType == CTRL_EDITBOX || nType == CTRL_SPINBOX || nType == CTRL_COMBOBOX) && nPart == PART_ENTIRE_CONTROL )
    1153             :     {
    1154           0 :         NWEnsureGTKEditBox( m_nXScreen );
    1155           0 :         GtkWidget* widget = gWidgetData[m_nXScreen].gEditBoxWidget;
    1156             :         GtkRequisition aReq;
    1157           0 :         gtk_widget_size_request( widget, &aReq );
    1158           0 :         Rectangle aEditRect = rControlRegion;
    1159           0 :         long nHeight = (aEditRect.GetHeight() > aReq.height) ? aEditRect.GetHeight() : aReq.height;
    1160             :         aEditRect = Rectangle( aEditRect.TopLeft(),
    1161           0 :                                Size( aEditRect.GetWidth(), nHeight ) );
    1162           0 :         rNativeBoundingRegion = aEditRect;
    1163           0 :         rNativeContentRegion = rNativeBoundingRegion;
    1164           0 :         returnVal = true;
    1165             :     }
    1166           0 :     if( (nType == CTRL_SLIDER) && (nPart == PART_THUMB_HORZ || nPart == PART_THUMB_VERT) )
    1167             :     {
    1168           0 :         NWEnsureGTKSlider( m_nXScreen );
    1169           0 :         GtkWidget* widget = (nPart == PART_THUMB_HORZ) ? gWidgetData[m_nXScreen].gHScale : gWidgetData[m_nXScreen].gVScale;
    1170           0 :         gint slider_length = 10;
    1171           0 :         gint slider_width = 10;
    1172             :         gtk_widget_style_get( widget,
    1173             :                               "slider-width", &slider_width,
    1174             :                               "slider-length", &slider_length,
    1175           0 :                               (char *)NULL);
    1176           0 :         Rectangle aRect( rControlRegion );
    1177           0 :         if( nPart == PART_THUMB_HORZ )
    1178             :         {
    1179           0 :             aRect.Right() = aRect.Left() + slider_length - 1;
    1180           0 :             aRect.Bottom() = aRect.Top() + slider_width - 1;
    1181             :         }
    1182             :         else
    1183             :         {
    1184           0 :             aRect.Bottom() = aRect.Top() + slider_length - 1;
    1185           0 :             aRect.Right() = aRect.Left() + slider_width - 1;
    1186             :         }
    1187           0 :         rNativeBoundingRegion = rNativeContentRegion = aRect;
    1188           0 :         returnVal = true;
    1189             :     }
    1190           0 :     if( nType == CTRL_FRAME && nPart == PART_BORDER )
    1191             :     {
    1192           0 :         int frameWidth = getFrameWidth(gWidgetData[m_nXScreen].gFrame);
    1193           0 :         rNativeBoundingRegion = rControlRegion;
    1194           0 :         sal_uInt16 nStyle = aValue.getNumericVal();
    1195           0 :         int x1=rControlRegion.Left();
    1196           0 :         int y1=rControlRegion.Top();
    1197           0 :         int x2=rControlRegion.Right();
    1198           0 :         int y2=rControlRegion.Bottom();
    1199             : 
    1200           0 :         if( nStyle & FRAME_DRAW_NODRAW )
    1201             :         {
    1202           0 :             rNativeContentRegion = Rectangle(x1+frameWidth,
    1203           0 :                                              y1+frameWidth,
    1204           0 :                                              x2-frameWidth,
    1205           0 :                                              y2-frameWidth);
    1206             :         }
    1207             :         else
    1208           0 :             rNativeContentRegion = rControlRegion;
    1209           0 :         returnVal=true;
    1210             :     }
    1211             : 
    1212           0 :     return( returnVal );
    1213             : }
    1214             : 
    1215             : /************************************************************************
    1216             :  * Individual control drawing functions
    1217             :  ************************************************************************/
    1218           0 : bool GtkSalGraphics::NWPaintGTKArrow(
    1219             :             GdkDrawable* gdkDrawable,
    1220             :             ControlType, ControlPart,
    1221             :             const Rectangle& rControlRectangle,
    1222             :             const clipList& rClipList,
    1223             :             ControlState nState, const ImplControlValue& aValue,
    1224             :             const OUString& )
    1225             : {
    1226           0 :     GtkArrowType arrowType(aValue.getNumericVal()&1?GTK_ARROW_DOWN:GTK_ARROW_UP);
    1227           0 :     GtkStateType stateType(nState&CTRL_STATE_PRESSED?GTK_STATE_ACTIVE:GTK_STATE_NORMAL);
    1228             : 
    1229             :     GdkRectangle clipRect;
    1230           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    1231             :     {
    1232           0 :         clipRect.x = it->Left();
    1233           0 :         clipRect.y = it->Top();
    1234           0 :         clipRect.width = it->GetWidth();
    1235           0 :         clipRect.height = it->GetHeight();
    1236             : 
    1237             :         gtk_paint_arrow(m_pWindow->style,gdkDrawable,stateType,GTK_SHADOW_NONE,&clipRect,
    1238             :                 m_pWindow,"arrow",arrowType,true,
    1239           0 :                 rControlRectangle.Left(),
    1240           0 :                 rControlRectangle.Top(),
    1241           0 :                 rControlRectangle.GetWidth(),
    1242           0 :                 rControlRectangle.GetHeight());
    1243             :     }
    1244           0 :     return true;
    1245             : }
    1246             : 
    1247           0 : bool GtkSalGraphics::NWPaintGTKListHeader(
    1248             :             GdkDrawable* gdkDrawable,
    1249             :             ControlType, ControlPart,
    1250             :             const Rectangle& rControlRectangle,
    1251             :             const clipList& rClipList,
    1252             :             ControlState nState, const ImplControlValue&,
    1253             :             const OUString& )
    1254             : {
    1255             :     GtkStateType    stateType;
    1256             :     GtkShadowType    shadowType;
    1257           0 :     NWEnsureGTKTreeView( m_nXScreen );
    1258           0 :     GtkWidget* &treeview(gWidgetData[m_nXScreen].gTreeView);
    1259           0 :     GtkTreeViewColumn* column=gtk_tree_view_get_column(GTK_TREE_VIEW(treeview),0);
    1260           0 :     GtkWidget* button=gtk_tree_view_column_get_widget(column);
    1261           0 :     while(button && !GTK_IS_BUTTON(button))
    1262           0 :         button=gtk_widget_get_parent(button);
    1263           0 :     if(!button)
    1264             :         // Shouldn't ever happen
    1265           0 :         return false;
    1266           0 :     gtk_widget_realize(button);
    1267           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    1268           0 :     NWSetWidgetState( button, nState, stateType );
    1269             : 
    1270             :     GdkRectangle clipRect;
    1271           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    1272             :     {
    1273           0 :         clipRect.x = it->Left();
    1274           0 :         clipRect.y = it->Top();
    1275           0 :         clipRect.width = it->GetWidth();
    1276           0 :         clipRect.height = it->GetHeight();
    1277             : 
    1278             :         gtk_paint_box(button->style,gdkDrawable,stateType,shadowType,&clipRect,
    1279             :                 button,"button",
    1280           0 :                 rControlRectangle.Left()-1,
    1281           0 :                 rControlRectangle.Top(),
    1282           0 :                 rControlRectangle.GetWidth()+1,
    1283           0 :                 rControlRectangle.GetHeight());
    1284             :     }
    1285           0 :     return true;
    1286             : }
    1287             : 
    1288           0 : bool GtkSalGraphics::NWPaintGTKFixedLine(
    1289             :             GdkDrawable* gdkDrawable,
    1290             :             ControlType, ControlPart nPart,
    1291             :             const Rectangle& rControlRectangle,
    1292             :             const clipList&,
    1293             :             ControlState, const ImplControlValue&,
    1294             :             const OUString& )
    1295             : {
    1296           0 :     if(nPart == PART_SEPARATOR_HORZ)
    1297           0 :         gtk_paint_hline(m_pWindow->style,gdkDrawable,GTK_STATE_NORMAL,NULL,m_pWindow,"hseparator",rControlRectangle.Left(),rControlRectangle.Right(),rControlRectangle.Top());
    1298             :     else
    1299           0 :         gtk_paint_vline(m_pWindow->style,gdkDrawable,GTK_STATE_NORMAL,NULL,m_pWindow,"vseparator",rControlRectangle.Top(),rControlRectangle.Bottom(),rControlRectangle.Left());
    1300             : 
    1301           0 :     return true;
    1302             : }
    1303             : 
    1304           0 : bool GtkSalGraphics::NWPaintGTKFrame(
    1305             :             GdkDrawable* gdkDrawable,
    1306             :             ControlType, ControlPart,
    1307             :             const Rectangle& rControlRectangle,
    1308             :             const clipList& rClipList,
    1309             :             ControlState /* nState */, const ImplControlValue& aValue,
    1310             :             const OUString& )
    1311             : {
    1312             :     GdkRectangle clipRect;
    1313           0 :     int frameWidth=getFrameWidth(gWidgetData[m_nXScreen].gFrame);
    1314           0 :     GtkShadowType shadowType=GTK_SHADOW_IN;
    1315           0 :     sal_uInt16 nStyle = aValue.getNumericVal();
    1316           0 :     if( nStyle & FRAME_DRAW_IN )
    1317           0 :         shadowType=GTK_SHADOW_OUT;
    1318           0 :     if( nStyle & FRAME_DRAW_OUT )
    1319           0 :         shadowType=GTK_SHADOW_IN;
    1320             : 
    1321           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    1322             :     {
    1323           0 :         clipRect.x = it->Left();
    1324           0 :         clipRect.y = it->Top();
    1325           0 :         clipRect.width = it->GetWidth();
    1326           0 :         clipRect.height = it->GetHeight();
    1327             : 
    1328             :         // Draw background first
    1329             : 
    1330             :         // Top
    1331             :         gtk_paint_flat_box(m_pWindow->style,gdkDrawable,GTK_STATE_NORMAL,GTK_SHADOW_OUT,&clipRect,
    1332             :                          m_pWindow,"base",
    1333           0 :                          rControlRectangle.Left(),
    1334           0 :                          rControlRectangle.Top(),
    1335           0 :                          rControlRectangle.GetWidth(),
    1336           0 :                          frameWidth);
    1337             :         // Bottom
    1338             :         gtk_paint_flat_box(m_pWindow->style,gdkDrawable,GTK_STATE_NORMAL,GTK_SHADOW_OUT,&clipRect,
    1339             :                          m_pWindow,"base",
    1340           0 :                          rControlRectangle.Left(),
    1341           0 :                          rControlRectangle.Top()+rControlRectangle.GetHeight()-frameWidth,
    1342           0 :                          rControlRectangle.GetWidth(),
    1343           0 :                          frameWidth);
    1344             :         // Left
    1345             :         gtk_paint_flat_box(m_pWindow->style,gdkDrawable,GTK_STATE_NORMAL,GTK_SHADOW_OUT,&clipRect,
    1346             :                          m_pWindow,"base",
    1347           0 :                          rControlRectangle.Left(),
    1348           0 :                          rControlRectangle.Top(),
    1349             :                          2*frameWidth,
    1350           0 :                          rControlRectangle.GetHeight());
    1351             :         // Right
    1352             :         gtk_paint_flat_box(m_pWindow->style,gdkDrawable,GTK_STATE_NORMAL,GTK_SHADOW_OUT,&clipRect,
    1353             :                          m_pWindow,"base",
    1354           0 :                          rControlRectangle.Left()+rControlRectangle.GetWidth()-frameWidth,
    1355           0 :                          rControlRectangle.Top(),
    1356             :                          2*frameWidth,
    1357           0 :                          rControlRectangle.GetHeight());
    1358             : 
    1359             :         // Now render the frame
    1360           0 :         gtk_paint_shadow(gWidgetData[m_nXScreen].gFrame->style,gdkDrawable,GTK_STATE_NORMAL,shadowType,&clipRect,
    1361           0 :                          gWidgetData[m_nXScreen].gFrame,"base",
    1362           0 :                          rControlRectangle.Left(),
    1363           0 :                          rControlRectangle.Top(),
    1364           0 :                          rControlRectangle.GetWidth(),
    1365           0 :                          rControlRectangle.GetHeight());
    1366             :     }
    1367             : 
    1368           0 :     return true;
    1369             : }
    1370             : 
    1371           0 : bool GtkSalGraphics::NWPaintGTKWindowBackground(
    1372             :             GdkDrawable* gdkDrawable,
    1373             :             ControlType, ControlPart,
    1374             :             const Rectangle& /* rControlRectangle */,
    1375             :             const clipList& rClipList,
    1376             :             ControlState /* nState */, const ImplControlValue&,
    1377             :             const OUString& )
    1378             : {
    1379             :     int w,h;
    1380           0 :     gtk_window_get_size(GTK_WINDOW(m_pWindow),&w,&h);
    1381             :     GdkRectangle clipRect;
    1382           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    1383             :     {
    1384           0 :         clipRect.x = it->Left();
    1385           0 :         clipRect.y = it->Top();
    1386           0 :         clipRect.width = it->GetWidth();
    1387           0 :         clipRect.height = it->GetHeight();
    1388             : 
    1389           0 :         gtk_paint_flat_box(m_pWindow->style,gdkDrawable,GTK_STATE_NORMAL,GTK_SHADOW_NONE,&clipRect,m_pWindow,"base",0,0,w,h);
    1390             :     }
    1391             : 
    1392           0 :     return true;
    1393             : }
    1394             : 
    1395           0 : bool GtkSalGraphics::NWPaintGTKButtonReal(
    1396             :             GtkWidget* button,
    1397             :             GdkDrawable* gdkDrawable,
    1398             :             ControlType, ControlPart,
    1399             :             const Rectangle& rControlRectangle,
    1400             :             const clipList& rClipList,
    1401             :             ControlState nState, const ImplControlValue&,
    1402             :             const OUString& )
    1403             : {
    1404             :     GtkStateType    stateType;
    1405             :     GtkShadowType    shadowType;
    1406             :     gboolean        interiorFocus;
    1407             :     gint            focusWidth;
    1408             :     gint            focusPad;
    1409           0 :     bool            bDrawFocus = true;
    1410             :     gint            x, y, w, h;
    1411             :     GtkBorder        aDefBorder;
    1412             :     GtkBorder*        pBorder;
    1413             :     GdkRectangle    clipRect;
    1414             : 
    1415           0 :     NWEnsureGTKButton( m_nXScreen );
    1416           0 :     NWEnsureGTKToolbar( m_nXScreen );
    1417             : 
    1418             :     // Flat toolbutton has a bit bigger variety of states than normal buttons, so handle it differently
    1419           0 :     if(GTK_IS_TOGGLE_BUTTON(button))
    1420             :     {
    1421           0 :        if(gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(button)))
    1422           0 :            shadowType=GTK_SHADOW_IN;
    1423             :        else
    1424           0 :            shadowType=GTK_SHADOW_OUT;
    1425             : 
    1426           0 :        if(nState & CTRL_STATE_ROLLOVER)
    1427           0 :            stateType=GTK_STATE_PRELIGHT;
    1428             :        else
    1429           0 :            stateType=GTK_STATE_NORMAL;
    1430             : 
    1431           0 :        if(nState & CTRL_STATE_PRESSED)
    1432             :        {
    1433           0 :            stateType=GTK_STATE_ACTIVE;
    1434           0 :            shadowType=GTK_SHADOW_IN;
    1435             :        }
    1436             :     }
    1437             :     else
    1438             :     {
    1439           0 :         NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    1440           0 :         NWSetWidgetState( gWidgetData[m_nXScreen].gBtnWidget, nState, stateType );
    1441             :     }
    1442             : 
    1443           0 :     x = rControlRectangle.Left();
    1444           0 :     y = rControlRectangle.Top();
    1445           0 :     w = rControlRectangle.GetWidth();
    1446           0 :     h = rControlRectangle.GetHeight();
    1447             : 
    1448           0 :     gint internal_padding = 0;
    1449           0 :     if(GTK_IS_TOOL_ITEM(button))
    1450             :     {
    1451           0 :         gtk_widget_style_get (GTK_WIDGET (gWidgetData[m_nXScreen].gToolbarWidget),
    1452             :                 "internal-padding", &internal_padding,
    1453           0 :                 NULL);
    1454           0 :         x += internal_padding/2;
    1455           0 :         w -= internal_padding;
    1456           0 :         stateType = GTK_STATE_PRELIGHT;
    1457             :     }
    1458             : 
    1459             :     // Grab some button style attributes
    1460           0 :     gtk_widget_style_get( gWidgetData[m_nXScreen].gBtnWidget,    "focus-line-width",    &focusWidth,
    1461             :                                 "focus-padding",     &focusPad,
    1462             :                                  "interior_focus",    &interiorFocus,
    1463           0 :                                 (char *)NULL );
    1464           0 :     gtk_widget_style_get( gWidgetData[m_nXScreen].gBtnWidget,
    1465             :                                 "default_border",    &pBorder,
    1466           0 :                                 (char *)NULL );
    1467             : 
    1468             :     // Make sure the border values exist, otherwise use some defaults
    1469           0 :     if ( pBorder )
    1470             :     {
    1471           0 :         NW_gtk_border_set_from_border( aDefBorder, pBorder );
    1472           0 :         gtk_border_free( pBorder );
    1473             :     }
    1474           0 :     else NW_gtk_border_set_from_border( aDefBorder, &aDefDefBorder );
    1475             : 
    1476             :     // If the button is too small, don't ever draw focus or grab more space
    1477           0 :     if ( (w < 16) || (h < 16) )
    1478           0 :         bDrawFocus = false;
    1479             : 
    1480           0 :     gint xi = x, yi = y, wi = w, hi = h;
    1481           0 :     if ( (nState & CTRL_STATE_DEFAULT) && bDrawFocus )
    1482             :     {
    1483           0 :         xi += aDefBorder.left;
    1484           0 :         yi += aDefBorder.top;
    1485           0 :         wi -= aDefBorder.left + aDefBorder.right;
    1486           0 :         hi -= aDefBorder.top + aDefBorder.bottom;
    1487             :     }
    1488             : 
    1489           0 :     if ( !interiorFocus && bDrawFocus )
    1490             :     {
    1491           0 :         xi += focusWidth + focusPad;
    1492           0 :         yi += focusWidth + focusPad;
    1493           0 :         wi -= 2 * (focusWidth + focusPad);
    1494           0 :         hi -= 2 * (focusWidth + focusPad);
    1495             :     }
    1496           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it)
    1497             :     {
    1498           0 :         clipRect.x = it->Left();
    1499           0 :         clipRect.y = it->Top();
    1500           0 :         clipRect.width = it->GetWidth();
    1501           0 :         clipRect.height = it->GetHeight();
    1502             : 
    1503             :         // Buttons must paint opaque since some themes have alpha-channel enabled buttons
    1504           0 :         if(button == gWidgetData[m_nXScreen].gToolbarButtonWidget)
    1505             :         {
    1506           0 :             gtk_paint_box( gWidgetData[m_nXScreen].gToolbarWidget->style, gdkDrawable, GTK_STATE_NORMAL, GTK_SHADOW_NONE,
    1507           0 :                                 &clipRect, gWidgetData[m_nXScreen].gToolbarWidget, "toolbar", x, y, w, h );
    1508             :         }
    1509             :         else
    1510             :         {
    1511             :             gtk_paint_box( m_pWindow->style, gdkDrawable, GTK_STATE_NORMAL, GTK_SHADOW_NONE,
    1512           0 :                                 &clipRect, m_pWindow, "base", x, y, w, h );
    1513             :         }
    1514             : 
    1515           0 :         if ( GTK_IS_BUTTON(button) )
    1516             :         {
    1517           0 :             if ( (nState & CTRL_STATE_DEFAULT) )
    1518             :                 gtk_paint_box( button->style, gdkDrawable, GTK_STATE_NORMAL, GTK_SHADOW_IN,
    1519           0 :                                &clipRect, button, "buttondefault", x, y, w, h );
    1520             : 
    1521             :             /* don't draw "button", because it can be a tool_button, and
    1522             :              * it causes some weird things, so, the default button is
    1523             :              * just fine */
    1524             :             gtk_paint_box( button->style, gdkDrawable, stateType, shadowType,
    1525           0 :                            &clipRect, button, "button", xi, yi, wi, hi );
    1526             :         }
    1527             :     }
    1528             : 
    1529           0 :     return true;
    1530             : }
    1531             : 
    1532           0 : bool GtkSalGraphics::NWPaintGTKButton(
    1533             :             GdkDrawable* gdkDrawable,
    1534             :             ControlType type, ControlPart part,
    1535             :             const Rectangle& rControlRectangle,
    1536             :             const clipList& rClipList,
    1537             :             ControlState nState, const ImplControlValue& value,
    1538             :             const OUString& string)
    1539             : {
    1540             :         return NWPaintGTKButtonReal(
    1541           0 :             gWidgetData[m_nXScreen].gBtnWidget,
    1542             :             gdkDrawable,
    1543             :             type, part,
    1544             :             rControlRectangle,
    1545             :             rClipList,
    1546             :             nState, value,
    1547           0 :             string );
    1548             : }
    1549             : 
    1550           0 : static Rectangle NWGetButtonArea( SalX11Screen nScreen,
    1551             :                                   ControlType, ControlPart, Rectangle aAreaRect, ControlState nState,
    1552             :                                   const ImplControlValue&, const OUString& )
    1553             : {
    1554             :     gboolean        interiorFocus;
    1555             :     gint            focusWidth;
    1556             :     gint            focusPad;
    1557             :     GtkBorder        aDefBorder;
    1558             :     GtkBorder *    pBorder;
    1559           0 :     bool            bDrawFocus = true;
    1560           0 :     Rectangle        aRect;
    1561             :     gint            x, y, w, h;
    1562             : 
    1563           0 :     NWEnsureGTKButton( nScreen );
    1564           0 :     gtk_widget_style_get( gWidgetData[nScreen].gBtnWidget,
    1565             :                                 "focus-line-width",    &focusWidth,
    1566             :                                 "focus-padding",     &focusPad,
    1567             :                                  "interior_focus",    &interiorFocus,
    1568             :                                 "default_border",    &pBorder,
    1569           0 :                                 (char *)NULL );
    1570             : 
    1571             :     // Make sure the border values exist, otherwise use some defaults
    1572           0 :     if ( pBorder )
    1573             :     {
    1574           0 :         NW_gtk_border_set_from_border( aDefBorder, pBorder );
    1575           0 :         gtk_border_free( pBorder );
    1576             :     }
    1577           0 :     else NW_gtk_border_set_from_border( aDefBorder, &aDefDefBorder );
    1578             : 
    1579           0 :     x = aAreaRect.Left();
    1580           0 :     y = aAreaRect.Top();
    1581           0 :     w = aAreaRect.GetWidth();
    1582           0 :     h = aAreaRect.GetHeight();
    1583             : 
    1584             :     // If the button is too small, don't ever draw focus or grab more space
    1585           0 :     if ( (w < 16) || (h < 16) )
    1586           0 :         bDrawFocus = false;
    1587             : 
    1588           0 :     if ( (nState & CTRL_STATE_DEFAULT) && bDrawFocus )
    1589             :     {
    1590           0 :         x -= aDefBorder.left;
    1591           0 :         y -= aDefBorder.top;
    1592           0 :         w += aDefBorder.left + aDefBorder.right;
    1593           0 :         h += aDefBorder.top + aDefBorder.bottom;
    1594             :     }
    1595             : 
    1596           0 :     aRect = Rectangle( Point( x, y ), Size( w, h ) );
    1597             : 
    1598           0 :     return( aRect );
    1599             : }
    1600             : 
    1601           0 : static Rectangle NWGetTabItemRect( SalX11Screen nScreen, Rectangle aAreaRect )
    1602             : {
    1603           0 :     NWEnsureGTKNotebook( nScreen );
    1604             : 
    1605             :     gint            x, y, w, h;
    1606             : 
    1607           0 :     x = aAreaRect.Left();
    1608           0 :     y = aAreaRect.Top();
    1609           0 :     w = aAreaRect.GetWidth();
    1610           0 :     h = aAreaRect.GetHeight();
    1611             : 
    1612           0 :     gint xthickness = gWidgetData[nScreen].gNotebookWidget->style->xthickness;
    1613           0 :     gint ythickness = gWidgetData[nScreen].gNotebookWidget->style->ythickness;
    1614             : 
    1615           0 :     x -= xthickness;
    1616           0 :     y -= ythickness;
    1617           0 :     w += xthickness*2;
    1618           0 :     h += ythickness*2;
    1619             : 
    1620           0 :     return Rectangle( Point( x, y ), Size( w, h ) );
    1621             : }
    1622             : 
    1623           0 : bool GtkSalGraphics::NWPaintGTKRadio( GdkDrawable* gdkDrawable,
    1624             :                                       ControlType, ControlPart,
    1625             :                                       const Rectangle& rControlRectangle,
    1626             :                                       const clipList& rClipList,
    1627             :                                       ControlState nState,
    1628             :                                       const ImplControlValue& aValue,
    1629             :                                       const OUString& )
    1630             : {
    1631             :     GtkStateType    stateType;
    1632             :     GtkShadowType    shadowType;
    1633           0 :     bool            isChecked = (aValue.getTristateVal()==BUTTONVALUE_ON);
    1634             :     gint            x, y;
    1635             :     GdkRectangle    clipRect;
    1636             : 
    1637           0 :     NWEnsureGTKButton( m_nXScreen );
    1638           0 :     NWEnsureGTKRadio( m_nXScreen );
    1639           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    1640             : 
    1641             :     gint indicator_size;
    1642           0 :     gtk_widget_style_get( gWidgetData[m_nXScreen].gRadioWidget, "indicator_size", &indicator_size, (char *)NULL);
    1643             : 
    1644           0 :     x = rControlRectangle.Left() + (rControlRectangle.GetWidth()-indicator_size)/2;
    1645           0 :     y = rControlRectangle.Top() + (rControlRectangle.GetHeight()-indicator_size)/2;
    1646             : 
    1647             :     // Set the shadow based on if checked or not so we get a freakin checkmark.
    1648           0 :     shadowType = isChecked ? GTK_SHADOW_IN : GTK_SHADOW_OUT;
    1649           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gRadioWidget, nState, stateType );
    1650           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gRadioWidgetSibling, nState, stateType );
    1651             : 
    1652             :     // GTK enforces radio groups, so that if we don't have 2 buttons in the group,
    1653             :     // the single button will always be active.  So we have to have 2 buttons.
    1654             : 
    1655             :     // #i59666# set the members directly where we should use
    1656             :     // gtk_toggle_button_set_active. reason: there are animated themes
    1657             :     // which are in active state only after a while leading to painting
    1658             :     // intermediate states between active/inactive. Let's hope that
    1659             :     // GtkToggleButtone stays binary compatible.
    1660           0 :     if (!isChecked)
    1661           0 :         GTK_TOGGLE_BUTTON(gWidgetData[m_nXScreen].gRadioWidgetSibling)->active = true;
    1662           0 :     GTK_TOGGLE_BUTTON(gWidgetData[m_nXScreen].gRadioWidget)->active = isChecked;
    1663             : 
    1664           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    1665             :     {
    1666           0 :         clipRect.x = it->Left();
    1667           0 :         clipRect.y = it->Top();
    1668           0 :         clipRect.width = it->GetWidth();
    1669           0 :         clipRect.height = it->GetHeight();
    1670             : 
    1671           0 :         gtk_paint_option( gWidgetData[m_nXScreen].gRadioWidget->style, gdkDrawable, stateType, shadowType,
    1672           0 :                           &clipRect, gWidgetData[m_nXScreen].gRadioWidget, "radiobutton",
    1673           0 :                           x, y, indicator_size, indicator_size );
    1674             :     }
    1675             : 
    1676           0 :     return true;
    1677             : }
    1678             : 
    1679           0 : bool GtkSalGraphics::NWPaintGTKCheck( GdkDrawable* gdkDrawable,
    1680             :                                       ControlType, ControlPart,
    1681             :                                       const Rectangle& rControlRectangle,
    1682             :                                       const clipList& rClipList,
    1683             :                                       ControlState nState,
    1684             :                                       const ImplControlValue& aValue,
    1685             :                                       const OUString& )
    1686             : {
    1687             :     GtkStateType    stateType;
    1688             :     GtkShadowType    shadowType;
    1689           0 :     bool            isChecked = (aValue.getTristateVal() == BUTTONVALUE_ON);
    1690           0 :     bool            isInconsistent = (aValue.getTristateVal() == BUTTONVALUE_MIXED);
    1691             :     GdkRectangle    clipRect;
    1692             :     gint            x,y;
    1693             : 
    1694           0 :     NWEnsureGTKButton( m_nXScreen );
    1695           0 :     NWEnsureGTKCheck( m_nXScreen );
    1696           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    1697             : 
    1698             :     gint indicator_size;
    1699           0 :     gtk_widget_style_get( gWidgetData[m_nXScreen].gCheckWidget, "indicator_size", &indicator_size, (char *)NULL);
    1700             : 
    1701           0 :     x = rControlRectangle.Left() + (rControlRectangle.GetWidth()-indicator_size)/2;
    1702           0 :     y = rControlRectangle.Top() + (rControlRectangle.GetHeight()-indicator_size)/2;
    1703             : 
    1704             :     // Set the shadow based on if checked or not so we get a checkmark.
    1705           0 :     shadowType = isChecked ? GTK_SHADOW_IN : isInconsistent ? GTK_SHADOW_ETCHED_IN : GTK_SHADOW_OUT;
    1706           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gCheckWidget, nState, stateType );
    1707           0 :     GTK_TOGGLE_BUTTON(gWidgetData[m_nXScreen].gCheckWidget)->active = isChecked;
    1708             : 
    1709           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    1710             :     {
    1711           0 :         clipRect.x = it->Left();
    1712           0 :         clipRect.y = it->Top();
    1713           0 :         clipRect.width = it->GetWidth();
    1714           0 :         clipRect.height = it->GetHeight();
    1715             : 
    1716           0 :         gtk_paint_check( gWidgetData[m_nXScreen].gCheckWidget->style, gdkDrawable, stateType, shadowType,
    1717           0 :                          &clipRect, gWidgetData[m_nXScreen].gCheckWidget, "checkbutton",
    1718           0 :                          x, y, indicator_size, indicator_size );
    1719             :     }
    1720             : 
    1721           0 :     return true;
    1722             : }
    1723             : 
    1724           0 : static void NWCalcArrowRect( const Rectangle& rButton, Rectangle& rArrow )
    1725             : {
    1726             :     // Size the arrow appropriately
    1727           0 :     Size aSize( rButton.GetWidth()/2, rButton.GetHeight()/2 );
    1728           0 :     rArrow.SetSize( aSize );
    1729             : 
    1730             :     rArrow.SetPos( Point(
    1731           0 :         rButton.Left() + ( rButton.GetWidth()  - rArrow.GetWidth()  ) / 2,
    1732           0 :         rButton.Top() + ( rButton.GetHeight() - rArrow.GetHeight() ) / 2
    1733           0 :         ) );
    1734           0 : }
    1735             : 
    1736           0 : bool GtkSalGraphics::NWPaintGTKScrollbar( ControlType, ControlPart nPart,
    1737             :                                           const Rectangle& rControlRectangle,
    1738             :                                           const clipList&,
    1739             :                                           ControlState nState,
    1740             :                                           const ImplControlValue& aValue,
    1741             :                                           const OUString& )
    1742             : {
    1743             :     assert(aValue.getType() == CTRL_SCROLLBAR);
    1744           0 :     const ScrollbarValue& rScrollbarVal = static_cast<const ScrollbarValue&>(aValue);
    1745           0 :     GdkPixmap*      pixmap = NULL;
    1746           0 :     Rectangle        pixmapRect, scrollbarRect;
    1747             :     GtkStateType    stateType;
    1748             :     GtkShadowType    shadowType;
    1749             :     GtkScrollbar *    scrollbarWidget;
    1750             :     GtkStyle *    style;
    1751           0 :     GtkAdjustment* scrollbarValues = NULL;
    1752             :     GtkOrientation    scrollbarOrientation;
    1753           0 :     Rectangle        thumbRect = rScrollbarVal.maThumbRect;
    1754           0 :     Rectangle        button11BoundRect = rScrollbarVal.maButton1Rect;   // backward
    1755           0 :     Rectangle        button22BoundRect = rScrollbarVal.maButton2Rect;   // forward
    1756           0 :     Rectangle        button12BoundRect = rScrollbarVal.maButton1Rect;   // secondary forward
    1757           0 :     Rectangle        button21BoundRect = rScrollbarVal.maButton2Rect;   // secondary backward
    1758             :     GtkArrowType    button1Type;                                        // backward
    1759             :     GtkArrowType    button2Type;                                        // forward
    1760           0 :     gchar *        scrollbarTagH = (gchar *) "hscrollbar";
    1761           0 :     gchar *        scrollbarTagV = (gchar *) "vscrollbar";
    1762           0 :     gchar *        scrollbarTag = NULL;
    1763           0 :     Rectangle        arrowRect;
    1764           0 :     gint            slider_width = 0;
    1765           0 :     gint            stepper_size = 0;
    1766           0 :     gint            stepper_spacing = 0;
    1767           0 :     gint            trough_border = 0;
    1768           0 :     gint            min_slider_length = 0;
    1769           0 :     gint            vShim = 0;
    1770           0 :     gint            hShim = 0;
    1771             :     gint            x,y,w,h;
    1772             : 
    1773             :     // make controlvalue rectangles relative to area
    1774           0 :     thumbRect.Move( -rControlRectangle.Left(), -rControlRectangle.Top() );
    1775           0 :     button11BoundRect.Move( -rControlRectangle.Left(), -rControlRectangle.Top() );
    1776           0 :     button22BoundRect.Move( -rControlRectangle.Left(), -rControlRectangle.Top() );
    1777           0 :     button12BoundRect.Move( -rControlRectangle.Left(), -rControlRectangle.Top() );
    1778           0 :     button21BoundRect.Move( -rControlRectangle.Left(), -rControlRectangle.Top() );
    1779             : 
    1780           0 :     NWEnsureGTKButton( m_nXScreen );
    1781           0 :     NWEnsureGTKScrollbars( m_nXScreen );
    1782           0 :     NWEnsureGTKArrow( m_nXScreen );
    1783             : 
    1784             :     // Find the overall bounding rect of the control
    1785           0 :     pixmapRect = rControlRectangle;
    1786           0 :     scrollbarRect = pixmapRect;
    1787             : 
    1788           0 :     if ( (scrollbarRect.GetWidth() <= 1) || (scrollbarRect.GetHeight() <= 1) )
    1789           0 :         return true;
    1790             : 
    1791             :     // Grab some button style attributes
    1792           0 :     gtk_widget_style_get( gWidgetData[m_nXScreen].gScrollHorizWidget,
    1793             :                                       "slider_width", &slider_width,
    1794             :                                       "stepper_size", &stepper_size,
    1795             :                                       "trough_border", &trough_border,
    1796             :                                       "stepper_spacing", &stepper_spacing,
    1797           0 :                                       "min_slider_length", &min_slider_length, (char *)NULL );
    1798             :     gboolean has_forward;
    1799             :     gboolean has_forward2;
    1800             :     gboolean has_backward;
    1801             :     gboolean has_backward2;
    1802             : 
    1803           0 :     gtk_widget_style_get( gWidgetData[m_nXScreen].gScrollHorizWidget, "has-forward-stepper", &has_forward,
    1804             :                                       "has-secondary-forward-stepper", &has_forward2,
    1805             :                                       "has-backward-stepper", &has_backward,
    1806           0 :                                          "has-secondary-backward-stepper", &has_backward2, (char *)NULL );
    1807           0 :     gint magic = trough_border ? 1 : 0;
    1808           0 :     gint nFirst = 0;
    1809             : 
    1810           0 :     if ( has_backward )  nFirst  += 1;
    1811           0 :     if ( has_forward2 )  nFirst  += 1;
    1812             : 
    1813           0 :     if ( nPart == PART_DRAW_BACKGROUND_HORZ )
    1814             :     {
    1815           0 :         unsigned int sliderHeight = slider_width + (trough_border * 2);
    1816           0 :         vShim = (pixmapRect.GetHeight() - sliderHeight) / 2;
    1817           0 :         bool bRTLSwap = button11BoundRect.Left() > button22BoundRect.Left();
    1818             : 
    1819           0 :         scrollbarRect.Move( 0, vShim );
    1820           0 :         scrollbarRect.SetSize( Size( scrollbarRect.GetWidth(), sliderHeight ) );
    1821             : 
    1822           0 :         scrollbarWidget = GTK_SCROLLBAR( gWidgetData[m_nXScreen].gScrollHorizWidget );
    1823           0 :         scrollbarOrientation = GTK_ORIENTATION_HORIZONTAL;
    1824           0 :         scrollbarTag = scrollbarTagH;
    1825           0 :         button1Type = bRTLSwap? GTK_ARROW_RIGHT: GTK_ARROW_LEFT;
    1826           0 :         button2Type = bRTLSwap? GTK_ARROW_LEFT: GTK_ARROW_RIGHT;
    1827             : 
    1828           0 :         if ( has_backward )
    1829             :         {
    1830           0 :             button12BoundRect.Move( stepper_size - trough_border,
    1831           0 :                                     (scrollbarRect.GetHeight() - slider_width) / 2 );
    1832             :         }
    1833             : 
    1834           0 :         button11BoundRect.Move( trough_border, (scrollbarRect.GetHeight() - slider_width) / 2 );
    1835           0 :         button11BoundRect.SetSize( Size( stepper_size, slider_width ) );
    1836           0 :         button12BoundRect.SetSize( Size( stepper_size, slider_width ) );
    1837             : 
    1838           0 :         if ( has_backward2 )
    1839             :         {
    1840           0 :             button22BoundRect.Move( stepper_size+(trough_border+1)/2, (scrollbarRect.GetHeight() - slider_width) / 2 );
    1841           0 :             button21BoundRect.Move( (trough_border+1)/2, (scrollbarRect.GetHeight() - slider_width) / 2 );
    1842             :         }
    1843             :         else
    1844             :         {
    1845           0 :             button22BoundRect.Move( (trough_border+1)/2, (scrollbarRect.GetHeight() - slider_width) / 2 );
    1846             :         }
    1847             : 
    1848           0 :         button21BoundRect.SetSize( Size( stepper_size, slider_width ) );
    1849           0 :         button22BoundRect.SetSize( Size( stepper_size, slider_width ) );
    1850             : 
    1851           0 :         thumbRect.Bottom() = thumbRect.Top() + slider_width - 1;
    1852             :         // Make sure the thumb is at least the default width (so we don't get tiny thumbs),
    1853             :         // but if the VCL gives us a size smaller than the theme's default thumb size,
    1854             :         // honor the VCL size
    1855           0 :         thumbRect.Right() += magic;
    1856             :         // Center vertically in the track
    1857           0 :         thumbRect.Move( 0, (scrollbarRect.GetHeight() - slider_width) / 2 );
    1858             :     }
    1859             :     else
    1860             :     {
    1861           0 :         unsigned int sliderWidth = slider_width + (trough_border * 2);
    1862           0 :         hShim = (pixmapRect.GetWidth() - sliderWidth) / 2;
    1863             : 
    1864           0 :         scrollbarRect.Move( hShim, 0 );
    1865           0 :         scrollbarRect.SetSize( Size( sliderWidth, scrollbarRect.GetHeight() ) );
    1866             : 
    1867           0 :         scrollbarWidget = GTK_SCROLLBAR( gWidgetData[m_nXScreen].gScrollVertWidget );
    1868           0 :         scrollbarOrientation = GTK_ORIENTATION_VERTICAL;
    1869           0 :         scrollbarTag = scrollbarTagV;
    1870           0 :         button1Type = GTK_ARROW_UP;
    1871           0 :         button2Type = GTK_ARROW_DOWN;
    1872             : 
    1873           0 :         if ( has_backward )
    1874             :         {
    1875           0 :             button12BoundRect.Move( (scrollbarRect.GetWidth() - slider_width) / 2,
    1876           0 :                                     stepper_size + trough_border );
    1877             :         }
    1878           0 :         button11BoundRect.Move( (scrollbarRect.GetWidth() - slider_width) / 2, trough_border );
    1879           0 :         button11BoundRect.SetSize( Size( slider_width, stepper_size ) );
    1880           0 :         button12BoundRect.SetSize( Size( slider_width, stepper_size ) );
    1881             : 
    1882           0 :         if ( has_backward2 )
    1883             :         {
    1884           0 :             button22BoundRect.Move( (scrollbarRect.GetWidth() - slider_width) / 2, stepper_size+(trough_border+1)/2 );
    1885           0 :             button21BoundRect.Move( (scrollbarRect.GetWidth() - slider_width) / 2, (trough_border+1)/2 );
    1886             :         }
    1887             :         else
    1888             :         {
    1889           0 :             button22BoundRect.Move( (scrollbarRect.GetWidth() - slider_width) / 2, (trough_border+1)/2 );
    1890             :         }
    1891             : 
    1892           0 :         button21BoundRect.SetSize( Size( slider_width, stepper_size ) );
    1893           0 :         button22BoundRect.SetSize( Size( slider_width, stepper_size ) );
    1894             : 
    1895           0 :         thumbRect.Right() = thumbRect.Left() + slider_width - 1;
    1896             : 
    1897           0 :         thumbRect.Bottom() += magic;
    1898             :         // Center horizontally in the track
    1899           0 :         thumbRect.Move( (scrollbarRect.GetWidth() - slider_width) / 2, 0 );
    1900             :     }
    1901             : 
    1902           0 :     bool has_slider = ( thumbRect.GetWidth() > 0 && thumbRect.GetHeight() > 0 );
    1903             : 
    1904           0 :     scrollbarValues = gtk_range_get_adjustment( GTK_RANGE(scrollbarWidget) );
    1905           0 :     if ( scrollbarValues == NULL )
    1906           0 :         scrollbarValues = GTK_ADJUSTMENT( gtk_adjustment_new(0, 0, 0, 0, 0, 0) );
    1907           0 :     if ( nPart == PART_DRAW_BACKGROUND_HORZ )
    1908             :     {
    1909           0 :         scrollbarValues->lower = rScrollbarVal.mnMin;
    1910           0 :         scrollbarValues->upper = rScrollbarVal.mnMax;
    1911           0 :         scrollbarValues->value = rScrollbarVal.mnCur;
    1912           0 :         scrollbarValues->page_size = scrollbarRect.GetWidth() / 2;
    1913             :     }
    1914             :     else
    1915             :     {
    1916           0 :         scrollbarValues->lower = rScrollbarVal.mnMin;
    1917           0 :         scrollbarValues->upper = rScrollbarVal.mnMax;
    1918           0 :         scrollbarValues->value = rScrollbarVal.mnCur;
    1919           0 :         scrollbarValues->page_size = scrollbarRect.GetHeight() / 2;
    1920             :     }
    1921           0 :     gtk_adjustment_changed( scrollbarValues );
    1922             : 
    1923             :     // as multiple paints are required for the scrollbar
    1924             :     // painting them directly to the window flickers
    1925           0 :     pixmap = NWGetPixmapFromScreen( pixmapRect );
    1926           0 :     if( ! pixmap )
    1927           0 :         return false;
    1928           0 :     x = y = 0;
    1929             : 
    1930           0 :     w = pixmapRect.GetWidth();
    1931           0 :     h = pixmapRect.GetHeight();
    1932             : 
    1933           0 :     GdkDrawable* const &gdkDrawable = GDK_DRAWABLE( pixmap );
    1934           0 :     GdkRectangle* gdkRect = NULL;
    1935             : 
    1936           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    1937           0 :     NWSetWidgetState( GTK_WIDGET(scrollbarWidget), nState, stateType );
    1938           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gBtnWidget, nState, stateType );
    1939           0 :     style = GTK_WIDGET( scrollbarWidget )->style;
    1940             : 
    1941             :     gtk_style_apply_default_background( m_pWindow->style, gdkDrawable, TRUE,
    1942             :                                         GTK_STATE_NORMAL, gdkRect,
    1943           0 :                                         x, y, w, h );
    1944             : 
    1945             :     // ----------------- TROUGH
    1946             :     // Pass coordinates of draw rect: window(0,0) -> widget(bottom-right) (coords relative to widget)
    1947             :     gtk_paint_flat_box(m_pWindow->style, gdkDrawable,
    1948             :                         GTK_STATE_NORMAL, GTK_SHADOW_NONE, gdkRect,
    1949           0 :                         m_pWindow, "base", x-pixmapRect.Left(),y-pixmapRect.Top(),x+pixmapRect.Right(),y+pixmapRect.Bottom());
    1950             : 
    1951             :     gtk_paint_box( style, gdkDrawable, GTK_STATE_ACTIVE, GTK_SHADOW_IN,
    1952           0 :                    gdkRect, GTK_WIDGET(scrollbarWidget), "trough",
    1953             :                    x, y,
    1954           0 :                    scrollbarRect.GetWidth(), scrollbarRect.GetHeight() );
    1955             : 
    1956           0 :     if ( nState & CTRL_STATE_FOCUSED )
    1957             :     {
    1958             :         gtk_paint_focus( style, gdkDrawable, GTK_STATE_ACTIVE,
    1959           0 :                          gdkRect, GTK_WIDGET(scrollbarWidget), "trough",
    1960             :                          x, y,
    1961           0 :                          scrollbarRect.GetWidth(), scrollbarRect.GetHeight() );
    1962             :     }
    1963             : 
    1964             :     // ----------------- THUMB
    1965           0 :     if ( has_slider )
    1966             :     {
    1967           0 :         NWConvertVCLStateToGTKState( rScrollbarVal.mnThumbState, &stateType, &shadowType );
    1968             :         gtk_paint_slider( style, gdkDrawable, stateType, GTK_SHADOW_OUT,
    1969           0 :                         gdkRect, GTK_WIDGET(scrollbarWidget), "slider",
    1970           0 :                         x+hShim+thumbRect.Left(), y+vShim+thumbRect.Top(),
    1971           0 :                         thumbRect.GetWidth(), thumbRect.GetHeight(), scrollbarOrientation );
    1972             :     }
    1973             : 
    1974             :     // Some engines require allocation, e.g. Clearlooks uses it to identify
    1975             :     // positions of the buttons, whereupon the first and the last button will
    1976             :     // have rounded corners.
    1977           0 :     GTK_WIDGET(scrollbarWidget)->allocation.x = x;
    1978           0 :     GTK_WIDGET(scrollbarWidget)->allocation.y = y;
    1979           0 :     GTK_WIDGET(scrollbarWidget)->allocation.width = w;
    1980           0 :     GTK_WIDGET(scrollbarWidget)->allocation.height = h;
    1981             : 
    1982             :     bool backwardButtonInsensitive =
    1983           0 :         rScrollbarVal.mnCur == rScrollbarVal.mnMin;
    1984           0 :     bool forwardButtonInsensitive = rScrollbarVal.mnMax == 0 ||
    1985           0 :         rScrollbarVal.mnCur + rScrollbarVal.mnVisibleSize >= rScrollbarVal.mnMax;
    1986             : 
    1987             :     // ----------------- BUTTON 1
    1988           0 :     if ( has_backward )
    1989             :     {
    1990           0 :         NWConvertVCLStateToGTKState( rScrollbarVal.mnButton1State, &stateType, &shadowType );
    1991           0 :         if ( backwardButtonInsensitive )
    1992           0 :             stateType = GTK_STATE_INSENSITIVE;
    1993             :         gtk_paint_box( style, gdkDrawable, stateType, shadowType,
    1994           0 :                        gdkRect, GTK_WIDGET(scrollbarWidget), scrollbarTag,
    1995           0 :                        x+hShim+button11BoundRect.Left(), y+vShim+button11BoundRect.Top(),
    1996           0 :                        button11BoundRect.GetWidth(), button11BoundRect.GetHeight() );
    1997             :         // ----------------- ARROW 1
    1998           0 :         NWCalcArrowRect( button11BoundRect, arrowRect );
    1999             :         gtk_paint_arrow( style, gdkDrawable, stateType, shadowType,
    2000           0 :                          gdkRect, GTK_WIDGET(scrollbarWidget), scrollbarTag, button1Type, true,
    2001           0 :                          x+hShim+arrowRect.Left(), y+vShim+arrowRect.Top(),
    2002           0 :                          arrowRect.GetWidth(), arrowRect.GetHeight() );
    2003             :     }
    2004           0 :     if ( has_forward2 )
    2005             :     {
    2006           0 :         NWConvertVCLStateToGTKState( rScrollbarVal.mnButton2State, &stateType, &shadowType );
    2007           0 :         if ( forwardButtonInsensitive )
    2008           0 :             stateType = GTK_STATE_INSENSITIVE;
    2009             :         gtk_paint_box( style, gdkDrawable, stateType, shadowType,
    2010           0 :                        gdkRect, GTK_WIDGET(scrollbarWidget), scrollbarTag,
    2011           0 :                        x+hShim+button12BoundRect.Left(), y+vShim+button12BoundRect.Top(),
    2012           0 :                        button12BoundRect.GetWidth(), button12BoundRect.GetHeight() );
    2013             :         // ----------------- ARROW 1
    2014           0 :         NWCalcArrowRect( button12BoundRect, arrowRect );
    2015             :         gtk_paint_arrow( style, gdkDrawable, stateType, shadowType,
    2016           0 :                          gdkRect, GTK_WIDGET(scrollbarWidget), scrollbarTag, button2Type, true,
    2017           0 :                          x+hShim+arrowRect.Left(), y+vShim+arrowRect.Top(),
    2018           0 :                          arrowRect.GetWidth(), arrowRect.GetHeight() );
    2019             :     }
    2020             :     // ----------------- BUTTON 2
    2021           0 :     if ( has_backward2 )
    2022             :     {
    2023           0 :         NWConvertVCLStateToGTKState( rScrollbarVal.mnButton1State, &stateType, &shadowType );
    2024           0 :         if ( backwardButtonInsensitive )
    2025           0 :             stateType = GTK_STATE_INSENSITIVE;
    2026             :         gtk_paint_box( style, gdkDrawable, stateType, shadowType, gdkRect,
    2027           0 :                        GTK_WIDGET(scrollbarWidget), scrollbarTag,
    2028           0 :                        x+hShim+button21BoundRect.Left(), y+vShim+button21BoundRect.Top(),
    2029           0 :                        button21BoundRect.GetWidth(), button21BoundRect.GetHeight() );
    2030             :         // ----------------- ARROW 2
    2031           0 :         NWCalcArrowRect( button21BoundRect, arrowRect );
    2032             :         gtk_paint_arrow( style, gdkDrawable, stateType, shadowType,
    2033           0 :                          gdkRect, GTK_WIDGET(scrollbarWidget), scrollbarTag, button1Type, true,
    2034           0 :                          x+hShim+arrowRect.Left(), y+vShim+arrowRect.Top(),
    2035           0 :                          arrowRect.GetWidth(), arrowRect.GetHeight() );
    2036             :     }
    2037           0 :     if ( has_forward )
    2038             :     {
    2039           0 :         NWConvertVCLStateToGTKState( rScrollbarVal.mnButton2State, &stateType, &shadowType );
    2040           0 :         if ( forwardButtonInsensitive )
    2041           0 :             stateType = GTK_STATE_INSENSITIVE;
    2042             :         gtk_paint_box( style, gdkDrawable, stateType, shadowType, gdkRect,
    2043           0 :                        GTK_WIDGET(scrollbarWidget), scrollbarTag,
    2044           0 :                        x+hShim+button22BoundRect.Left(), y+vShim+button22BoundRect.Top(),
    2045           0 :                        button22BoundRect.GetWidth(), button22BoundRect.GetHeight() );
    2046             :         // ----------------- ARROW 2
    2047           0 :         NWCalcArrowRect( button22BoundRect, arrowRect );
    2048             :         gtk_paint_arrow( style, gdkDrawable, stateType, shadowType,
    2049           0 :                          gdkRect, GTK_WIDGET(scrollbarWidget), scrollbarTag, button2Type, true,
    2050           0 :                          x+hShim+arrowRect.Left(), y+vShim+arrowRect.Top(),
    2051           0 :                          arrowRect.GetWidth(), arrowRect.GetHeight() );
    2052             :     }
    2053             : 
    2054           0 :     if( !NWRenderPixmapToScreen(pixmap, pixmapRect) )
    2055             :     {
    2056           0 :         g_object_unref( pixmap );
    2057           0 :         return false;
    2058             :     }
    2059           0 :     g_object_unref( pixmap );
    2060             : 
    2061           0 :     return true;
    2062             : }
    2063             : 
    2064           0 : static Rectangle NWGetScrollButtonRect(    SalX11Screen nScreen, ControlPart nPart, Rectangle aAreaRect )
    2065             : {
    2066             :     gint slider_width;
    2067             :     gint stepper_size;
    2068             :     gint stepper_spacing;
    2069             :     gint trough_border;
    2070             : 
    2071           0 :     NWEnsureGTKScrollbars( nScreen );
    2072             : 
    2073             :     // Grab some button style attributes
    2074           0 :     gtk_widget_style_get( gWidgetData[nScreen].gScrollHorizWidget,
    2075             :                                       "slider-width", &slider_width,
    2076             :                                       "stepper-size", &stepper_size,
    2077             :                                       "trough-border", &trough_border,
    2078           0 :                                          "stepper-spacing", &stepper_spacing, (char *)NULL );
    2079             : 
    2080             :     gboolean has_forward;
    2081             :     gboolean has_forward2;
    2082             :     gboolean has_backward;
    2083             :     gboolean has_backward2;
    2084             : 
    2085           0 :     gtk_widget_style_get( gWidgetData[nScreen].gScrollHorizWidget,
    2086             :                                       "has-forward-stepper", &has_forward,
    2087             :                                       "has-secondary-forward-stepper", &has_forward2,
    2088             :                                       "has-backward-stepper", &has_backward,
    2089           0 :                                          "has-secondary-backward-stepper", &has_backward2, (char *)NULL );
    2090             :     gint       buttonWidth;
    2091             :     gint       buttonHeight;
    2092           0 :     Rectangle  buttonRect;
    2093             : 
    2094           0 :     gint nFirst = 0;
    2095           0 :     gint nSecond = 0;
    2096             : 
    2097           0 :     if ( has_forward )   nSecond += 1;
    2098           0 :     if ( has_forward2 )  nFirst  += 1;
    2099           0 :     if ( has_backward )  nFirst  += 1;
    2100           0 :     if ( has_backward2 ) nSecond += 1;
    2101             : 
    2102           0 :     if ( ( nPart == PART_BUTTON_UP ) || ( nPart == PART_BUTTON_DOWN ) )
    2103             :     {
    2104           0 :         buttonWidth = slider_width + 2 * trough_border;
    2105           0 :         buttonHeight = stepper_size + trough_border + stepper_spacing;
    2106             :     }
    2107             :     else
    2108             :     {
    2109           0 :         buttonWidth = stepper_size + trough_border + stepper_spacing;
    2110           0 :         buttonHeight = slider_width + 2 * trough_border;
    2111             :     }
    2112             : 
    2113           0 :     if ( nPart == PART_BUTTON_UP )
    2114             :     {
    2115           0 :         buttonHeight *= nFirst;
    2116           0 :         buttonHeight -= 1;
    2117           0 :         buttonRect.setX( aAreaRect.Left() );
    2118           0 :         buttonRect.setY( aAreaRect.Top() );
    2119             :     }
    2120           0 :     else if ( nPart == PART_BUTTON_LEFT )
    2121             :     {
    2122           0 :         buttonWidth *= nFirst;
    2123           0 :         buttonWidth -= 1;
    2124           0 :         buttonRect.setX( aAreaRect.Left() );
    2125           0 :         buttonRect.setY( aAreaRect.Top() );
    2126             :     }
    2127           0 :     else if ( nPart == PART_BUTTON_DOWN )
    2128             :     {
    2129           0 :         buttonHeight *= nSecond;
    2130           0 :         buttonRect.setX( aAreaRect.Left() );
    2131           0 :         buttonRect.setY( aAreaRect.Top() + aAreaRect.GetHeight() - buttonHeight );
    2132             :     }
    2133           0 :     else if ( nPart == PART_BUTTON_RIGHT )
    2134             :     {
    2135           0 :         buttonWidth *= nSecond;
    2136           0 :         buttonRect.setX( aAreaRect.Left() + aAreaRect.GetWidth() - buttonWidth );
    2137           0 :         buttonRect.setY( aAreaRect.Top() );
    2138             :     }
    2139             : 
    2140           0 :     buttonRect.SetSize( Size( buttonWidth, buttonHeight ) );
    2141             : 
    2142           0 :     return( buttonRect );
    2143             : }
    2144             : 
    2145           0 : bool GtkSalGraphics::NWPaintGTKEditBox( GdkDrawable* gdkDrawable,
    2146             :                                         ControlType nType, ControlPart nPart,
    2147             :                                         const Rectangle& rControlRectangle,
    2148             :                                         const clipList& rClipList,
    2149             :                                         ControlState nState,
    2150             :                                         const ImplControlValue& aValue,
    2151             :                                         const OUString& rCaption )
    2152             : {
    2153           0 :     Rectangle        pixmapRect;
    2154             :     GdkRectangle    clipRect;
    2155             : 
    2156             :     // Find the overall bounding rect of the buttons's drawing area,
    2157             :     // plus its actual draw rect excluding adornment
    2158             :     pixmapRect = NWGetEditBoxPixmapRect( m_nXScreen, nType, nPart, rControlRectangle,
    2159           0 :                                          nState, aValue, rCaption );
    2160           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    2161             :     {
    2162           0 :         clipRect.x = it->Left();
    2163           0 :         clipRect.y = it->Top();
    2164           0 :         clipRect.width = it->GetWidth();
    2165           0 :         clipRect.height = it->GetHeight();
    2166             : 
    2167           0 :         NWPaintOneEditBox( m_nXScreen, gdkDrawable, &clipRect, nType, nPart, pixmapRect, nState, aValue, rCaption );
    2168             :     }
    2169             : 
    2170           0 :     return true;
    2171             : }
    2172             : 
    2173             : /* Take interior/exterior focus into account and return
    2174             :  * the bounding rectangle of the edit box including
    2175             :  * any focus requirements.
    2176             :  */
    2177           0 : static Rectangle NWGetEditBoxPixmapRect(SalX11Screen nScreen,
    2178             :                                         ControlType,
    2179             :                                         ControlPart,
    2180             :                                         Rectangle aAreaRect,
    2181             :                                         ControlState,
    2182             :                                         const ImplControlValue&,
    2183             :                                         const OUString& )
    2184             : {
    2185           0 :     Rectangle        pixmapRect = aAreaRect;
    2186             :     gboolean        interiorFocus;
    2187             :     gint            focusWidth;
    2188             : 
    2189           0 :     NWEnsureGTKEditBox( nScreen );
    2190             : 
    2191             :     // Grab some entry style attributes
    2192           0 :     gtk_widget_style_get( gWidgetData[nScreen].gEditBoxWidget,
    2193             :                                     "focus-line-width",    &focusWidth,
    2194           0 :                                      "interior-focus",    &interiorFocus, (char *)NULL );
    2195             : 
    2196           0 :     if ( !interiorFocus )
    2197             :     {
    2198           0 :         pixmapRect.Move( -(focusWidth), -(focusWidth) );
    2199           0 :         pixmapRect.SetSize( Size( pixmapRect.GetWidth() + (2*(focusWidth)),
    2200           0 :                                   pixmapRect.GetHeight() + (2*(focusWidth)) ) );
    2201             :     }
    2202             : 
    2203           0 :     return( pixmapRect );
    2204             : }
    2205             : 
    2206             : /* Paint a GTK Entry widget into the specified GdkPixmap.
    2207             :  * All coordinates should be local to the Pixmap, NOT
    2208             :  * screen/window coordinates.
    2209             :  */
    2210           0 : static void NWPaintOneEditBox(    SalX11Screen nScreen,
    2211             :                                 GdkDrawable * gdkDrawable,
    2212             :                                 GdkRectangle *    gdkRect,
    2213             :                                 ControlType            nType,
    2214             :                                 ControlPart,
    2215             :                                 Rectangle                aEditBoxRect,
    2216             :                                 ControlState            nState,
    2217             :                                 const ImplControlValue&,
    2218             :                                 const OUString& )
    2219             : {
    2220             :     GtkStateType    stateType;
    2221             :     GtkShadowType    shadowType;
    2222             :     GtkWidget      *widget;
    2223             : 
    2224           0 :     NWEnsureGTKButton( nScreen );
    2225           0 :     NWEnsureGTKEditBox( nScreen );
    2226           0 :     NWEnsureGTKSpinButton( nScreen );
    2227           0 :     NWEnsureGTKCombo( nScreen );
    2228           0 :     NWEnsureGTKScrolledWindow( nScreen );
    2229           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    2230             : 
    2231           0 :     switch ( nType )
    2232             :     {
    2233             :         case CTRL_SPINBOX:
    2234           0 :             widget = gWidgetData[nScreen].gSpinButtonWidget;
    2235           0 :             break;
    2236             : 
    2237             :         case CTRL_MULTILINE_EDITBOX:
    2238           0 :             widget = gWidgetData[nScreen].gScrolledWindowWidget;
    2239           0 :             break;
    2240             :         case CTRL_COMBOBOX:
    2241           0 :             widget = GTK_COMBO(gWidgetData[nScreen].gComboWidget)->entry;
    2242           0 :             break;
    2243             : 
    2244             :         default:
    2245           0 :             widget = gWidgetData[nScreen].gEditBoxWidget;
    2246           0 :             break;
    2247             :     }
    2248             : 
    2249           0 :     if ( stateType == GTK_STATE_PRELIGHT )
    2250           0 :         stateType = GTK_STATE_NORMAL;
    2251             : 
    2252           0 :     NWSetWidgetState( widget, nState, stateType );
    2253             : 
    2254           0 :     gint xborder = widget->style->xthickness;
    2255           0 :     gint yborder = widget->style->ythickness;
    2256             :     gint bInteriorFocus, nFocusLineWidth;
    2257             :     gtk_widget_style_get( widget,
    2258             :         "interior-focus",   &bInteriorFocus,
    2259             :         "focus-line-width", &nFocusLineWidth,
    2260           0 :         (char *)NULL);
    2261           0 :     if ( !bInteriorFocus )
    2262             :     {
    2263           0 :         xborder += nFocusLineWidth;
    2264           0 :         yborder += nFocusLineWidth;
    2265             :     }
    2266             : 
    2267             :     gtk_paint_flat_box( widget->style, gdkDrawable, stateType, GTK_SHADOW_NONE,
    2268             :                         gdkRect, widget, "entry_bg",
    2269           0 :                         aEditBoxRect.Left() + xborder, aEditBoxRect.Top() + yborder,
    2270           0 :                         aEditBoxRect.GetWidth() - 2*xborder, aEditBoxRect.GetHeight() - 2*yborder );
    2271             :     gtk_paint_shadow( widget->style, gdkDrawable, GTK_STATE_NORMAL, GTK_SHADOW_IN,
    2272             :                       gdkRect, widget, "entry",
    2273           0 :                       aEditBoxRect.Left(), aEditBoxRect.Top(),
    2274           0 :                       aEditBoxRect.GetWidth(), aEditBoxRect.GetHeight() );
    2275             : 
    2276           0 : }
    2277             : 
    2278           0 : bool GtkSalGraphics::NWPaintGTKSpinBox( ControlType nType, ControlPart nPart,
    2279             :                                         const Rectangle& rControlRectangle,
    2280             :                                         const clipList&,
    2281             :                                         ControlState nState,
    2282             :                                         const ImplControlValue& aValue,
    2283             :                                         const OUString& rCaption )
    2284             : {
    2285             :     GdkPixmap    *        pixmap;
    2286           0 :     Rectangle            pixmapRect;
    2287             :     GtkStateType        stateType;
    2288             :     GtkShadowType        shadowType;
    2289           0 :     const SpinbuttonValue *    pSpinVal = (aValue.getType() == CTRL_SPINBUTTONS) ? static_cast<const SpinbuttonValue *>(&aValue) : NULL;
    2290           0 :     Rectangle            upBtnRect;
    2291           0 :     ControlPart        upBtnPart = PART_BUTTON_UP;
    2292           0 :     ControlState        upBtnState = CTRL_STATE_ENABLED;
    2293           0 :     Rectangle            downBtnRect;
    2294           0 :     ControlPart        downBtnPart = PART_BUTTON_DOWN;
    2295           0 :     ControlState        downBtnState = CTRL_STATE_ENABLED;
    2296             : 
    2297           0 :     NWEnsureGTKButton( m_nXScreen );
    2298           0 :     NWEnsureGTKSpinButton( m_nXScreen );
    2299           0 :     NWEnsureGTKArrow( m_nXScreen );
    2300             : 
    2301           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    2302             : 
    2303           0 :     if ( pSpinVal )
    2304             :     {
    2305           0 :         upBtnPart = pSpinVal->mnUpperPart;
    2306           0 :         upBtnState = pSpinVal->mnUpperState;
    2307             : 
    2308           0 :         downBtnPart = pSpinVal->mnLowerPart;
    2309           0 :         downBtnState = pSpinVal->mnLowerState;
    2310             :     }
    2311             : 
    2312             :     // CTRL_SPINBUTTONS pass their area in pSpinVal, not in rControlRectangle
    2313           0 :     if ( nType == CTRL_SPINBUTTONS )
    2314             :     {
    2315           0 :         if ( !pSpinVal )
    2316             :         {
    2317           0 :             std::fprintf( stderr, "Tried to draw CTRL_SPINBUTTONS, but the SpinButtons data structure didn't exist!\n" );
    2318           0 :             return( false );
    2319             :         }
    2320           0 :         pixmapRect = pSpinVal->maUpperRect;
    2321           0 :         pixmapRect.Union( pSpinVal->maLowerRect );
    2322             :     }
    2323             :     else
    2324           0 :         pixmapRect = rControlRectangle;
    2325             : 
    2326           0 :     pixmap = NWGetPixmapFromScreen( pixmapRect );
    2327           0 :     if ( !pixmap )
    2328           0 :         return false;
    2329             : 
    2330             :     // First render background
    2331             :     gtk_paint_flat_box(m_pWindow->style,pixmap,GTK_STATE_NORMAL,GTK_SHADOW_NONE,NULL,m_pWindow,"base",
    2332           0 :             -pixmapRect.Left(),
    2333           0 :             -pixmapRect.Top(),
    2334           0 :             pixmapRect.Right(),
    2335           0 :             pixmapRect.Bottom() );
    2336             : 
    2337           0 :     upBtnRect = NWGetSpinButtonRect( m_nXScreen, nType, upBtnPart, pixmapRect, upBtnState, aValue, rCaption );
    2338           0 :     downBtnRect = NWGetSpinButtonRect( m_nXScreen, nType, downBtnPart, pixmapRect, downBtnState, aValue, rCaption );
    2339             : 
    2340           0 :     if ( (nType==CTRL_SPINBOX) && (nPart!=PART_ALL_BUTTONS) )
    2341             :     {
    2342             :         // Draw an edit field for SpinBoxes and ComboBoxes
    2343           0 :         Rectangle aEditBoxRect( pixmapRect );
    2344           0 :         aEditBoxRect.SetSize( Size( pixmapRect.GetWidth() - upBtnRect.GetWidth(), aEditBoxRect.GetHeight() ) );
    2345           0 :         if( Application::GetSettings().GetLayoutRTL() )
    2346           0 :             aEditBoxRect.setX( upBtnRect.GetWidth() );
    2347             :         else
    2348           0 :             aEditBoxRect.setX( 0 );
    2349           0 :         aEditBoxRect.setY( 0 );
    2350             : 
    2351           0 :         NWPaintOneEditBox( m_nXScreen, pixmap, NULL, nType, nPart, aEditBoxRect, nState, aValue, rCaption );
    2352             :     }
    2353             : 
    2354           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gSpinButtonWidget, nState, stateType );
    2355           0 :     gtk_widget_style_get( gWidgetData[m_nXScreen].gSpinButtonWidget, "shadow_type", &shadowType, (char *)NULL );
    2356             : 
    2357           0 :     if ( shadowType != GTK_SHADOW_NONE )
    2358             :     {
    2359           0 :         Rectangle        shadowRect( upBtnRect );
    2360             : 
    2361           0 :         shadowRect.Union( downBtnRect );
    2362           0 :         gtk_paint_box( gWidgetData[m_nXScreen].gSpinButtonWidget->style, pixmap, GTK_STATE_NORMAL, shadowType, NULL,
    2363           0 :             gWidgetData[m_nXScreen].gSpinButtonWidget, "spinbutton",
    2364           0 :             (shadowRect.Left() - pixmapRect.Left()), (shadowRect.Top() - pixmapRect.Top()),
    2365           0 :             shadowRect.GetWidth(), shadowRect.GetHeight() );
    2366             :     }
    2367             : 
    2368           0 :     NWPaintOneSpinButton( m_nXScreen, pixmap, nType, upBtnPart, pixmapRect, upBtnState, aValue, rCaption );
    2369           0 :     NWPaintOneSpinButton( m_nXScreen, pixmap, nType, downBtnPart, pixmapRect, downBtnState, aValue, rCaption );
    2370             : 
    2371           0 :     if( !NWRenderPixmapToScreen(pixmap, pixmapRect) )
    2372             :     {
    2373           0 :         g_object_unref( pixmap );
    2374           0 :         return false;
    2375             :     }
    2376             : 
    2377           0 :     g_object_unref( pixmap );
    2378           0 :     return true;
    2379             : }
    2380             : 
    2381           0 : static Rectangle NWGetSpinButtonRect( SalX11Screen nScreen,
    2382             :                                       ControlType,
    2383             :                                       ControlPart            nPart,
    2384             :                                       Rectangle             aAreaRect,
    2385             :                                       ControlState,
    2386             :                                       const ImplControlValue&,
    2387             :                                       const OUString& )
    2388             : {
    2389             :     gint            buttonSize;
    2390           0 :     Rectangle        buttonRect;
    2391             : 
    2392           0 :     NWEnsureGTKSpinButton( nScreen );
    2393             : 
    2394           0 :     buttonSize = MAX( PANGO_PIXELS( pango_font_description_get_size(GTK_WIDGET(gWidgetData[nScreen].gSpinButtonWidget)->style->font_desc) ),
    2395           0 :                    MIN_SPIN_ARROW_WIDTH );
    2396           0 :     buttonSize -= buttonSize % 2 - 1; /* force odd */
    2397           0 :     buttonRect.SetSize( Size( buttonSize + 2 * gWidgetData[nScreen].gSpinButtonWidget->style->xthickness,
    2398           0 :                               buttonRect.GetHeight() ) );
    2399           0 :     if( Application::GetSettings().GetLayoutRTL() )
    2400           0 :         buttonRect.setX( aAreaRect.Left() );
    2401             :     else
    2402           0 :         buttonRect.setX( aAreaRect.Left() + (aAreaRect.GetWidth() - buttonRect.GetWidth()) );
    2403           0 :     if ( nPart == PART_BUTTON_UP )
    2404             :     {
    2405           0 :         buttonRect.setY( aAreaRect.Top() );
    2406           0 :         buttonRect.Bottom() = buttonRect.Top() + (aAreaRect.GetHeight() / 2);
    2407             :     }
    2408           0 :     else if( nPart == PART_BUTTON_DOWN )
    2409             :     {
    2410           0 :         buttonRect.setY( aAreaRect.Top() + (aAreaRect.GetHeight() / 2) );
    2411           0 :         buttonRect.Bottom() = aAreaRect.Bottom(); // cover area completely
    2412             :     }
    2413             :     else
    2414             :     {
    2415           0 :         if( Application::GetSettings().GetLayoutRTL() ) {
    2416           0 :             buttonRect.Left()   = buttonRect.Right()+1;
    2417           0 :             buttonRect.Right()  = aAreaRect.Right();
    2418             :         } else {
    2419           0 :             buttonRect.Right()  = buttonRect.Left()-1;
    2420           0 :             buttonRect.Left()   = aAreaRect.Left();
    2421             :         }
    2422           0 :         buttonRect.Top()    = aAreaRect.Top();
    2423           0 :         buttonRect.Bottom() = aAreaRect.Bottom();
    2424             :     }
    2425             : 
    2426           0 :     return( buttonRect );
    2427             : }
    2428             : 
    2429           0 : static void NWPaintOneSpinButton( SalX11Screen nScreen,
    2430             :                                   GdkPixmap*            pixmap,
    2431             :                                   ControlType            nType,
    2432             :                                   ControlPart            nPart,
    2433             :                                   Rectangle                aAreaRect,
    2434             :                                   ControlState            nState,
    2435             :                                   const ImplControlValue&    aValue,
    2436             :                                   const OUString&                rCaption )
    2437             : {
    2438           0 :     Rectangle            buttonRect;
    2439             :     GtkStateType        stateType;
    2440             :     GtkShadowType        shadowType;
    2441           0 :     Rectangle            arrowRect;
    2442             :     gint                arrowSize;
    2443             : 
    2444           0 :     NWEnsureGTKSpinButton( nScreen );
    2445           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    2446             : 
    2447           0 :     buttonRect = NWGetSpinButtonRect( nScreen, nType, nPart, aAreaRect, nState, aValue, rCaption );
    2448             : 
    2449           0 :     NWSetWidgetState( gWidgetData[nScreen].gSpinButtonWidget, nState, stateType );
    2450           0 :     gtk_paint_box( gWidgetData[nScreen].gSpinButtonWidget->style, pixmap, stateType, shadowType, NULL, gWidgetData[nScreen].gSpinButtonWidget,
    2451             :             (nPart == PART_BUTTON_UP) ? "spinbutton_up" : "spinbutton_down",
    2452           0 :             (buttonRect.Left() - aAreaRect.Left()), (buttonRect.Top() - aAreaRect.Top()),
    2453           0 :             buttonRect.GetWidth(), buttonRect.GetHeight() );
    2454             : 
    2455           0 :     arrowSize = (buttonRect.GetWidth() - (2 * gWidgetData[nScreen].gSpinButtonWidget->style->xthickness)) - 4;
    2456           0 :     arrowSize -= arrowSize % 2 - 1; /* force odd */
    2457           0 :     arrowRect.SetSize( Size( arrowSize, arrowSize ) );
    2458           0 :     arrowRect.setX( buttonRect.Left() + (buttonRect.GetWidth() - arrowRect.GetWidth()) / 2 );
    2459           0 :     if ( nPart == PART_BUTTON_UP )
    2460           0 :         arrowRect.setY( buttonRect.Top() + (buttonRect.GetHeight() - arrowRect.GetHeight()) / 2 + 1);
    2461             :     else
    2462           0 :         arrowRect.setY( buttonRect.Top() + (buttonRect.GetHeight() - arrowRect.GetHeight()) / 2 - 1);
    2463             : 
    2464           0 :     gtk_paint_arrow( gWidgetData[nScreen].gSpinButtonWidget->style, pixmap, stateType, GTK_SHADOW_OUT, NULL, gWidgetData[nScreen].gSpinButtonWidget,
    2465             :             "spinbutton", (nPart == PART_BUTTON_UP) ? GTK_ARROW_UP : GTK_ARROW_DOWN, true,
    2466           0 :             (arrowRect.Left() - aAreaRect.Left()), (arrowRect.Top() - aAreaRect.Top()),
    2467           0 :             arrowRect.GetWidth(), arrowRect.GetHeight() );
    2468           0 : }
    2469             : 
    2470           0 : bool GtkSalGraphics::NWPaintGTKComboBox( GdkDrawable* gdkDrawable,
    2471             :                                          ControlType nType, ControlPart nPart,
    2472             :                                          const Rectangle& rControlRectangle,
    2473             :                                          const clipList& rClipList,
    2474             :                                          ControlState nState,
    2475             :                                          const ImplControlValue& aValue,
    2476             :                                          const OUString& rCaption )
    2477             : {
    2478           0 :     Rectangle        pixmapRect;
    2479           0 :     Rectangle        buttonRect;
    2480             :     GtkStateType    stateType;
    2481             :     GtkShadowType    shadowType;
    2482           0 :     Rectangle        arrowRect;
    2483             :     gint            x,y;
    2484             :     GdkRectangle    clipRect;
    2485             : 
    2486           0 :     NWEnsureGTKButton( m_nXScreen );
    2487           0 :     NWEnsureGTKArrow( m_nXScreen );
    2488           0 :     NWEnsureGTKCombo( m_nXScreen );
    2489           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    2490             : 
    2491             :     // Find the overall bounding rect of the buttons's drawing area,
    2492             :     // plus its actual draw rect excluding adornment
    2493           0 :     pixmapRect = rControlRectangle;
    2494           0 :     x = rControlRectangle.Left();
    2495           0 :     y = rControlRectangle.Top();
    2496             : 
    2497           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gBtnWidget, nState, stateType );
    2498           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gComboWidget, nState, stateType );
    2499           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gArrowWidget, nState, stateType );
    2500             : 
    2501           0 :     buttonRect = NWGetComboBoxButtonRect( m_nXScreen, nType, PART_BUTTON_DOWN, pixmapRect, nState, aValue, rCaption );
    2502           0 :     if( nPart == PART_BUTTON_DOWN )
    2503           0 :         buttonRect.Left() += 1;
    2504             : 
    2505           0 :     Rectangle        aEditBoxRect( pixmapRect );
    2506           0 :     aEditBoxRect.SetSize( Size( pixmapRect.GetWidth() - buttonRect.GetWidth(), aEditBoxRect.GetHeight() ) );
    2507           0 :     if( Application::GetSettings().GetLayoutRTL() )
    2508           0 :         aEditBoxRect.SetPos( Point( x + buttonRect.GetWidth() , y ) );
    2509             : 
    2510             :     #define ARROW_EXTENT        0.7
    2511             :     arrowRect.SetSize( Size( (gint)(MIN_ARROW_SIZE * ARROW_EXTENT),
    2512           0 :                              (gint)(MIN_ARROW_SIZE * ARROW_EXTENT) ) );
    2513           0 :     arrowRect.SetPos( Point( buttonRect.Left() + (gint)((buttonRect.GetWidth() - arrowRect.GetWidth()) / 2),
    2514           0 :                              buttonRect.Top() + (gint)((buttonRect.GetHeight() - arrowRect.GetHeight()) / 2) ) );
    2515             : 
    2516           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    2517             :     {
    2518           0 :         clipRect.x = it->Left();
    2519           0 :         clipRect.y = it->Top();
    2520           0 :         clipRect.width = it->GetWidth();
    2521           0 :         clipRect.height = it->GetHeight();
    2522             : 
    2523           0 :         if( nPart == PART_ENTIRE_CONTROL )
    2524             :             NWPaintOneEditBox( m_nXScreen, gdkDrawable, &clipRect, nType, nPart, aEditBoxRect,
    2525           0 :                                nState, aValue, rCaption );
    2526             : 
    2527             :         // Buttons must paint opaque since some themes have alpha-channel enabled buttons
    2528             :         gtk_paint_flat_box( m_pWindow->style, gdkDrawable, GTK_STATE_NORMAL, GTK_SHADOW_NONE,
    2529             :                             &clipRect, m_pWindow, "base",
    2530           0 :                             x+(buttonRect.Left() - pixmapRect.Left()),
    2531           0 :                             y+(buttonRect.Top() - pixmapRect.Top()),
    2532           0 :                             buttonRect.GetWidth(), buttonRect.GetHeight() );
    2533           0 :         gtk_paint_box( GTK_COMBO(gWidgetData[m_nXScreen].gComboWidget)->button->style, gdkDrawable, stateType, shadowType,
    2534           0 :                        &clipRect, GTK_COMBO(gWidgetData[m_nXScreen].gComboWidget)->button, "button",
    2535           0 :                        x+(buttonRect.Left() - pixmapRect.Left()),
    2536           0 :                        y+(buttonRect.Top() - pixmapRect.Top()),
    2537           0 :                        buttonRect.GetWidth(), buttonRect.GetHeight() );
    2538             : 
    2539           0 :         gtk_paint_arrow( gWidgetData[m_nXScreen].gArrowWidget->style, gdkDrawable, stateType, shadowType,
    2540           0 :                          &clipRect, gWidgetData[m_nXScreen].gArrowWidget, "arrow", GTK_ARROW_DOWN, true,
    2541           0 :                          x+(arrowRect.Left() - pixmapRect.Left()), y+(arrowRect.Top() - pixmapRect.Top()),
    2542           0 :                          arrowRect.GetWidth(), arrowRect.GetHeight() );
    2543             :     }
    2544             : 
    2545           0 :     return true;
    2546             : }
    2547             : 
    2548           0 : static Rectangle NWGetComboBoxButtonRect( SalX11Screen nScreen,
    2549             :                                           ControlType,
    2550             :                                           ControlPart nPart,
    2551             :                                           Rectangle                aAreaRect,
    2552             :                                           ControlState,
    2553             :                                           const ImplControlValue&,
    2554             :                                           const OUString& )
    2555             : {
    2556           0 :     Rectangle    aButtonRect;
    2557             :     gint        nArrowWidth;
    2558             :     gint        nButtonWidth;
    2559             :     gint        nFocusWidth;
    2560             :     gint        nFocusPad;
    2561             : 
    2562           0 :     NWEnsureGTKArrow( nScreen );
    2563             : 
    2564             :     // Grab some button style attributes
    2565           0 :     gtk_widget_style_get( gWidgetData[nScreen].gDropdownWidget,
    2566             :                                       "focus-line-width",    &nFocusWidth,
    2567           0 :                                     "focus-padding",     &nFocusPad, (char *)NULL );
    2568             : 
    2569           0 :     nArrowWidth = MIN_ARROW_SIZE + (GTK_MISC(gWidgetData[nScreen].gArrowWidget)->xpad * 2);
    2570           0 :     nButtonWidth = nArrowWidth +
    2571           0 :                    ((BTN_CHILD_SPACING + gWidgetData[nScreen].gDropdownWidget->style->xthickness) * 2)
    2572           0 :                    + (2 * (nFocusWidth+nFocusPad));
    2573           0 :     if( nPart == PART_BUTTON_DOWN )
    2574             :     {
    2575           0 :         aButtonRect.SetSize( Size( nButtonWidth, aAreaRect.GetHeight() ) );
    2576           0 :         if( Application::GetSettings().GetLayoutRTL() )
    2577           0 :             aButtonRect.SetPos( Point( aAreaRect.Left(), aAreaRect.Top() ) );
    2578             :         else
    2579           0 :             aButtonRect.SetPos( Point( aAreaRect.Left() + aAreaRect.GetWidth() - nButtonWidth,
    2580           0 :                                        aAreaRect.Top() ) );
    2581             :     }
    2582           0 :     else if( nPart == PART_SUB_EDIT )
    2583             :     {
    2584           0 :         NWEnsureGTKCombo( nScreen );
    2585             : 
    2586           0 :         gint adjust_x = GTK_CONTAINER(gWidgetData[nScreen].gComboWidget)->border_width +
    2587           0 :                         nFocusWidth +
    2588           0 :                         nFocusPad;
    2589           0 :         gint adjust_y = adjust_x + gWidgetData[nScreen].gComboWidget->style->ythickness;
    2590           0 :         adjust_x     += gWidgetData[nScreen].gComboWidget->style->xthickness;
    2591           0 :         aButtonRect.SetSize( Size( aAreaRect.GetWidth() - nButtonWidth - 2 * adjust_x,
    2592           0 :                                    aAreaRect.GetHeight() - 2 * adjust_y ) );
    2593           0 :         Point aEditPos = aAreaRect.TopLeft();
    2594           0 :         aEditPos.X() += adjust_x;
    2595           0 :         aEditPos.Y() += adjust_y;
    2596           0 :         if( Application::GetSettings().GetLayoutRTL() )
    2597           0 :             aEditPos.X() += nButtonWidth;
    2598           0 :         aButtonRect.SetPos( aEditPos );
    2599             :     }
    2600             : 
    2601           0 :     return( aButtonRect );
    2602             : }
    2603             : 
    2604           0 : bool GtkSalGraphics::NWPaintGTKTabItem( ControlType nType, ControlPart,
    2605             :                                         const Rectangle& rControlRectangle,
    2606             :                                         const clipList&,
    2607             :                                         ControlState nState,
    2608             :                                         const ImplControlValue& aValue,
    2609             :                                         const OUString& )
    2610             : {
    2611             :     OSL_ASSERT( nType != CTRL_TAB_ITEM || aValue.getType() == CTRL_TAB_ITEM );
    2612             :     GdkPixmap *    pixmap;
    2613           0 :     Rectangle        pixmapRect;
    2614           0 :     Rectangle        tabRect;
    2615             :     GtkStateType    stateType;
    2616             :     GtkShadowType    shadowType;
    2617           0 :     if( ! gWidgetData[ m_nXScreen ].gCacheTabItems )
    2618             :     {
    2619           0 :         gWidgetData[ m_nXScreen ].gCacheTabItems = new NWPixmapCache( m_nXScreen );
    2620           0 :         gWidgetData[ m_nXScreen ].gCacheTabPages = new NWPixmapCache( m_nXScreen );
    2621             :     }
    2622           0 :     NWPixmapCache& aCacheItems = *gWidgetData[ m_nXScreen ].gCacheTabItems;
    2623           0 :     NWPixmapCache& aCachePage = *gWidgetData[ m_nXScreen ].gCacheTabPages;
    2624             : 
    2625           0 :     if( !aCacheItems.GetSize() )
    2626           0 :         aCacheItems.SetSize( 20 );
    2627           0 :     if( !aCachePage.GetSize() )
    2628           0 :         aCachePage.SetSize( 1 );
    2629             : 
    2630           0 :     if ( (nType == CTRL_TAB_ITEM) && (aValue.getType() != CTRL_TAB_ITEM) )
    2631             :     {
    2632           0 :         return( false );
    2633             :     }
    2634             : 
    2635           0 :     NWEnsureGTKButton( m_nXScreen );
    2636           0 :     NWEnsureGTKNotebook( m_nXScreen );
    2637           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    2638             : 
    2639             :     // Find the overall bounding rect of the buttons's drawing area,
    2640             :     // plus its actual draw rect excluding adornment
    2641           0 :     pixmapRect = rControlRectangle;
    2642           0 :     if ( nType == CTRL_TAB_ITEM )
    2643             :     {
    2644           0 :         const TabitemValue *    pTabitemValue = static_cast<const TabitemValue *>(&aValue);
    2645           0 :         if ( !pTabitemValue->isFirst() )
    2646             :         {
    2647             :             // GTK+ tabs overlap on the right edge (the top tab obscures the
    2648             :             // left edge of the tab right "below" it, so adjust the rectangle
    2649             :             // to draw tabs slightly large so the overlap happens
    2650           0 :             pixmapRect.Move( -2, 0 );
    2651           0 :             pixmapRect.SetSize( Size( pixmapRect.GetWidth() + 2, pixmapRect.GetHeight() ) );
    2652             :         }
    2653           0 :         if ( nState & CTRL_STATE_SELECTED )
    2654             :         {
    2655             :             // In GTK+, the selected tab is 2px taller than all other tabs
    2656           0 :             pixmapRect.Move( 0, -2 );
    2657           0 :             pixmapRect.Bottom() += 2;
    2658           0 :             tabRect = pixmapRect;
    2659             :             // Only draw over 1 pixel of the tab pane that this tab is drawn on top of.
    2660           0 :             tabRect.Bottom() -= 1;
    2661             :         }
    2662             :         else
    2663           0 :             tabRect = pixmapRect;
    2664             : 
    2665             :         // Allow the tab to draw a right border if needed
    2666           0 :         tabRect.Right() -= 1;
    2667             : 
    2668             :         // avoid degenerate cases which might lead to crashes
    2669           0 :         if( tabRect.GetWidth() <= 1 || tabRect.GetHeight() <= 1 )
    2670           0 :             return false;
    2671             :     }
    2672             : 
    2673           0 :     if( nType == CTRL_TAB_ITEM )
    2674             :     {
    2675           0 :         if( aCacheItems.Find( nType, nState, pixmapRect, &pixmap ) )
    2676           0 :             return NWRenderPixmapToScreen( pixmap, pixmapRect );
    2677             :     }
    2678             :     else
    2679             :     {
    2680           0 :         if( aCachePage.Find( nType, nState, pixmapRect, &pixmap ) )
    2681           0 :             return NWRenderPixmapToScreen( pixmap, pixmapRect );
    2682             :     }
    2683             : 
    2684           0 :     pixmap = gdk_pixmap_new( NULL, pixmapRect.GetWidth(), pixmapRect.GetHeight(),
    2685           0 :                              GetGenericData()->GetSalDisplay()->GetVisual( m_nXScreen ).GetDepth() );
    2686             :     GdkRectangle paintRect;
    2687           0 :     paintRect.x = paintRect.y = 0;
    2688           0 :     paintRect.width = pixmapRect.GetWidth();
    2689           0 :     paintRect.height = pixmapRect.GetHeight();
    2690             : 
    2691             :     gtk_paint_flat_box( m_pWindow->style, pixmap, GTK_STATE_NORMAL,
    2692             :                         GTK_SHADOW_NONE, &paintRect, m_pWindow, "base",
    2693           0 :                         -rControlRectangle.Left(),
    2694           0 :                         -rControlRectangle.Top(),
    2695           0 :                         pixmapRect.GetWidth()+rControlRectangle.Left(),
    2696           0 :                         pixmapRect.GetHeight()+rControlRectangle.Top());
    2697             : 
    2698           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gNotebookWidget, nState, stateType );
    2699             : 
    2700           0 :     switch( nType )
    2701             :     {
    2702             :         case CTRL_TAB_BODY:
    2703           0 :             break;
    2704             : 
    2705             :         case CTRL_TAB_PANE:
    2706           0 :             gtk_paint_box_gap( gWidgetData[m_nXScreen].gNotebookWidget->style, pixmap, GTK_STATE_NORMAL, GTK_SHADOW_OUT, NULL, gWidgetData[m_nXScreen].gNotebookWidget,
    2707           0 :                 (char *)"notebook", 0, 0, pixmapRect.GetWidth(), pixmapRect.GetHeight(), GTK_POS_TOP, 0, 0 );
    2708           0 :             break;
    2709             : 
    2710             :         case CTRL_TAB_ITEM:
    2711             :         {
    2712           0 :             stateType = ( nState & CTRL_STATE_SELECTED ) ? GTK_STATE_NORMAL : GTK_STATE_ACTIVE;
    2713             : 
    2714             :             // First draw the background
    2715           0 :             gtk_paint_flat_box(gWidgetData[m_nXScreen].gNotebookWidget->style, pixmap,
    2716             :                                    GTK_STATE_NORMAL, GTK_SHADOW_NONE, NULL, m_pWindow, "base",
    2717           0 :                                    -rControlRectangle.Left(),
    2718           0 :                                    -rControlRectangle.Top(),
    2719           0 :                                    pixmapRect.GetWidth()+rControlRectangle.Left(),
    2720           0 :                                    pixmapRect.GetHeight()+rControlRectangle.Top());
    2721             : 
    2722             :             // Now the tab itself
    2723           0 :             if( nState & CTRL_STATE_ROLLOVER )
    2724           0 :                 g_object_set_data(G_OBJECT(pixmap),tabPrelitDataName,reinterpret_cast<gpointer>(TRUE));
    2725             : 
    2726           0 :             gtk_paint_extension( gWidgetData[m_nXScreen].gNotebookWidget->style, pixmap, stateType, GTK_SHADOW_OUT, NULL, gWidgetData[m_nXScreen].gNotebookWidget,
    2727           0 :                 (char *)"tab", (tabRect.Left() - pixmapRect.Left()), (tabRect.Top() - pixmapRect.Top()),
    2728           0 :                 tabRect.GetWidth(), tabRect.GetHeight(), GTK_POS_BOTTOM );
    2729             : 
    2730           0 :             g_object_steal_data(G_OBJECT(pixmap),tabPrelitDataName);
    2731             : 
    2732           0 :             if ( nState & CTRL_STATE_SELECTED )
    2733             :             {
    2734             :                 gtk_paint_flat_box( m_pWindow->style, pixmap, stateType, GTK_SHADOW_NONE, NULL, m_pWindow,
    2735           0 :                     "base", 0, (pixmapRect.GetHeight() - 1), pixmapRect.GetWidth(), 1 );
    2736             :             }
    2737           0 :             break;
    2738             :         }
    2739             : 
    2740             :         default:
    2741           0 :             break;
    2742             :     }
    2743             : 
    2744             :     // cache data
    2745           0 :     if( nType == CTRL_TAB_ITEM )
    2746           0 :         aCacheItems.Fill( nType, nState, pixmapRect, pixmap );
    2747             :     else
    2748           0 :         aCachePage.Fill( nType, nState, pixmapRect, pixmap );
    2749             : 
    2750           0 :     bool bSuccess = NWRenderPixmapToScreen(pixmap, pixmapRect);
    2751           0 :     g_object_unref( pixmap );
    2752           0 :     return bSuccess;
    2753             : }
    2754             : 
    2755           0 : bool GtkSalGraphics::NWPaintGTKListBox( GdkDrawable* gdkDrawable,
    2756             :                                         ControlType nType, ControlPart nPart,
    2757             :                                         const Rectangle& rControlRectangle,
    2758             :                                         const clipList& rClipList,
    2759             :                                         ControlState nState,
    2760             :                                         const ImplControlValue& aValue,
    2761             :                                         const OUString& rCaption )
    2762             : {
    2763           0 :     Rectangle        aIndicatorRect;
    2764             :     GtkStateType    stateType;
    2765             :     GtkShadowType    shadowType;
    2766             :     gint            bInteriorFocus;
    2767             :     gint            nFocusLineWidth;
    2768             :     gint            nFocusPadding;
    2769             :     gint            x,y,w,h;
    2770             :     GdkRectangle    clipRect;
    2771             : 
    2772           0 :     NWEnsureGTKButton( m_nXScreen );
    2773           0 :     NWEnsureGTKOptionMenu( m_nXScreen );
    2774           0 :     NWEnsureGTKScrolledWindow( m_nXScreen );
    2775           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    2776             : 
    2777             :     // set up references to correct drawable and cliprect
    2778           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gBtnWidget, nState, stateType );
    2779           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gOptionMenuWidget, nState, stateType );
    2780           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gScrolledWindowWidget, nState, stateType );
    2781             : 
    2782           0 :     x = rControlRectangle.Left();
    2783           0 :     y = rControlRectangle.Top();
    2784           0 :     w = rControlRectangle.GetWidth();
    2785           0 :     h = rControlRectangle.GetHeight();
    2786             : 
    2787           0 :     if ( nPart != PART_WINDOW )
    2788             :     {
    2789           0 :         gtk_widget_style_get( gWidgetData[m_nXScreen].gOptionMenuWidget,
    2790             :             "interior_focus",    &bInteriorFocus,
    2791             :             "focus_line_width",    &nFocusLineWidth,
    2792             :             "focus_padding",    &nFocusPadding,
    2793           0 :             (char *)NULL);
    2794             :     }
    2795             : 
    2796           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    2797             :     {
    2798           0 :         clipRect.x = it->Left();
    2799           0 :         clipRect.y = it->Top();
    2800           0 :         clipRect.width = it->GetWidth();
    2801           0 :         clipRect.height = it->GetHeight();
    2802             : 
    2803           0 :         if ( nPart != PART_WINDOW )
    2804             :         {
    2805             :             // Listboxes must paint opaque since some themes have alpha-channel enabled bodies
    2806             :             gtk_paint_flat_box( m_pWindow->style, gdkDrawable, GTK_STATE_NORMAL, GTK_SHADOW_NONE,
    2807           0 :                                 &clipRect, m_pWindow, "base", x, y, w, h);
    2808           0 :             gtk_paint_box( gWidgetData[m_nXScreen].gOptionMenuWidget->style, gdkDrawable, stateType, shadowType, &clipRect,
    2809           0 :                            gWidgetData[m_nXScreen].gOptionMenuWidget, "optionmenu",
    2810           0 :                            x, y, w, h);
    2811             :             aIndicatorRect = NWGetListBoxIndicatorRect( m_nXScreen, nType, nPart, rControlRectangle, nState,
    2812           0 :                                                         aValue, rCaption );
    2813           0 :             gtk_paint_tab( gWidgetData[m_nXScreen].gOptionMenuWidget->style, gdkDrawable, stateType, shadowType, &clipRect,
    2814           0 :                            gWidgetData[m_nXScreen].gOptionMenuWidget, "optionmenutab",
    2815           0 :                            aIndicatorRect.Left(), aIndicatorRect.Top(),
    2816           0 :                            aIndicatorRect.GetWidth(), aIndicatorRect.GetHeight() );
    2817             :         }
    2818             :         else
    2819             :         {
    2820           0 :             shadowType = GTK_SHADOW_IN;
    2821             : 
    2822           0 :             gtk_paint_shadow( gWidgetData[m_nXScreen].gScrolledWindowWidget->style, gdkDrawable, GTK_STATE_NORMAL, shadowType,
    2823           0 :                 &clipRect, gWidgetData[m_nXScreen].gScrolledWindowWidget, "scrolled_window",
    2824           0 :                 x, y, w, h );
    2825             :         }
    2826             :     }
    2827             : 
    2828           0 :     return true;
    2829             : }
    2830             : 
    2831           0 : bool GtkSalGraphics::NWPaintGTKToolbar(
    2832             :             GdkDrawable* gdkDrawable,
    2833             :             ControlType, ControlPart nPart,
    2834             :             const Rectangle& rControlRectangle,
    2835             :             const clipList& rClipList,
    2836             :             ControlState nState, const ImplControlValue& aValue,
    2837             :             const OUString& string)
    2838             : {
    2839             :     GtkStateType    stateType;
    2840             :     GtkShadowType    shadowType;
    2841             :     gint            x, y, w, h;
    2842           0 :     gint            g_x=0, g_y=0, g_w=10, g_h=10;
    2843           0 :     GtkWidget*      pButtonWidget = gWidgetData[m_nXScreen].gToolbarButtonWidget;
    2844             :     GdkRectangle    clipRect;
    2845             : 
    2846           0 :     NWEnsureGTKToolbar( m_nXScreen );
    2847           0 :     if( nPart == PART_BUTTON ) // toolbar buttons cannot focus in gtk
    2848           0 :         nState &= ~CTRL_STATE_FOCUSED;
    2849           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    2850             : 
    2851           0 :     x = rControlRectangle.Left();
    2852           0 :     y = rControlRectangle.Top();
    2853           0 :     w = rControlRectangle.GetWidth();
    2854           0 :     h = rControlRectangle.GetHeight();
    2855             : 
    2856             :     // handle toolbar
    2857           0 :     if( nPart == PART_DRAW_BACKGROUND_HORZ || nPart == PART_DRAW_BACKGROUND_VERT )
    2858             :     {
    2859           0 :         NWSetWidgetState( gWidgetData[m_nXScreen].gToolbarWidget, nState, stateType );
    2860             : 
    2861           0 :         GTK_WIDGET_UNSET_FLAGS( gWidgetData[m_nXScreen].gToolbarWidget, GTK_SENSITIVE );
    2862           0 :         if ( nState & CTRL_STATE_ENABLED )
    2863           0 :             GTK_WIDGET_SET_FLAGS( gWidgetData[m_nXScreen].gToolbarWidget, GTK_SENSITIVE );
    2864             : 
    2865           0 :         if( nPart == PART_DRAW_BACKGROUND_HORZ )
    2866           0 :             gtk_toolbar_set_orientation( GTK_TOOLBAR(gWidgetData[m_nXScreen].gToolbarWidget), GTK_ORIENTATION_HORIZONTAL );
    2867             :         else
    2868           0 :             gtk_toolbar_set_orientation( GTK_TOOLBAR(gWidgetData[m_nXScreen].gToolbarWidget), GTK_ORIENTATION_VERTICAL );
    2869             :     }
    2870             :     // handle grip
    2871           0 :     else if( nPart == PART_THUMB_HORZ || nPart == PART_THUMB_VERT )
    2872             :     {
    2873           0 :         NWSetWidgetState( gWidgetData[m_nXScreen].gHandleBoxWidget, nState, stateType );
    2874             : 
    2875           0 :         GTK_WIDGET_UNSET_FLAGS( gWidgetData[m_nXScreen].gHandleBoxWidget, GTK_SENSITIVE );
    2876           0 :         if ( nState & CTRL_STATE_ENABLED )
    2877           0 :             GTK_WIDGET_SET_FLAGS( gWidgetData[m_nXScreen].gHandleBoxWidget, GTK_SENSITIVE );
    2878             : 
    2879           0 :         gtk_handle_box_set_shadow_type( GTK_HANDLE_BOX(gWidgetData[m_nXScreen].gHandleBoxWidget), shadowType );
    2880             : 
    2881             :         // evaluate grip rect
    2882           0 :         if( aValue.getType() == CTRL_TOOLBAR )
    2883             :         {
    2884           0 :             const ToolbarValue* pVal = static_cast<const ToolbarValue*>(&aValue);
    2885           0 :             g_x = pVal->maGripRect.Left();
    2886           0 :             g_y = pVal->maGripRect.Top();
    2887           0 :             g_w = pVal->maGripRect.GetWidth();
    2888           0 :             g_h = pVal->maGripRect.GetHeight();
    2889           0 :         }
    2890             :     }
    2891             :     // handle button
    2892           0 :     else if( nPart == PART_BUTTON )
    2893             :     {
    2894           0 :         bool bPaintButton = (nState & CTRL_STATE_PRESSED)
    2895           0 :             || (nState & CTRL_STATE_ROLLOVER);
    2896           0 :         if( aValue.getTristateVal() == BUTTONVALUE_ON )
    2897             :         {
    2898           0 :             gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(pButtonWidget),TRUE);
    2899           0 :             bPaintButton = true;
    2900             :         }
    2901             :         else
    2902           0 :             gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(pButtonWidget),FALSE);
    2903             : 
    2904           0 :         NWSetWidgetState( pButtonWidget, nState, stateType );
    2905           0 :         gtk_widget_ensure_style( pButtonWidget );
    2906           0 :         if(bPaintButton)
    2907           0 :             NWPaintGTKButtonReal(pButtonWidget, gdkDrawable, 0, 0, rControlRectangle, rClipList, nState, aValue, string);
    2908             :     }
    2909             : 
    2910           0 :     if( nPart != PART_BUTTON )
    2911             :     {
    2912           0 :         for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    2913             :         {
    2914           0 :             clipRect.x = it->Left();
    2915           0 :             clipRect.y = it->Top();
    2916           0 :             clipRect.width = it->GetWidth();
    2917           0 :             clipRect.height = it->GetHeight();
    2918             : 
    2919             :             // draw toolbar
    2920           0 :             if( nPart == PART_DRAW_BACKGROUND_HORZ || nPart == PART_DRAW_BACKGROUND_VERT )
    2921             :             {
    2922           0 :                 gtk_paint_flat_box( gWidgetData[m_nXScreen].gToolbarWidget->style,
    2923             :                                     gdkDrawable,
    2924             :                                     (GtkStateType)GTK_STATE_NORMAL,
    2925             :                                     GTK_SHADOW_NONE,
    2926             :                                     &clipRect,
    2927           0 :                                     gWidgetData[m_nXScreen].gToolbarWidget,
    2928             :                                     "base",
    2929           0 :                                     x, y, w, h );
    2930           0 :                 gtk_paint_box( gWidgetData[m_nXScreen].gToolbarWidget->style,
    2931             :                                gdkDrawable,
    2932             :                                stateType,
    2933             :                                shadowType,
    2934             :                                &clipRect,
    2935           0 :                                gWidgetData[m_nXScreen].gToolbarWidget,
    2936             :                                "toolbar",
    2937           0 :                                x, y, w, h );
    2938             :             }
    2939             :             // draw grip
    2940           0 :             else if( nPart == PART_THUMB_HORZ || nPart == PART_THUMB_VERT )
    2941             :             {
    2942           0 :                 gtk_paint_handle( gWidgetData[m_nXScreen].gHandleBoxWidget->style,
    2943             :                                   gdkDrawable,
    2944             :                                   GTK_STATE_NORMAL,
    2945             :                                   GTK_SHADOW_OUT,
    2946             :                                   &clipRect,
    2947           0 :                                   gWidgetData[m_nXScreen].gHandleBoxWidget,
    2948             :                                   "handlebox",
    2949             :                                   g_x, g_y, g_w, g_h,
    2950             :                                   nPart == PART_THUMB_HORZ ?
    2951             :                                   GTK_ORIENTATION_HORIZONTAL :
    2952             :                                   GTK_ORIENTATION_VERTICAL
    2953           0 :                                   );
    2954             :             }
    2955           0 :             else if( nPart == PART_SEPARATOR_HORZ || nPart == PART_SEPARATOR_VERT )
    2956             :             {
    2957           0 :                 const double shim = 0.2;
    2958             : 
    2959             : #if GTK_CHECK_VERSION(2,10,0)
    2960           0 :                 gint separator_height, separator_width, wide_separators = 0;
    2961             : 
    2962           0 :                 gtk_widget_style_get (gWidgetData[m_nXScreen].gSeparator,
    2963             :                                       "wide-separators",  &wide_separators,
    2964             :                                       "separator-width",  &separator_width,
    2965             :                                       "separator-height", &separator_height,
    2966           0 :                                       NULL);
    2967             : 
    2968           0 :                 if (wide_separators)
    2969             :                 {
    2970           0 :                     if (nPart == PART_SEPARATOR_VERT)
    2971           0 :                         gtk_paint_box (gWidgetData[m_nXScreen].gSeparator->style, gdkDrawable,
    2972             :                                        GTK_STATE_NORMAL, GTK_SHADOW_ETCHED_OUT,
    2973           0 :                                        &clipRect, gWidgetData[m_nXScreen].gSeparator, "vseparator",
    2974           0 :                                        x + (w - separator_width) / 2, y + h * shim,
    2975           0 :                                        separator_width, h * (1 - 2*shim));
    2976             :                     else
    2977           0 :                         gtk_paint_box (gWidgetData[m_nXScreen].gSeparator->style, gdkDrawable,
    2978             :                                        GTK_STATE_NORMAL, GTK_SHADOW_ETCHED_OUT,
    2979           0 :                                        &clipRect, gWidgetData[m_nXScreen].gSeparator, "hseparator",
    2980           0 :                                        x + w * shim, y + (h - separator_width) / 2,
    2981           0 :                                        w * (1 - 2*shim), separator_width);
    2982             :                 }
    2983             :                 else
    2984             : #endif
    2985             :                 {
    2986           0 :                     if (nPart == PART_SEPARATOR_VERT)
    2987           0 :                         gtk_paint_vline (gWidgetData[m_nXScreen].gSeparator->style, gdkDrawable,
    2988             :                                          GTK_STATE_NORMAL,
    2989           0 :                                          &clipRect, gWidgetData[m_nXScreen].gSeparator, "vseparator",
    2990           0 :                                          y + h * shim, y + h * (1 - shim), x + w/2 - 1);
    2991             :                     else
    2992           0 :                         gtk_paint_hline (gWidgetData[m_nXScreen].gSeparator->style, gdkDrawable,
    2993             :                                          GTK_STATE_NORMAL,
    2994           0 :                                          &clipRect, gWidgetData[m_nXScreen].gSeparator, "hseparator",
    2995           0 :                                          x + w * shim, x + w * (1 - shim), y + h/2 - 1);
    2996             :                 }
    2997             :             }
    2998             :         }
    2999             :     }
    3000             : 
    3001           0 :     return true;
    3002             : }
    3003             : 
    3004           0 : bool GtkSalGraphics::NWPaintGTKMenubar(
    3005             :             GdkDrawable* gdkDrawable,
    3006             :             ControlType, ControlPart nPart,
    3007             :             const Rectangle& rControlRectangle,
    3008             :             const clipList& rClipList,
    3009             :             ControlState nState, const ImplControlValue&,
    3010             :             const OUString& )
    3011             : {
    3012             :     GtkStateType    stateType;
    3013             :     GtkShadowType    shadowType;
    3014           0 :     GtkShadowType   selected_shadow_type = GTK_SHADOW_OUT;
    3015             :     gint            x, y, w, h;
    3016             :     GdkRectangle    clipRect;
    3017             : 
    3018           0 :     NWEnsureGTKMenubar( m_nXScreen );
    3019           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    3020             : 
    3021           0 :     x = rControlRectangle.Left();
    3022           0 :     y = rControlRectangle.Top();
    3023           0 :     w = rControlRectangle.GetWidth();
    3024           0 :     h = rControlRectangle.GetHeight();
    3025             : 
    3026           0 :     if( nPart == PART_MENU_ITEM )
    3027             :     {
    3028           0 :         if( nState & CTRL_STATE_SELECTED )
    3029             :         {
    3030           0 :             gtk_widget_style_get( gWidgetData[m_nXScreen].gMenuItemMenubarWidget,
    3031             :                                   "selected_shadow_type", &selected_shadow_type,
    3032           0 :                                   (char *)NULL);
    3033             :         }
    3034             :     }
    3035             : 
    3036           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    3037             :     {
    3038           0 :         clipRect.x = it->Left();
    3039           0 :         clipRect.y = it->Top();
    3040           0 :         clipRect.width = it->GetWidth();
    3041           0 :         clipRect.height = it->GetHeight();
    3042             : 
    3043             :         // handle Menubar
    3044           0 :         if( nPart == PART_ENTIRE_CONTROL )
    3045             :         {
    3046           0 :             NWSetWidgetState( gWidgetData[m_nXScreen].gMenubarWidget, nState, stateType );
    3047             : 
    3048           0 :             GTK_WIDGET_UNSET_FLAGS( gWidgetData[m_nXScreen].gMenubarWidget, GTK_SENSITIVE );
    3049           0 :             if ( nState & CTRL_STATE_ENABLED )
    3050           0 :                 GTK_WIDGET_SET_FLAGS( gWidgetData[m_nXScreen].gMenubarWidget, GTK_SENSITIVE );
    3051             : 
    3052             :             // for translucent menubar styles paint background first
    3053           0 :             gtk_paint_flat_box( gWidgetData[m_nXScreen].gMenubarWidget->style,
    3054             :                                 gdkDrawable,
    3055             :                                 GTK_STATE_NORMAL,
    3056             :                                 GTK_SHADOW_NONE,
    3057             :                                 &clipRect,
    3058           0 :                                 GTK_WIDGET(m_pWindow),
    3059             :                                 "base",
    3060           0 :                                 x, y, w, h );
    3061           0 :             gtk_paint_box( gWidgetData[m_nXScreen].gMenubarWidget->style,
    3062             :                            gdkDrawable,
    3063             :                            stateType,
    3064             :                            shadowType,
    3065             :                            &clipRect,
    3066           0 :                            gWidgetData[m_nXScreen].gMenubarWidget,
    3067             :                            "menubar",
    3068           0 :                            x, y, w, h );
    3069             :         }
    3070             : 
    3071           0 :         else if( nPart == PART_MENU_ITEM )
    3072             :         {
    3073           0 :             if( nState & CTRL_STATE_SELECTED )
    3074             :             {
    3075           0 :                 gtk_paint_box( gWidgetData[m_nXScreen].gMenuItemMenubarWidget->style,
    3076             :                                gdkDrawable,
    3077             :                                GTK_STATE_PRELIGHT,
    3078             :                                selected_shadow_type,
    3079             :                                &clipRect,
    3080           0 :                                gWidgetData[m_nXScreen].gMenuItemMenubarWidget,
    3081             :                                "menuitem",
    3082           0 :                                x, y, w, h);
    3083             :             }
    3084             :         }
    3085             :     }
    3086             : 
    3087           0 :     return true;
    3088             : }
    3089             : 
    3090           0 : bool GtkSalGraphics::NWPaintGTKPopupMenu(
    3091             :             GdkDrawable* gdkDrawable,
    3092             :             ControlType, ControlPart nPart,
    3093             :             const Rectangle& rControlRectangle,
    3094             :             const clipList& rClipList,
    3095             :             ControlState nState, const ImplControlValue&,
    3096             :             const OUString& )
    3097             : {
    3098             :     // #i50745# gtk does not draw disabled menu entries (and crux theme
    3099             :     // even crashes) in very old (Fedora Core 4 vintage) gtk's
    3100           0 :     if (gtk_major_version <= 2 && gtk_minor_version <= 8 &&
    3101           0 :         nPart == PART_MENU_ITEM && ! (nState & CTRL_STATE_ENABLED) )
    3102           0 :         return true;
    3103             : 
    3104             :     GtkStateType    stateType;
    3105             :     GtkShadowType    shadowType;
    3106           0 :     GtkShadowType   selected_shadow_type = GTK_SHADOW_OUT;
    3107             :     gint            x, y, w, h;
    3108             :     GdkRectangle    clipRect;
    3109             : 
    3110           0 :     NWEnsureGTKMenu( m_nXScreen );
    3111           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    3112             : 
    3113           0 :     x = rControlRectangle.Left();
    3114           0 :     y = rControlRectangle.Top();
    3115           0 :     w = rControlRectangle.GetWidth();
    3116           0 :     h = rControlRectangle.GetHeight();
    3117             : 
    3118           0 :     if( nPart == PART_MENU_ITEM &&
    3119           0 :         ( nState & (CTRL_STATE_SELECTED|CTRL_STATE_ROLLOVER) ) )
    3120             :     {
    3121           0 :         gtk_widget_style_get( gWidgetData[m_nXScreen].gMenuItemMenuWidget,
    3122             :                               "selected_shadow_type", &selected_shadow_type,
    3123           0 :                               (char *)NULL);
    3124             :     }
    3125             : 
    3126           0 :     NWSetWidgetState( gWidgetData[m_nXScreen].gMenuWidget, nState, stateType );
    3127             : 
    3128           0 :     GTK_WIDGET_UNSET_FLAGS( gWidgetData[m_nXScreen].gMenuWidget, GTK_SENSITIVE );
    3129           0 :     if ( nState & CTRL_STATE_ENABLED )
    3130           0 :         GTK_WIDGET_SET_FLAGS( gWidgetData[m_nXScreen].gMenuWidget, GTK_SENSITIVE );
    3131             : 
    3132           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    3133             :     {
    3134           0 :         clipRect.x = it->Left();
    3135           0 :         clipRect.y = it->Top();
    3136           0 :         clipRect.width = it->GetWidth();
    3137           0 :         clipRect.height = it->GetHeight();
    3138             : 
    3139           0 :         if( nPart == PART_ENTIRE_CONTROL )
    3140             :         {
    3141             :             // for translucent menubar styles paint background first
    3142           0 :             gtk_paint_flat_box( gWidgetData[m_nXScreen].gMenuWidget->style,
    3143             :                                 gdkDrawable,
    3144             :                                 GTK_STATE_NORMAL,
    3145             :                                 GTK_SHADOW_NONE,
    3146             :                                 &clipRect,
    3147           0 :                                 GTK_WIDGET(m_pWindow),
    3148             :                                 "base",
    3149           0 :                                 x, y, w, h );
    3150           0 :             gtk_paint_box( gWidgetData[m_nXScreen].gMenuWidget->style,
    3151             :                            gdkDrawable,
    3152             :                            GTK_STATE_NORMAL,
    3153             :                            GTK_SHADOW_OUT,
    3154             :                            &clipRect,
    3155           0 :                            gWidgetData[m_nXScreen].gMenuWidget,
    3156             :                            "menu",
    3157           0 :                            x, y, w, h );
    3158             :         }
    3159           0 :         else if( nPart == PART_MENU_ITEM )
    3160             :         {
    3161           0 :             if( nState & (CTRL_STATE_SELECTED|CTRL_STATE_ROLLOVER) )
    3162             :             {
    3163           0 :                 if( nState & CTRL_STATE_ENABLED )
    3164           0 :                 gtk_paint_box( gWidgetData[m_nXScreen].gMenuItemMenuWidget->style,
    3165             :                                gdkDrawable,
    3166             :                                GTK_STATE_PRELIGHT,
    3167             :                                selected_shadow_type,
    3168             :                                &clipRect,
    3169           0 :                                gWidgetData[m_nXScreen].gMenuItemMenuWidget,
    3170             :                                "menuitem",
    3171           0 :                                x, y, w, h);
    3172             :             }
    3173             :         }
    3174           0 :         else if( nPart == PART_MENU_ITEM_CHECK_MARK || nPart == PART_MENU_ITEM_RADIO_MARK )
    3175             :         {
    3176             :             GtkWidget* pWidget = (nPart == PART_MENU_ITEM_CHECK_MARK) ?
    3177           0 :                                  gWidgetData[m_nXScreen].gMenuItemCheckMenuWidget :
    3178           0 :                                  gWidgetData[m_nXScreen].gMenuItemRadioMenuWidget;
    3179             : 
    3180             :             GtkStateType nStateType;
    3181             :             GtkShadowType nShadowType;
    3182           0 :             NWConvertVCLStateToGTKState( nState, &nStateType, &nShadowType );
    3183             : 
    3184           0 :             if ( (nState & CTRL_STATE_SELECTED) && (nState & CTRL_STATE_ENABLED) )
    3185           0 :                 nStateType = GTK_STATE_PRELIGHT;
    3186             : 
    3187           0 :             NWSetWidgetState( pWidget, nState, nStateType );
    3188             : 
    3189           0 :             if ( nPart == PART_MENU_ITEM_CHECK_MARK )
    3190             :             {
    3191             :                 gtk_paint_check( pWidget->style,
    3192             :                                  gdkDrawable,
    3193             :                                  nStateType,
    3194             :                                  nShadowType,
    3195             :                                  &clipRect,
    3196           0 :                                  gWidgetData[m_nXScreen].gMenuItemMenuWidget,
    3197             :                                  "check",
    3198           0 :                                  x, y, w, h );
    3199             :             }
    3200             :             else
    3201             :             {
    3202             :                 gtk_paint_option( pWidget->style,
    3203             :                                   gdkDrawable,
    3204             :                                   nStateType,
    3205             :                                   nShadowType,
    3206             :                                   &clipRect,
    3207           0 :                                   gWidgetData[m_nXScreen].gMenuItemMenuWidget,
    3208             :                                   "option",
    3209           0 :                                   x, y, w, h );
    3210           0 :             }
    3211             :         }
    3212           0 :         else if( nPart == PART_MENU_SEPARATOR )
    3213             :         {
    3214           0 :             gtk_paint_hline( gWidgetData[m_nXScreen].gMenuItemSeparatorMenuWidget->style,
    3215             :                              gdkDrawable,
    3216             :                              GTK_STATE_NORMAL,
    3217             :                              &clipRect,
    3218           0 :                              gWidgetData[m_nXScreen].gMenuItemSeparatorMenuWidget,
    3219             :                              "menuitem",
    3220           0 :                              x, x + w, y + h / 2);
    3221             :         }
    3222           0 :         else if( nPart == PART_MENU_SUBMENU_ARROW )
    3223             :         {
    3224             :             GtkStateType nStateType;
    3225             :             GtkShadowType nShadowType;
    3226           0 :             NWConvertVCLStateToGTKState( nState, &nStateType, &nShadowType );
    3227             : 
    3228           0 :             if ( (nState & CTRL_STATE_SELECTED) && (nState & CTRL_STATE_ENABLED) )
    3229           0 :                 nStateType = GTK_STATE_PRELIGHT;
    3230             : 
    3231           0 :             NWSetWidgetState( gWidgetData[m_nXScreen].gMenuItemMenuWidget,
    3232           0 :                               nState, nStateType );
    3233             : 
    3234             :             GtkArrowType eArrow;
    3235           0 :             if( Application::GetSettings().GetLayoutRTL() )
    3236           0 :                 eArrow = GTK_ARROW_LEFT;
    3237             :             else
    3238           0 :                 eArrow = GTK_ARROW_RIGHT;
    3239             : 
    3240           0 :             gtk_paint_arrow( gWidgetData[m_nXScreen].gMenuItemMenuWidget->style,
    3241             :                              gdkDrawable,
    3242             :                              nStateType,
    3243             :                              nShadowType,
    3244             :                              &clipRect,
    3245           0 :                              gWidgetData[m_nXScreen].gMenuItemMenuWidget,
    3246             :                              "menuitem",
    3247             :                              eArrow, TRUE,
    3248           0 :                              x, y, w, h);
    3249             :         }
    3250             :     }
    3251             : 
    3252           0 :     return true;
    3253             : }
    3254             : 
    3255           0 : bool GtkSalGraphics::NWPaintGTKTooltip(
    3256             :             GdkDrawable* gdkDrawable,
    3257             :             ControlType, ControlPart,
    3258             :             const Rectangle& rControlRectangle,
    3259             :             const clipList& rClipList,
    3260             :             ControlState, const ImplControlValue&,
    3261             :             const OUString& )
    3262             : {
    3263           0 :     NWEnsureGTKTooltip( m_nXScreen );
    3264             : 
    3265             :     gint            x, y, w, h;
    3266             :     GdkRectangle    clipRect;
    3267             : 
    3268           0 :     x = rControlRectangle.Left();
    3269           0 :     y = rControlRectangle.Top();
    3270           0 :     w = rControlRectangle.GetWidth();
    3271           0 :     h = rControlRectangle.GetHeight();
    3272             : 
    3273           0 :     for( clipList::const_iterator it = rClipList.begin(); it != rClipList.end(); ++it )
    3274             :     {
    3275           0 :         clipRect.x = it->Left();
    3276           0 :         clipRect.y = it->Top();
    3277           0 :         clipRect.width = it->GetWidth();
    3278           0 :         clipRect.height = it->GetHeight();
    3279             : 
    3280           0 :         gtk_paint_flat_box( gWidgetData[m_nXScreen].gTooltipPopup->style,
    3281             :                             gdkDrawable,
    3282             :                             GTK_STATE_NORMAL,
    3283             :                             GTK_SHADOW_OUT,
    3284             :                             &clipRect,
    3285           0 :                             gWidgetData[m_nXScreen].gTooltipPopup,
    3286             :                             "tooltip",
    3287           0 :                             x, y, w, h );
    3288             :     }
    3289             : 
    3290           0 :     return true;
    3291             : }
    3292             : 
    3293           0 : bool GtkSalGraphics::NWPaintGTKListNode(
    3294             :             GdkDrawable*,
    3295             :             ControlType, ControlPart,
    3296             :             const Rectangle& rControlRectangle,
    3297             :             const clipList&,
    3298             :             ControlState nState, const ImplControlValue& rValue,
    3299             :             const OUString& )
    3300             : {
    3301           0 :     NWEnsureGTKTreeView( m_nXScreen );
    3302             : 
    3303           0 :     Rectangle aRect( rControlRectangle );
    3304           0 :     aRect.Left() -= 2;
    3305           0 :     aRect.Right() += 2;
    3306           0 :     aRect.Top() -= 2;
    3307           0 :     aRect.Bottom() += 2;
    3308             :     gint            w, h;
    3309           0 :     w = aRect.GetWidth();
    3310           0 :     h = aRect.GetHeight();
    3311             : 
    3312             :     GtkStateType    stateType;
    3313             :     GtkShadowType    shadowType;
    3314           0 :     NWConvertVCLStateToGTKState( nState, &stateType, &shadowType );
    3315             : 
    3316           0 :     ButtonValue aButtonValue = rValue.getTristateVal();
    3317           0 :     GtkExpanderStyle eStyle = GTK_EXPANDER_EXPANDED;
    3318             : 
    3319           0 :     switch( aButtonValue )
    3320             :     {
    3321           0 :         case BUTTONVALUE_ON: eStyle = GTK_EXPANDER_EXPANDED;break;
    3322           0 :         case BUTTONVALUE_OFF: eStyle = GTK_EXPANDER_COLLAPSED; break;
    3323             :         default:
    3324           0 :             break;
    3325             :     }
    3326             : 
    3327           0 :     GdkPixmap* pixmap = NWGetPixmapFromScreen( aRect );
    3328           0 :     if( ! pixmap )
    3329           0 :         return false;
    3330             : 
    3331           0 :     GdkDrawable* const &pixDrawable = GDK_DRAWABLE( pixmap );
    3332           0 :     gtk_paint_expander( gWidgetData[m_nXScreen].gTreeView->style,
    3333             :                         pixDrawable,
    3334             :                         stateType,
    3335             :                         NULL,
    3336           0 :                         gWidgetData[m_nXScreen].gTreeView,
    3337             :                         "treeview",
    3338             :                         w/2, h/2,
    3339           0 :                         eStyle );
    3340             : 
    3341           0 :     bool bRet = NWRenderPixmapToScreen( pixmap, aRect );
    3342           0 :     g_object_unref( pixmap );
    3343             : 
    3344           0 :     return bRet;
    3345             : }
    3346             : 
    3347           0 : bool GtkSalGraphics::NWPaintGTKProgress(
    3348             :             GdkDrawable*,
    3349             :             ControlType, ControlPart,
    3350             :             const Rectangle& rControlRectangle,
    3351             :             const clipList&,
    3352             :             ControlState, const ImplControlValue& rValue,
    3353             :             const OUString& )
    3354             : {
    3355           0 :     NWEnsureGTKProgressBar( m_nXScreen );
    3356             : 
    3357             :     gint            w, h;
    3358           0 :     w = rControlRectangle.GetWidth();
    3359           0 :     h = rControlRectangle.GetHeight();
    3360             : 
    3361           0 :     long nProgressWidth = rValue.getNumericVal();
    3362             : 
    3363           0 :     GdkPixmap* pixmap = NWGetPixmapFromScreen( Rectangle( Point( 0, 0 ), Size( w, h ) ) );
    3364           0 :     if( ! pixmap )
    3365           0 :         return false;
    3366             : 
    3367           0 :     GdkDrawable* const &pixDrawable = GDK_DRAWABLE( pixmap );
    3368             : 
    3369             :     // paint background
    3370           0 :     gtk_paint_flat_box(gWidgetData[m_nXScreen].gProgressBar->style, pixDrawable,
    3371             :                            GTK_STATE_NORMAL, GTK_SHADOW_NONE, NULL, m_pWindow, "base",
    3372           0 :                            -rControlRectangle.Left(),-rControlRectangle.Top(),
    3373           0 :                            rControlRectangle.Left()+w,rControlRectangle.Top()+h);
    3374             : 
    3375           0 :     gtk_paint_flat_box( gWidgetData[m_nXScreen].gProgressBar->style,
    3376             :                         pixDrawable,
    3377             :                         GTK_STATE_NORMAL,
    3378             :                         GTK_SHADOW_NONE,
    3379             :                         NULL,
    3380           0 :                         gWidgetData[m_nXScreen].gProgressBar,
    3381             :                         "trough",
    3382           0 :                         0, 0, w, h );
    3383           0 :     if( nProgressWidth > 0 )
    3384             :     {
    3385             :         // paint progress
    3386           0 :         if( Application::GetSettings().GetLayoutRTL() )
    3387             :         {
    3388           0 :             gtk_paint_box( gWidgetData[m_nXScreen].gProgressBar->style,
    3389             :                            pixDrawable,
    3390             :                            GTK_STATE_PRELIGHT, GTK_SHADOW_OUT,
    3391             :                            NULL,
    3392           0 :                            gWidgetData[m_nXScreen].gProgressBar,
    3393             :                            "bar",
    3394             :                            w-nProgressWidth, 0, nProgressWidth, h
    3395           0 :                            );
    3396             :         }
    3397             :         else
    3398             :         {
    3399           0 :             gtk_paint_box( gWidgetData[m_nXScreen].gProgressBar->style,
    3400             :                            pixDrawable,
    3401             :                            GTK_STATE_PRELIGHT, GTK_SHADOW_OUT,
    3402             :                            NULL,
    3403           0 :                            gWidgetData[m_nXScreen].gProgressBar,
    3404             :                            "bar",
    3405             :                            0, 0, nProgressWidth, h
    3406           0 :                            );
    3407             :         }
    3408             :     }
    3409             : 
    3410           0 :     bool bRet = NWRenderPixmapToScreen( pixmap, rControlRectangle );
    3411           0 :     g_object_unref( pixmap );
    3412             : 
    3413           0 :     return bRet;
    3414             : }
    3415             : 
    3416           0 : bool GtkSalGraphics::NWPaintGTKSlider(
    3417             :             GdkDrawable*,
    3418             :             ControlType, ControlPart nPart,
    3419             :             const Rectangle& rControlRectangle,
    3420             :             const clipList&,
    3421             :             ControlState nState, const ImplControlValue& rValue,
    3422             :             const OUString& )
    3423             : {
    3424             :     OSL_ASSERT( rValue.getType() == CTRL_SLIDER );
    3425           0 :     NWEnsureGTKSlider( m_nXScreen );
    3426             : 
    3427             :     gint            w, h;
    3428           0 :     w = rControlRectangle.GetWidth();
    3429           0 :     h = rControlRectangle.GetHeight();
    3430             : 
    3431           0 :     const SliderValue* pVal = static_cast<const SliderValue*>(&rValue);
    3432             : 
    3433           0 :     GdkPixmap* pixmap = NWGetPixmapFromScreen( rControlRectangle );
    3434           0 :     if( ! pixmap )
    3435           0 :         return false;
    3436             : 
    3437           0 :     GdkDrawable* const &pixDrawable = GDK_DRAWABLE( pixmap );
    3438             :     GtkWidget* pWidget = (nPart == PART_TRACK_HORZ_AREA)
    3439           0 :                          ? GTK_WIDGET(gWidgetData[m_nXScreen].gHScale)
    3440           0 :                          : GTK_WIDGET(gWidgetData[m_nXScreen].gVScale);
    3441           0 :     const gchar* pDetail = (nPart == PART_TRACK_HORZ_AREA) ? "hscale" : "vscale";
    3442           0 :     GtkOrientation eOri = (nPart == PART_TRACK_HORZ_AREA) ? GTK_ORIENTATION_HORIZONTAL : GTK_ORIENTATION_VERTICAL;
    3443           0 :     gint slider_width = 10;
    3444           0 :     gint slider_length = 10;
    3445           0 :     gint trough_border = 0;
    3446             :     gtk_widget_style_get( pWidget,
    3447             :                           "slider-width", &slider_width,
    3448             :                           "slider-length", &slider_length,
    3449             :                           "trough-border", &trough_border,
    3450           0 :                           NULL);
    3451             : 
    3452           0 :     GtkStateType eState = (nState & CTRL_STATE_ENABLED) ? GTK_STATE_NORMAL : GTK_STATE_INSENSITIVE;
    3453           0 :     if( nPart == PART_TRACK_HORZ_AREA )
    3454             :     {
    3455             :         gtk_paint_box( pWidget->style,
    3456             :                        pixDrawable,
    3457             :                        eState,
    3458             :                        GTK_SHADOW_IN,
    3459             :                        NULL,
    3460             :                        pWidget,
    3461             :                        "trough",
    3462           0 :                        0, (h-slider_width-2*trough_border)/2, w, slider_width + 2*trough_border);
    3463           0 :         gint x = (w - slider_length + 1) * (pVal->mnCur - pVal->mnMin) / (pVal->mnMax - pVal->mnMin);
    3464             :         gtk_paint_slider( pWidget->style,
    3465             :                           pixDrawable,
    3466             :                           eState,
    3467             :                           GTK_SHADOW_OUT,
    3468             :                           NULL,
    3469             :                           pWidget,
    3470             :                           pDetail,
    3471           0 :                           x, (h-slider_width)/2,
    3472             :                           slider_length, slider_width,
    3473           0 :                           eOri );
    3474             :     }
    3475             :     else
    3476             :     {
    3477             :         gtk_paint_box( pWidget->style,
    3478             :                        pixDrawable,
    3479             :                        eState,
    3480             :                        GTK_SHADOW_IN,
    3481             :                        NULL,
    3482             :                        pWidget,
    3483             :                        "trough",
    3484           0 :                        (w-slider_width-2*trough_border)/2, 0, slider_width + 2*trough_border, h);
    3485           0 :         gint y = (h - slider_length + 1) * (pVal->mnCur - pVal->mnMin) / (pVal->mnMax - pVal->mnMin);
    3486             :         gtk_paint_slider( pWidget->style,
    3487             :                           pixDrawable,
    3488             :                           eState,
    3489             :                           GTK_SHADOW_OUT,
    3490             :                           NULL,
    3491             :                           pWidget,
    3492             :                           pDetail,
    3493           0 :                           (w-slider_width)/2, y,
    3494             :                           slider_width, slider_length,
    3495           0 :                           eOri );
    3496             :     }
    3497             : 
    3498           0 :     bool bRet = NWRenderPixmapToScreen( pixmap, rControlRectangle );
    3499           0 :     g_object_unref( pixmap );
    3500             : 
    3501           0 :     return bRet;
    3502             : }
    3503             : 
    3504           0 : static int getFrameWidth(GtkWidget* widget)
    3505             : {
    3506           0 :     return widget->style->xthickness;
    3507             : }
    3508             : 
    3509           0 : static Rectangle NWGetListBoxButtonRect( SalX11Screen nScreen,
    3510             :                                          ControlType,
    3511             :                                          ControlPart    nPart,
    3512             :                                          Rectangle      aAreaRect,
    3513             :                                          ControlState,
    3514             :                                          const ImplControlValue&,
    3515             :                                          const OUString& )
    3516             : {
    3517           0 :     Rectangle       aPartRect;
    3518           0 :     GtkRequisition *pIndicatorSize = NULL;
    3519           0 :     GtkBorder      *pIndicatorSpacing = NULL;
    3520           0 :     gint            width = 13;    // GTK+ default
    3521           0 :     gint            right = 5;    // GTK+ default
    3522           0 :     gint            nButtonAreaWidth = 0;
    3523           0 :     gint            xthickness = 0;
    3524             : 
    3525           0 :     NWEnsureGTKOptionMenu( nScreen );
    3526             : 
    3527           0 :     gtk_widget_style_get( gWidgetData[nScreen].gOptionMenuWidget,
    3528             :             "indicator_size",    &pIndicatorSize,
    3529           0 :             "indicator_spacing",&pIndicatorSpacing, (char *)NULL);
    3530             : 
    3531           0 :     if ( pIndicatorSize )
    3532           0 :         width = pIndicatorSize->width;
    3533             : 
    3534           0 :     if ( pIndicatorSpacing )
    3535           0 :         right = pIndicatorSpacing->right;
    3536             : 
    3537           0 :     Size aPartSize( 0, aAreaRect.GetHeight() );
    3538           0 :     Point aPartPos ( 0, aAreaRect.Top() );
    3539             : 
    3540           0 :     xthickness = gWidgetData[nScreen].gOptionMenuWidget->style->xthickness;
    3541           0 :     nButtonAreaWidth = width + right + (xthickness * 2);
    3542           0 :     switch( nPart )
    3543             :     {
    3544             :         case PART_BUTTON_DOWN:
    3545           0 :             aPartSize.Width() = nButtonAreaWidth;
    3546           0 :             aPartPos.X() = aAreaRect.Left() + aAreaRect.GetWidth() - aPartSize.Width();
    3547           0 :             break;
    3548             : 
    3549             :         case PART_SUB_EDIT:
    3550           0 :             aPartSize.Width() = aAreaRect.GetWidth() - nButtonAreaWidth - xthickness;
    3551           0 :             if( Application::GetSettings().GetLayoutRTL() )
    3552           0 :                 aPartPos.X() = aAreaRect.Left() + nButtonAreaWidth;
    3553             :             else
    3554           0 :                 aPartPos.X() = aAreaRect.Left() + xthickness;
    3555           0 :             break;
    3556             : 
    3557             :         default:
    3558           0 :             aPartSize.Width() = aAreaRect.GetWidth();
    3559           0 :             aPartPos.X() = aAreaRect.Left();
    3560           0 :             break;
    3561             :     }
    3562           0 :     aPartRect = Rectangle( aPartPos, aPartSize );
    3563             : 
    3564           0 :     if ( pIndicatorSize )
    3565           0 :         gtk_requisition_free( pIndicatorSize );
    3566           0 :     if ( pIndicatorSpacing )
    3567           0 :         gtk_border_free( pIndicatorSpacing );
    3568             : 
    3569           0 :     return( aPartRect );
    3570             : }
    3571             : 
    3572           0 : static Rectangle NWGetListBoxIndicatorRect( SalX11Screen nScreen,
    3573             :                                             ControlType,
    3574             :                                             ControlPart,
    3575             :                                             Rectangle                aAreaRect,
    3576             :                                             ControlState,
    3577             :                                             const ImplControlValue&,
    3578             :                                             const OUString& )
    3579             : {
    3580           0 :     Rectangle       aIndicatorRect;
    3581           0 :     GtkRequisition *pIndicatorSize = NULL;
    3582           0 :     GtkBorder      *pIndicatorSpacing = NULL;
    3583           0 :     gint            width = 13;    // GTK+ default
    3584           0 :     gint            height = 13;    // GTK+ default
    3585           0 :     gint            right = 5;    // GTK+ default
    3586             :     gint            x;
    3587             : 
    3588           0 :     NWEnsureGTKOptionMenu( nScreen );
    3589             : 
    3590           0 :     gtk_widget_style_get( gWidgetData[nScreen].gOptionMenuWidget,
    3591             :             "indicator_size",    &pIndicatorSize,
    3592           0 :             "indicator_spacing",&pIndicatorSpacing, (char *)NULL);
    3593             : 
    3594           0 :     if ( pIndicatorSize )
    3595             :     {
    3596           0 :         width = pIndicatorSize->width;
    3597           0 :         height = pIndicatorSize->height;
    3598             :     }
    3599             : 
    3600           0 :     if ( pIndicatorSpacing )
    3601           0 :         right = pIndicatorSpacing->right;
    3602             : 
    3603           0 :     aIndicatorRect.SetSize( Size( width, height ) );
    3604           0 :     if( Application::GetSettings().GetLayoutRTL() )
    3605           0 :         x = aAreaRect.Left() + right;
    3606             :     else
    3607           0 :         x = aAreaRect.Left() + aAreaRect.GetWidth() - width - right - gWidgetData[nScreen].gOptionMenuWidget->style->xthickness;
    3608           0 :     aIndicatorRect.SetPos( Point( x, aAreaRect.Top() + ((aAreaRect.GetHeight() - height) / 2) ) );
    3609             : 
    3610             :     // If height is odd, move the indicator down 1 pixel
    3611           0 :     if ( aIndicatorRect.GetHeight() % 2 )
    3612           0 :         aIndicatorRect.Move( 0, 1 );
    3613             : 
    3614           0 :     if ( pIndicatorSize )
    3615           0 :         gtk_requisition_free( pIndicatorSize );
    3616           0 :     if ( pIndicatorSpacing )
    3617           0 :         gtk_border_free( pIndicatorSpacing );
    3618             : 
    3619           0 :     return( aIndicatorRect );
    3620             : }
    3621             : 
    3622           0 : static Rectangle NWGetToolbarRect(  SalX11Screen nScreen,
    3623             :                                     ControlType,
    3624             :                                     ControlPart                nPart,
    3625             :                                     Rectangle                aAreaRect,
    3626             :                                     ControlState,
    3627             :                                     const ImplControlValue&,
    3628             :                                     const OUString& )
    3629             : {
    3630           0 :     Rectangle aRet;
    3631             : 
    3632           0 :     if( nPart == PART_DRAW_BACKGROUND_HORZ ||
    3633             :         nPart == PART_DRAW_BACKGROUND_VERT )
    3634           0 :         aRet = aAreaRect;
    3635           0 :     else if( nPart == PART_THUMB_HORZ )
    3636           0 :         aRet = Rectangle( Point( 0, 0 ), Size( aAreaRect.GetWidth(), 10 ) );
    3637           0 :     else if( nPart == PART_THUMB_VERT )
    3638           0 :         aRet = Rectangle( Point( 0, 0 ), Size( 10, aAreaRect.GetHeight() ) );
    3639           0 :     else if( nPart == PART_BUTTON )
    3640             :     {
    3641           0 :         aRet = aAreaRect;
    3642             : 
    3643           0 :         NWEnsureGTKToolbar( nScreen );
    3644             : 
    3645             :         gint nMinWidth =
    3646           0 :             2*gWidgetData[nScreen].gToolbarButtonWidget->style->xthickness
    3647           0 :             + 1 // CHILD_SPACING constant, found in gtk_button.c
    3648           0 :             + 3*gWidgetData[nScreen].gToolbarButtonWidget->style->xthickness; // Murphy factor
    3649             :         gint nMinHeight =
    3650           0 :             2*gWidgetData[nScreen].gToolbarButtonWidget->style->ythickness
    3651           0 :             + 1 // CHILD_SPACING constant, found in gtk_button.c
    3652           0 :             + 3*gWidgetData[nScreen].gToolbarButtonWidget->style->ythickness; // Murphy factor
    3653             : 
    3654           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gToolbarButtonWidget );
    3655           0 :         if( aAreaRect.GetWidth() < nMinWidth )
    3656           0 :             aRet.Right() = aRet.Left() + nMinWidth;
    3657           0 :         if( aAreaRect.GetHeight() < nMinHeight  )
    3658           0 :             aRet.Bottom() = aRet.Top() + nMinHeight;
    3659             :     }
    3660             : 
    3661           0 :     return aRet;
    3662             : }
    3663             : 
    3664             : /************************************************************************
    3665             :  * helper for GtkSalFrame
    3666             :  ************************************************************************/
    3667           0 : static inline Color getColor( const GdkColor& rCol )
    3668             : {
    3669           0 :     return Color( rCol.red >> 8, rCol.green >> 8, rCol.blue >> 8 );
    3670             : }
    3671             : 
    3672             : #if OSL_DEBUG_LEVEL > 1
    3673             : 
    3674             : void printColor( const char* name, const GdkColor& rCol )
    3675             : {
    3676             :     std::fprintf( stderr, "   %s = 0x%2x 0x%2x 0x%2x\n",
    3677             :              name,
    3678             :              rCol.red >> 8, rCol.green >> 8, rCol.blue >> 8 );
    3679             : }
    3680             : 
    3681             : void printStyleColors( GtkStyle* pStyle )
    3682             : {
    3683             :     static const char* pStates[] = { "NORMAL", "ACTIVE", "PRELIGHT", "SELECTED", "INSENSITIVE" };
    3684             : 
    3685             :     for( int i = 0; i < 5; i++ )
    3686             :     {
    3687             :         std::fprintf( stderr, "state %s colors:\n", pStates[i] );
    3688             :         printColor( "bg     ", pStyle->bg[i] );
    3689             :         printColor( "fg     ", pStyle->fg[i] );
    3690             :         printColor( "light  ", pStyle->light[i] );
    3691             :         printColor( "dark   ", pStyle->dark[i] );
    3692             :         printColor( "mid    ", pStyle->mid[i] );
    3693             :         printColor( "text   ", pStyle->text[i] );
    3694             :         printColor( "base   ", pStyle->base[i] );
    3695             :         printColor( "text_aa", pStyle->text_aa[i] );
    3696             :     }
    3697             : }
    3698             : #endif
    3699             : 
    3700           0 : void GtkSalGraphics::signalSettingsNotify( GObject *pSettings, GParamSpec *pSpec, gpointer )
    3701             : {
    3702           0 :     g_return_if_fail( pSpec != NULL );
    3703             : 
    3704           0 :     if( !strcmp( pSpec->name, "gtk-fontconfig-timestamp" ) )
    3705           0 :         GtkSalGraphics::refreshFontconfig( GTK_SETTINGS( pSettings ) );
    3706             : }
    3707             : 
    3708           0 : void GtkSalGraphics::refreshFontconfig( GtkSettings *pSettings )
    3709             : {
    3710           0 :     guint latest_fontconfig_timestamp = 0;
    3711             :     static guint our_fontconfig_timestamp = 0;
    3712           0 :     g_object_get( pSettings, "gtk-fontconfig-timestamp", &latest_fontconfig_timestamp, (char *)NULL );
    3713           0 :     if (latest_fontconfig_timestamp != our_fontconfig_timestamp)
    3714             :     {
    3715           0 :         bool bFirstTime = our_fontconfig_timestamp == 0;
    3716           0 :         our_fontconfig_timestamp = latest_fontconfig_timestamp;
    3717           0 :         if (!bFirstTime)
    3718             :         {
    3719           0 :             psp::PrintFontManager::get().initialize();
    3720             :         }
    3721             :     }
    3722           0 : }
    3723             : 
    3724           0 : void GtkSalGraphics::updateSettings( AllSettings& rSettings )
    3725             : {
    3726           0 :     GdkScreen* pScreen = gtk_widget_get_screen( m_pWindow );
    3727           0 :     gtk_widget_ensure_style( m_pWindow );
    3728           0 :     GtkStyle* pStyle = gtk_widget_get_style( m_pWindow );
    3729           0 :     GtkSettings* pSettings = gtk_widget_get_settings( m_pWindow );
    3730           0 :     StyleSettings aStyleSet = rSettings.GetStyleSettings();
    3731             : 
    3732             :     // Listen for font changes
    3733           0 :     if( !g_object_get_data( G_OBJECT( pSettings ), "libo:listening" ) )
    3734             :     {
    3735           0 :         g_object_set_data( G_OBJECT( pSettings ), "libo:listening",
    3736           0 :                            GUINT_TO_POINTER( 1 ) );
    3737           0 :         g_signal_connect_data( G_OBJECT( pSettings ), "notify",
    3738             :                                G_CALLBACK( signalSettingsNotify ),
    3739           0 :                                NULL, NULL, G_CONNECT_AFTER );
    3740             :     }
    3741             : 
    3742           0 :     refreshFontconfig( pSettings );
    3743             : 
    3744             :     // get the widgets in place
    3745           0 :     NWEnsureGTKMenu( m_nXScreen );
    3746           0 :     NWEnsureGTKMenubar( m_nXScreen );
    3747           0 :     NWEnsureGTKScrollbars( m_nXScreen );
    3748           0 :     NWEnsureGTKEditBox( m_nXScreen );
    3749           0 :     NWEnsureGTKTooltip( m_nXScreen );
    3750           0 :     NWEnsureGTKDialog( m_nXScreen );
    3751           0 :     NWEnsureGTKFrame( m_nXScreen );
    3752             : 
    3753             : #if OSL_DEBUG_LEVEL > 2
    3754             :     printStyleColors( pStyle );
    3755             : #endif
    3756             : 
    3757             :     // text colors
    3758           0 :     Color aTextColor = getColor( pStyle->text[GTK_STATE_NORMAL] );
    3759           0 :     aStyleSet.SetDialogTextColor( aTextColor );
    3760           0 :     aStyleSet.SetWindowTextColor( aTextColor );
    3761           0 :     aStyleSet.SetFieldTextColor( aTextColor );
    3762           0 :     aTextColor = getColor( pStyle->fg[GTK_STATE_NORMAL] );
    3763           0 :     aStyleSet.SetButtonTextColor( aTextColor );
    3764           0 :     aStyleSet.SetRadioCheckTextColor( aTextColor );
    3765           0 :     aStyleSet.SetGroupTextColor( aTextColor );
    3766           0 :     aStyleSet.SetLabelTextColor( aTextColor );
    3767           0 :     aStyleSet.SetInfoTextColor( aTextColor );
    3768             : 
    3769             :     // Tooltip colors
    3770           0 :     GtkStyle* pTooltipStyle = gtk_widget_get_style( gWidgetData[m_nXScreen].gTooltipPopup );
    3771           0 :     aTextColor = getColor( pTooltipStyle->fg[ GTK_STATE_NORMAL ] );
    3772           0 :     aStyleSet.SetHelpTextColor( aTextColor );
    3773             : 
    3774           0 :     DialogStyle aDialogStyle(aStyleSet.GetDialogStyle());
    3775           0 :     gtk_widget_style_get (gWidgetData[m_nXScreen].gDialog,
    3776             :         "content-area-border", &aDialogStyle.content_area_border,
    3777             :         "content-area-spacing", &aDialogStyle.content_area_spacing,
    3778             :         "button-spacing", &aDialogStyle.button_spacing,
    3779             :         "action-area-border", &aDialogStyle.action_area_border,
    3780           0 :         NULL);
    3781           0 :     aStyleSet.SetDialogStyle(aDialogStyle);
    3782             : 
    3783           0 :     FrameStyle aFrameStyle(aStyleSet.GetFrameStyle());
    3784             :     aFrameStyle.left = aFrameStyle.right =
    3785           0 :         gWidgetData[m_nXScreen].gFrame->style->xthickness;
    3786             :     aFrameStyle.top = aFrameStyle.bottom =
    3787           0 :         gWidgetData[m_nXScreen].gFrame->style->ythickness;
    3788           0 :     aStyleSet.SetFrameStyle(aFrameStyle);
    3789             : 
    3790             :     // mouse over text colors
    3791           0 :     aTextColor = getColor( pStyle->fg[ GTK_STATE_PRELIGHT ] );
    3792           0 :     aStyleSet.SetButtonRolloverTextColor( aTextColor );
    3793           0 :     aStyleSet.SetFieldRolloverTextColor( aTextColor );
    3794             : 
    3795             :     // background colors
    3796           0 :     Color aBackColor = getColor( pStyle->bg[GTK_STATE_NORMAL] );
    3797           0 :     Color aBackFieldColor = getColor( pStyle->base[ GTK_STATE_NORMAL ] );
    3798           0 :     aStyleSet.Set3DColors( aBackColor );
    3799           0 :     aStyleSet.SetFaceColor( aBackColor );
    3800           0 :     aStyleSet.SetDialogColor( aBackColor );
    3801           0 :     aStyleSet.SetWorkspaceColor( aBackColor );
    3802           0 :     aStyleSet.SetFieldColor( aBackFieldColor );
    3803           0 :     aStyleSet.SetWindowColor( aBackFieldColor );
    3804           0 :     aStyleSet.SetCheckedColorSpecialCase( );
    3805             : 
    3806             :     // highlighting colors
    3807           0 :     Color aHighlightColor = getColor( pStyle->base[GTK_STATE_SELECTED] );
    3808           0 :     Color aHighlightTextColor = getColor( pStyle->text[GTK_STATE_SELECTED] );
    3809           0 :     aStyleSet.SetHighlightColor( aHighlightColor );
    3810           0 :     aStyleSet.SetHighlightTextColor( aHighlightTextColor );
    3811             : 
    3812           0 :     if( ! gtk_check_version( 2, 10, 0 ) ) // link colors came in with 2.10, avoid an assertion
    3813             :     {
    3814             :         // hyperlink colors
    3815           0 :         GdkColor *link_color = NULL;
    3816           0 :         gtk_widget_style_get (m_pWindow, "link-color", &link_color, NULL);
    3817           0 :         if (link_color)
    3818             :         {
    3819           0 :             aStyleSet.SetLinkColor(getColor(*link_color));
    3820           0 :             gdk_color_free (link_color);
    3821           0 :             link_color = NULL;
    3822             :         }
    3823           0 :         gtk_widget_style_get (m_pWindow, "visited-link-color", &link_color, NULL);
    3824           0 :         if (link_color)
    3825             :         {
    3826           0 :             aStyleSet.SetVisitedLinkColor(getColor(*link_color));
    3827           0 :             gdk_color_free (link_color);
    3828             :         }
    3829             :     }
    3830             : 
    3831             :     // Tab colors
    3832           0 :     aStyleSet.SetActiveTabColor( aBackFieldColor ); // same as the window color.
    3833           0 :     Color aSelectedBackColor = getColor( pStyle->bg[GTK_STATE_ACTIVE] );
    3834           0 :     aStyleSet.SetInactiveTabColor( aSelectedBackColor );
    3835             : 
    3836             :     // menu disabled entries handling
    3837           0 :     aStyleSet.SetSkipDisabledInMenus( true );
    3838           0 :     aStyleSet.SetAcceleratorsInContextMenus( false );
    3839             :     // menu colors
    3840           0 :     GtkStyle* pMenuStyle = gtk_widget_get_style( gWidgetData[m_nXScreen].gMenuWidget );
    3841           0 :     GtkStyle* pMenuItemStyle = gtk_rc_get_style( gWidgetData[m_nXScreen].gMenuItemMenuWidget );
    3842           0 :     GtkStyle* pMenubarStyle = gtk_rc_get_style( gWidgetData[m_nXScreen].gMenubarWidget );
    3843           0 :     GtkStyle* pMenuTextStyle = gtk_rc_get_style( gtk_bin_get_child( GTK_BIN(gWidgetData[m_nXScreen].gMenuItemMenuWidget) ) );
    3844             : 
    3845           0 :     aBackColor = getColor( pMenubarStyle->bg[GTK_STATE_NORMAL] );
    3846           0 :     aStyleSet.SetMenuBarColor( aBackColor );
    3847           0 :     aStyleSet.SetMenuBarRolloverColor( aBackColor );
    3848           0 :     aBackColor = getColor( pMenuStyle->bg[GTK_STATE_NORMAL] );
    3849           0 :     aTextColor = getColor( pMenuTextStyle->fg[GTK_STATE_NORMAL] );
    3850           0 :     aStyleSet.SetMenuColor( aBackColor );
    3851           0 :     aStyleSet.SetMenuTextColor( aTextColor );
    3852             : 
    3853           0 :     aTextColor = aStyleSet.GetPersonaMenuBarTextColor().get_value_or( getColor( pMenubarStyle->fg[GTK_STATE_NORMAL] ) );
    3854           0 :     aStyleSet.SetMenuBarTextColor( aTextColor );
    3855           0 :     aStyleSet.SetMenuBarRolloverTextColor( aTextColor );
    3856             : 
    3857             : #if OSL_DEBUG_LEVEL > 1
    3858             :     std::fprintf( stderr, "==\n" );
    3859             :     std::fprintf( stderr, "MenuColor = %x (%d)\n", (int)aStyleSet.GetMenuColor().GetColor(), aStyleSet.GetMenuColor().GetLuminance() );
    3860             :     std::fprintf( stderr, "MenuTextColor = %x (%d)\n", (int)aStyleSet.GetMenuTextColor().GetColor(), aStyleSet.GetMenuTextColor().GetLuminance() );
    3861             :     std::fprintf( stderr, "MenuBarColor = %x (%d)\n", (int)aStyleSet.GetMenuBarColor().GetColor(), aStyleSet.GetMenuBarColor().GetLuminance() );
    3862             :     std::fprintf( stderr, "MenuBarRolloverColor = %x (%d)\n", (int)aStyleSet.GetMenuBarRolloverColor().GetColor(), aStyleSet.GetMenuBarRolloverColor().GetLuminance() );
    3863             :     std::fprintf( stderr, "MenuBarTextColor = %x (%d)\n", (int)aStyleSet.GetMenuBarTextColor().GetColor(), aStyleSet.GetMenuBarTextColor().GetLuminance() );
    3864             :     std::fprintf( stderr, "MenuBarRolloverTextColor = %x (%d)\n", (int)aStyleSet.GetMenuBarRolloverTextColor().GetColor(), aStyleSet.GetMenuBarRolloverTextColor().GetLuminance() );
    3865             :     std::fprintf( stderr, "LightColor = %x (%d)\n", (int)aStyleSet.GetLightColor().GetColor(), aStyleSet.GetLightColor().GetLuminance() );
    3866             :     std::fprintf( stderr, "ShadowColor = %x (%d)\n", (int)aStyleSet.GetShadowColor().GetColor(), aStyleSet.GetShadowColor().GetLuminance() );
    3867             :     std::fprintf( stderr, "DarkShadowColor = %x (%d)\n", (int)aStyleSet.GetDarkShadowColor().GetColor(), aStyleSet.GetDarkShadowColor().GetLuminance() );
    3868             : #endif
    3869             : 
    3870             :     // Awful hack for menu separators in the Sonar and similar themes.
    3871             :     // If the menu color is not too dark, and the menu text color is lighter,
    3872             :     // make the "light" color lighter than the menu color and the "shadow"
    3873             :     // color darker than it.
    3874           0 :     if ( aStyleSet.GetMenuColor().GetLuminance() >= 32 &&
    3875           0 :      aStyleSet.GetMenuColor().GetLuminance() <= aStyleSet.GetMenuTextColor().GetLuminance() )
    3876             :     {
    3877           0 :       Color temp = aStyleSet.GetMenuColor();
    3878           0 :       temp.IncreaseLuminance( 8 );
    3879           0 :       aStyleSet.SetLightColor( temp );
    3880           0 :       temp = aStyleSet.GetMenuColor();
    3881           0 :       temp.DecreaseLuminance( 16 );
    3882           0 :       aStyleSet.SetShadowColor( temp );
    3883             :     }
    3884             : 
    3885           0 :     aHighlightColor = getColor( pMenuItemStyle->bg[ GTK_STATE_SELECTED ] );
    3886           0 :     aHighlightTextColor = getColor( pMenuTextStyle->fg[ GTK_STATE_PRELIGHT ] );
    3887           0 :     if( aHighlightColor == aHighlightTextColor )
    3888           0 :         aHighlightTextColor = (aHighlightColor.GetLuminance() < 128) ? Color( COL_WHITE ) : Color( COL_BLACK );
    3889           0 :     aStyleSet.SetMenuHighlightColor( aHighlightColor );
    3890           0 :     aStyleSet.SetMenuHighlightTextColor( aHighlightTextColor );
    3891             : 
    3892             :     // UI font
    3893           0 :     OString    aFamily        = pango_font_description_get_family( pStyle->font_desc );
    3894           0 :     int nPangoHeight    = pango_font_description_get_size( pStyle->font_desc );
    3895           0 :     PangoStyle    eStyle    = pango_font_description_get_style( pStyle->font_desc );
    3896           0 :     PangoWeight    eWeight    = pango_font_description_get_weight( pStyle->font_desc );
    3897           0 :     PangoStretch eStretch = pango_font_description_get_stretch( pStyle->font_desc );
    3898             : 
    3899           0 :     psp::FastPrintFontInfo aInfo;
    3900             :     // set family name
    3901           0 :     aInfo.m_aFamilyName = OStringToOUString( aFamily, RTL_TEXTENCODING_UTF8 );
    3902             :     // set italic
    3903           0 :     switch( eStyle )
    3904             :     {
    3905           0 :         case PANGO_STYLE_NORMAL:    aInfo.m_eItalic = ITALIC_NONE;break;
    3906           0 :         case PANGO_STYLE_ITALIC:    aInfo.m_eItalic = ITALIC_NORMAL;break;
    3907           0 :         case PANGO_STYLE_OBLIQUE:    aInfo.m_eItalic = ITALIC_OBLIQUE;break;
    3908             :     }
    3909             :     // set weight
    3910           0 :     if( eWeight <= PANGO_WEIGHT_ULTRALIGHT )
    3911           0 :         aInfo.m_eWeight = WEIGHT_ULTRALIGHT;
    3912           0 :     else if( eWeight <= PANGO_WEIGHT_LIGHT )
    3913           0 :         aInfo.m_eWeight = WEIGHT_LIGHT;
    3914           0 :     else if( eWeight <= PANGO_WEIGHT_NORMAL )
    3915           0 :         aInfo.m_eWeight = WEIGHT_NORMAL;
    3916           0 :     else if( eWeight <= PANGO_WEIGHT_BOLD )
    3917           0 :         aInfo.m_eWeight = WEIGHT_BOLD;
    3918             :     else
    3919           0 :         aInfo.m_eWeight = WEIGHT_ULTRABOLD;
    3920             :     // set width
    3921           0 :     switch( eStretch )
    3922             :     {
    3923           0 :         case PANGO_STRETCH_ULTRA_CONDENSED:    aInfo.m_eWidth = WIDTH_ULTRA_CONDENSED;break;
    3924           0 :         case PANGO_STRETCH_EXTRA_CONDENSED:    aInfo.m_eWidth = WIDTH_EXTRA_CONDENSED;break;
    3925           0 :         case PANGO_STRETCH_CONDENSED:        aInfo.m_eWidth = WIDTH_CONDENSED;break;
    3926           0 :         case PANGO_STRETCH_SEMI_CONDENSED:    aInfo.m_eWidth = WIDTH_SEMI_CONDENSED;break;
    3927           0 :         case PANGO_STRETCH_NORMAL:            aInfo.m_eWidth = WIDTH_NORMAL;break;
    3928           0 :         case PANGO_STRETCH_SEMI_EXPANDED:    aInfo.m_eWidth = WIDTH_SEMI_EXPANDED;break;
    3929           0 :         case PANGO_STRETCH_EXPANDED:        aInfo.m_eWidth = WIDTH_EXPANDED;break;
    3930           0 :         case PANGO_STRETCH_EXTRA_EXPANDED:    aInfo.m_eWidth = WIDTH_EXTRA_EXPANDED;break;
    3931           0 :         case PANGO_STRETCH_ULTRA_EXPANDED:    aInfo.m_eWidth = WIDTH_ULTRA_EXPANDED;break;
    3932             :     }
    3933             : 
    3934             : #if OSL_DEBUG_LEVEL > 1
    3935             :     std::fprintf( stderr, "font name BEFORE system match: \"%s\"\n", aFamily.getStr() );
    3936             : #endif
    3937             : 
    3938             :     // match font to e.g. resolve "Sans"
    3939           0 :     psp::PrintFontManager::get().matchFont( aInfo, rSettings.GetUILanguageTag().getLocale() );
    3940             : 
    3941             : #if OSL_DEBUG_LEVEL > 1
    3942             :     std::fprintf( stderr, "font match %s, name AFTER: \"%s\"\n",
    3943             :              aInfo.m_nID != 0 ? "succeeded" : "failed",
    3944             :              OUStringToOString( aInfo.m_aFamilyName, RTL_TEXTENCODING_ISO_8859_1 ).getStr() );
    3945             : #endif
    3946             : 
    3947           0 :     sal_Int32 nDispDPIY = GetDisplay()->GetResolution().B();
    3948           0 :     int nPointHeight = 0;
    3949             :     static gboolean(*pAbso)(const PangoFontDescription*) =
    3950           0 :         (gboolean(*)(const PangoFontDescription*))osl_getAsciiFunctionSymbol( GetSalData()->m_pPlugin, "pango_font_description_get_size_is_absolute" );
    3951             : 
    3952           0 :     if( pAbso && pAbso( pStyle->font_desc ) )
    3953           0 :         nPointHeight = (nPangoHeight * 72 + nDispDPIY*PANGO_SCALE/2) / (nDispDPIY * PANGO_SCALE);
    3954             :     else
    3955           0 :         nPointHeight = nPangoHeight/PANGO_SCALE;
    3956             : 
    3957           0 :     vcl::Font aFont( aInfo.m_aFamilyName, Size( 0, nPointHeight ) );
    3958           0 :     if( aInfo.m_eWeight != WEIGHT_DONTKNOW )
    3959           0 :         aFont.SetWeight( aInfo.m_eWeight );
    3960           0 :     if( aInfo.m_eWidth != WIDTH_DONTKNOW )
    3961           0 :         aFont.SetWidthType( aInfo.m_eWidth );
    3962           0 :     if( aInfo.m_eItalic != ITALIC_DONTKNOW )
    3963           0 :         aFont.SetItalic( aInfo.m_eItalic );
    3964           0 :     if( aInfo.m_ePitch != PITCH_DONTKNOW )
    3965           0 :         aFont.SetPitch( aInfo.m_ePitch );
    3966             : 
    3967           0 :     aStyleSet.SetAppFont( aFont );
    3968           0 :     aStyleSet.SetHelpFont( aFont );
    3969           0 :     aStyleSet.SetMenuFont( aFont );
    3970           0 :     aStyleSet.SetToolFont( aFont );
    3971           0 :     aStyleSet.SetLabelFont( aFont );
    3972           0 :     aStyleSet.SetInfoFont( aFont );
    3973           0 :     aStyleSet.SetRadioCheckFont( aFont );
    3974           0 :     aStyleSet.SetPushButtonFont( aFont );
    3975           0 :     aStyleSet.SetFieldFont( aFont );
    3976           0 :     aStyleSet.SetIconFont( aFont );
    3977           0 :     aStyleSet.SetGroupFont( aFont );
    3978             : 
    3979           0 :     aFont.SetWeight( WEIGHT_BOLD );
    3980           0 :     aStyleSet.SetTitleFont( aFont );
    3981           0 :     aStyleSet.SetFloatTitleFont( aFont );
    3982             : 
    3983             :     // get cursor blink time
    3984           0 :     gboolean blink = false;
    3985             : 
    3986           0 :     g_object_get( pSettings, "gtk-cursor-blink", &blink, (char *)NULL );
    3987           0 :     if( blink )
    3988             :     {
    3989           0 :         gint blink_time = STYLE_CURSOR_NOBLINKTIME;
    3990           0 :         g_object_get( pSettings, "gtk-cursor-blink-time", &blink_time, (char *)NULL );
    3991             :         // set the blink_time if there is a setting and it is reasonable
    3992             :         // else leave the default value
    3993           0 :         if( blink_time > 100 && blink_time != gint(STYLE_CURSOR_NOBLINKTIME) )
    3994           0 :             aStyleSet.SetCursorBlinkTime( blink_time/2 );
    3995             :     }
    3996             :     else
    3997           0 :         aStyleSet.SetCursorBlinkTime( STYLE_CURSOR_NOBLINKTIME );
    3998             : 
    3999           0 :     MouseSettings aMouseSettings = rSettings.GetMouseSettings();
    4000             :     int iDoubleClickTime, iDoubleClickDistance, iDragThreshold, iMenuPopupDelay;
    4001             :     g_object_get( pSettings,
    4002             :                   "gtk-double-click-time", &iDoubleClickTime,
    4003             :                   "gtk-double-click-distance", &iDoubleClickDistance,
    4004             :                   "gtk-dnd-drag-threshold", &iDragThreshold,
    4005             :                   "gtk-menu-popup-delay", &iMenuPopupDelay,
    4006           0 :                   (char *)NULL );
    4007           0 :     aMouseSettings.SetDoubleClickTime( iDoubleClickTime );
    4008           0 :     aMouseSettings.SetDoubleClickWidth( iDoubleClickDistance );
    4009           0 :     aMouseSettings.SetDoubleClickHeight( iDoubleClickDistance );
    4010           0 :     aMouseSettings.SetStartDragWidth( iDragThreshold );
    4011           0 :     aMouseSettings.SetStartDragHeight( iDragThreshold );
    4012           0 :     aMouseSettings.SetMenuDelay( iMenuPopupDelay );
    4013           0 :     rSettings.SetMouseSettings( aMouseSettings );
    4014             : 
    4015           0 :     gboolean showmenuicons = true, primarybuttonwarps = false;
    4016             :     g_object_get( pSettings,
    4017             :         "gtk-menu-images", &showmenuicons,
    4018           0 :         (char *)NULL );
    4019           0 :     if( g_object_class_find_property(
    4020           0 :             G_OBJECT_GET_CLASS(pSettings), "gtk-primary-button-warps-slider") )
    4021             :     {
    4022             :         g_object_get( pSettings,
    4023             :             "gtk-primary-button-warps-slider", &primarybuttonwarps,
    4024           0 :             (char *)NULL );
    4025             :     }
    4026           0 :     aStyleSet.SetPreferredUseImagesInMenus(showmenuicons);
    4027           0 :     aStyleSet.SetPrimaryButtonWarpsSlider(primarybuttonwarps);
    4028             : 
    4029             :     // set scrollbar settings
    4030           0 :     gint slider_width = 14;
    4031           0 :     gint trough_border = 1;
    4032           0 :     gint min_slider_length = 21;
    4033             : 
    4034             :     // Grab some button style attributes
    4035           0 :     gtk_widget_style_get( gWidgetData[m_nXScreen].gScrollHorizWidget,
    4036             :                           "slider-width", &slider_width,
    4037             :                           "trough-border", &trough_border,
    4038             :                           "min-slider-length", &min_slider_length,
    4039           0 :                           (char *)NULL );
    4040           0 :     gint magic = trough_border ? 1 : 0;
    4041           0 :     aStyleSet.SetScrollBarSize( slider_width + 2*trough_border );
    4042           0 :     aStyleSet.SetMinThumbSize( min_slider_length - magic );
    4043             : 
    4044             :     // preferred icon style
    4045           0 :     gchar* pIconThemeName = NULL;
    4046           0 :     g_object_get( pSettings, "gtk-icon-theme-name", &pIconThemeName, (char *)NULL );
    4047           0 :     aStyleSet.SetPreferredIconTheme( OUString::createFromAscii( pIconThemeName ) );
    4048           0 :     g_free( pIconThemeName );
    4049             : 
    4050           0 :     aStyleSet.SetToolbarIconSize( STYLE_TOOLBAR_ICONSIZE_LARGE );
    4051             : 
    4052             : #if !GTK_CHECK_VERSION(2,9,0)
    4053             :     static cairo_font_options_t* (*gdk_screen_get_font_options)(GdkScreen*) =
    4054             :         (cairo_font_options_t*(*)(GdkScreen*))osl_getAsciiFunctionSymbol( GetSalData()->m_pPlugin, "gdk_screen_get_font_options" );
    4055             :     if( gdk_screen_get_font_options != NULL )
    4056             :     {
    4057             :         const cairo_font_options_t* pNewOptions = gdk_screen_get_font_options( pScreen );
    4058             :         aStyleSet.SetCairoFontOptions( pNewOptions );
    4059             :     }
    4060             : #else
    4061           0 :     const cairo_font_options_t* pNewOptions = gdk_screen_get_font_options( pScreen );
    4062           0 :     aStyleSet.SetCairoFontOptions( pNewOptions );
    4063             : #endif
    4064             : 
    4065             :     // finally update the collected settings
    4066           0 :     rSettings.SetStyleSettings( aStyleSet );
    4067           0 : }
    4068             : 
    4069             : /************************************************************************
    4070             :  * Create a GdkPixmap filled with the contents of an area of an Xlib window
    4071             :  ************************************************************************/
    4072             : 
    4073           0 : GdkPixmap* GtkSalGraphics::NWGetPixmapFromScreen( Rectangle srcRect )
    4074             : {
    4075             :     // Create a new pixmap to hold the composite of the window background and the control
    4076           0 :     GdkPixmap * pPixmap        = gdk_pixmap_new( GDK_DRAWABLE(GetGdkWindow()), srcRect.GetWidth(), srcRect.GetHeight(), -1 );
    4077           0 :     GdkGC *     pPixmapGC      = gdk_gc_new( pPixmap );
    4078             : 
    4079           0 :     if( !pPixmap || !pPixmapGC )
    4080             :     {
    4081           0 :         if ( pPixmap )
    4082           0 :             g_object_unref( pPixmap );
    4083           0 :         if ( pPixmapGC )
    4084           0 :             g_object_unref( pPixmapGC );
    4085           0 :         std::fprintf( stderr, "salnativewidgets-gtk.cxx: could not get valid pixmap from screen\n" );
    4086           0 :         return( NULL );
    4087             :     }
    4088             : 
    4089             :     // Copy the background of the screen into a composite pixmap
    4090             :     CopyScreenArea( GetXDisplay(),
    4091           0 :                     GetDrawable(), GetScreenNumber(), GetVisual().GetDepth(),
    4092             :                     gdk_x11_drawable_get_xid(pPixmap),
    4093           0 :                     SalX11Screen( gdk_screen_get_number( gdk_drawable_get_screen( GDK_DRAWABLE(pPixmap) ) ) ),
    4094           0 :                     gdk_drawable_get_depth( GDK_DRAWABLE( pPixmap ) ),
    4095             :                     gdk_x11_gc_get_xgc(pPixmapGC),
    4096           0 :                     srcRect.Left(), srcRect.Top(), srcRect.GetWidth(), srcRect.GetHeight(), 0, 0 );
    4097             : 
    4098           0 :     g_object_unref( pPixmapGC );
    4099           0 :     return( pPixmap );
    4100             : }
    4101             : 
    4102             : /************************************************************************
    4103             :  * Copy an alpha pixmap to screen using a gc with clipping
    4104             :  ************************************************************************/
    4105             : 
    4106           0 : bool GtkSalGraphics::NWRenderPixmapToScreen( GdkPixmap* pPixmap, Rectangle dstRect )
    4107             : {
    4108             :     // The GC can't be null, otherwise we'd have no clip region
    4109           0 :     GC aFontGC = GetFontGC();
    4110           0 :     if( aFontGC == NULL )
    4111             :     {
    4112           0 :         std::fprintf(stderr, "salnativewidgets.cxx: no valid GC\n" );
    4113           0 :         return false;
    4114             :     }
    4115             : 
    4116           0 :     if ( !pPixmap )
    4117           0 :         return false;
    4118             : 
    4119             :     // Copy the background of the screen into a composite pixmap
    4120             :     CopyScreenArea( GetXDisplay(),
    4121             :                     GDK_DRAWABLE_XID(pPixmap),
    4122           0 :                     SalX11Screen( gdk_screen_get_number( gdk_drawable_get_screen( GDK_DRAWABLE(pPixmap) ) ) ),
    4123           0 :                     gdk_drawable_get_depth( GDK_DRAWABLE(pPixmap) ),
    4124           0 :                     GetDrawable(), m_nXScreen, GetVisual().GetDepth(),
    4125             :                     aFontGC,
    4126           0 :                     0, 0, dstRect.GetWidth(), dstRect.GetHeight(), dstRect.Left(), dstRect.Top() );
    4127             : 
    4128           0 :     return true;
    4129             : }
    4130             : 
    4131             : /************************************************************************
    4132             :  * State conversion
    4133             :  ************************************************************************/
    4134           0 : static void NWConvertVCLStateToGTKState( ControlState nVCLState,
    4135             :             GtkStateType* nGTKState, GtkShadowType* nGTKShadow )
    4136             : {
    4137           0 :     *nGTKShadow = GTK_SHADOW_OUT;
    4138           0 :     *nGTKState = GTK_STATE_INSENSITIVE;
    4139             : 
    4140           0 :     if ( nVCLState & CTRL_STATE_ENABLED )
    4141             :     {
    4142           0 :         if ( nVCLState & CTRL_STATE_PRESSED )
    4143             :         {
    4144           0 :             *nGTKState = GTK_STATE_ACTIVE;
    4145           0 :             *nGTKShadow = GTK_SHADOW_IN;
    4146             :         }
    4147           0 :         else if ( nVCLState & CTRL_STATE_ROLLOVER )
    4148             :         {
    4149           0 :             *nGTKState = GTK_STATE_PRELIGHT;
    4150           0 :             *nGTKShadow = GTK_SHADOW_OUT;
    4151             :         }
    4152             :         else
    4153             :         {
    4154           0 :             *nGTKState = GTK_STATE_NORMAL;
    4155           0 :             *nGTKShadow = GTK_SHADOW_OUT;
    4156             :         }
    4157             :     }
    4158           0 : }
    4159             : 
    4160             : /************************************************************************
    4161             :  * Set widget flags
    4162             :  ************************************************************************/
    4163           0 : static void NWSetWidgetState( GtkWidget* widget, ControlState nState, GtkStateType nGtkState )
    4164             : {
    4165             :     // Set to default state, then build up from there
    4166           0 :     GTK_WIDGET_UNSET_FLAGS( widget, GTK_HAS_DEFAULT );
    4167           0 :     GTK_WIDGET_UNSET_FLAGS( widget, GTK_HAS_FOCUS );
    4168           0 :     GTK_WIDGET_UNSET_FLAGS( widget, GTK_SENSITIVE );
    4169           0 :     GTK_WIDGET_SET_FLAGS( widget, gWidgetDefaultFlags[reinterpret_cast<long>(widget)] );
    4170             : 
    4171           0 :     if ( nState & CTRL_STATE_DEFAULT )
    4172           0 :         GTK_WIDGET_SET_FLAGS( widget, GTK_HAS_DEFAULT );
    4173           0 :     if ( !GTK_IS_TOGGLE_BUTTON(widget) && (nState & CTRL_STATE_FOCUSED) )
    4174           0 :         GTK_WIDGET_SET_FLAGS( widget, GTK_HAS_FOCUS );
    4175           0 :     if ( nState & CTRL_STATE_ENABLED )
    4176           0 :         GTK_WIDGET_SET_FLAGS( widget, GTK_SENSITIVE );
    4177           0 :     gtk_widget_set_state( widget, nGtkState );
    4178           0 : }
    4179             : 
    4180             : /************************************************************************
    4181             :  * Widget ensure functions - make sure cached objects are valid
    4182             :  ************************************************************************/
    4183             : 
    4184           0 : static void NWAddWidgetToCacheWindow( GtkWidget* widget, SalX11Screen nScreen )
    4185             : {
    4186           0 :     NWFWidgetData& rData = gWidgetData[nScreen];
    4187           0 :     if ( !rData.gCacheWindow || !rData.gDumbContainer )
    4188             :     {
    4189           0 :         if ( !rData.gCacheWindow )
    4190             :         {
    4191           0 :             rData.gCacheWindow = gtk_window_new( GTK_WINDOW_TOPLEVEL );
    4192           0 :             g_object_set_data( G_OBJECT( rData.gCacheWindow ), "libo-version",
    4193           0 :                                (gpointer)LIBO_VERSION_DOTTED );
    4194             : 
    4195             :             GdkScreen* pScreen = gdk_display_get_screen( gdk_display_get_default(),
    4196           0 :                                                          nScreen.getXScreen() );
    4197           0 :             if( pScreen )
    4198           0 :                 gtk_window_set_screen( GTK_WINDOW(rData.gCacheWindow), pScreen );
    4199             :         }
    4200           0 :         if ( !rData.gDumbContainer )
    4201           0 :             rData.gDumbContainer = gtk_fixed_new();
    4202           0 :         gtk_container_add( GTK_CONTAINER(rData.gCacheWindow), rData.gDumbContainer );
    4203           0 :         gtk_widget_realize( rData.gDumbContainer );
    4204           0 :         gtk_widget_realize( rData.gCacheWindow );
    4205             :     }
    4206             : 
    4207           0 :     gtk_container_add( GTK_CONTAINER(rData.gDumbContainer), widget );
    4208           0 :     gtk_widget_realize( widget );
    4209           0 :     gtk_widget_ensure_style( widget );
    4210             : 
    4211             :     // Store widget's default flags
    4212           0 :     gWidgetDefaultFlags[ reinterpret_cast<long>(widget) ] = GTK_WIDGET_FLAGS( widget );
    4213           0 : }
    4214             : 
    4215           0 : static void NWEnsureGTKButton( SalX11Screen nScreen )
    4216             : {
    4217           0 :     if ( !gWidgetData[nScreen].gBtnWidget )
    4218             :     {
    4219           0 :         gWidgetData[nScreen].gBtnWidget = gtk_button_new_with_label( "" );
    4220           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gBtnWidget, nScreen );
    4221             :     }
    4222           0 : }
    4223             : 
    4224           0 : static void NWEnsureGTKRadio( SalX11Screen nScreen )
    4225             : {
    4226           0 :     if ( !gWidgetData[nScreen].gRadioWidget || !gWidgetData[nScreen].gRadioWidgetSibling )
    4227             :     {
    4228           0 :         gWidgetData[nScreen].gRadioWidget = gtk_radio_button_new( NULL );
    4229           0 :         gWidgetData[nScreen].gRadioWidgetSibling = gtk_radio_button_new_from_widget( GTK_RADIO_BUTTON(gWidgetData[nScreen].gRadioWidget) );
    4230           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gRadioWidget, nScreen );
    4231           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gRadioWidgetSibling, nScreen );
    4232             :     }
    4233           0 : }
    4234             : 
    4235           0 : static void NWEnsureGTKCheck( SalX11Screen nScreen )
    4236             : {
    4237           0 :     if ( !gWidgetData[nScreen].gCheckWidget )
    4238             :     {
    4239           0 :         gWidgetData[nScreen].gCheckWidget = gtk_check_button_new();
    4240           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gCheckWidget, nScreen );
    4241             :     }
    4242           0 : }
    4243             : 
    4244           0 : static void NWEnsureGTKScrollbars( SalX11Screen nScreen )
    4245             : {
    4246           0 :     if ( !gWidgetData[nScreen].gScrollHorizWidget )
    4247             :     {
    4248           0 :         gWidgetData[nScreen].gScrollHorizWidget = gtk_hscrollbar_new( NULL );
    4249           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gScrollHorizWidget, nScreen );
    4250             :     }
    4251             : 
    4252           0 :     if ( !gWidgetData[nScreen].gScrollVertWidget )
    4253             :     {
    4254           0 :         gWidgetData[nScreen].gScrollVertWidget = gtk_vscrollbar_new( NULL );
    4255           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gScrollVertWidget, nScreen );
    4256             :     }
    4257           0 : }
    4258             : 
    4259           0 : static void NWEnsureGTKArrow( SalX11Screen nScreen )
    4260             : {
    4261           0 :     if ( !gWidgetData[nScreen].gArrowWidget || !gWidgetData[nScreen].gDropdownWidget )
    4262             :     {
    4263           0 :         gWidgetData[nScreen].gDropdownWidget = gtk_toggle_button_new();
    4264           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gDropdownWidget, nScreen );
    4265           0 :         gWidgetData[nScreen].gArrowWidget = gtk_arrow_new( GTK_ARROW_DOWN, GTK_SHADOW_OUT );
    4266           0 :         gtk_container_add( GTK_CONTAINER(gWidgetData[nScreen].gDropdownWidget), gWidgetData[nScreen].gArrowWidget );
    4267           0 :         gtk_widget_set_rc_style( gWidgetData[nScreen].gArrowWidget );
    4268           0 :         gtk_widget_realize( gWidgetData[nScreen].gArrowWidget );
    4269             :     }
    4270           0 : }
    4271             : 
    4272           0 : static void NWEnsureGTKEditBox( SalX11Screen nScreen )
    4273             : {
    4274           0 :     if ( !gWidgetData[nScreen].gEditBoxWidget )
    4275             :     {
    4276           0 :         gWidgetData[nScreen].gEditBoxWidget = gtk_entry_new();
    4277           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gEditBoxWidget, nScreen );
    4278             :     }
    4279           0 : }
    4280             : 
    4281           0 : static void NWEnsureGTKSpinButton( SalX11Screen nScreen )
    4282             : {
    4283           0 :     if ( !gWidgetData[nScreen].gSpinButtonWidget )
    4284             :     {
    4285           0 :         GtkAdjustment *adj = GTK_ADJUSTMENT( gtk_adjustment_new(0, 0, 1, 1, 1, 0) );
    4286           0 :         gWidgetData[nScreen].gSpinButtonWidget = gtk_spin_button_new( adj, 1, 2 );
    4287             : 
    4288             :         //Setting non-editable means it doesn't blink, so there's no timeouts
    4289             :         //running around to nobble us
    4290           0 :         gtk_editable_set_editable(GTK_EDITABLE(gWidgetData[nScreen].gSpinButtonWidget), false);
    4291             : 
    4292           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gSpinButtonWidget, nScreen );
    4293             :     }
    4294           0 : }
    4295             : 
    4296           0 : static void NWEnsureGTKNotebook( SalX11Screen nScreen )
    4297             : {
    4298           0 :     if ( !gWidgetData[nScreen].gNotebookWidget )
    4299             :     {
    4300           0 :         gWidgetData[nScreen].gNotebookWidget = gtk_notebook_new();
    4301           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gNotebookWidget, nScreen );
    4302             :     }
    4303           0 : }
    4304             : 
    4305           0 : static void NWEnsureGTKOptionMenu( SalX11Screen nScreen )
    4306             : {
    4307           0 :     if ( !gWidgetData[nScreen].gOptionMenuWidget )
    4308             :     {
    4309           0 :         gWidgetData[nScreen].gOptionMenuWidget = gtk_option_menu_new();
    4310           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gOptionMenuWidget, nScreen );
    4311             :     }
    4312           0 : }
    4313             : 
    4314           0 : static void NWEnsureGTKCombo( SalX11Screen nScreen )
    4315             : {
    4316           0 :     if ( !gWidgetData[nScreen].gComboWidget )
    4317             :     {
    4318           0 :         gWidgetData[nScreen].gComboWidget = gtk_combo_new();
    4319             : 
    4320             :         // #i59129# Setting non-editable means it doesn't blink, so
    4321             :         // there are no timeouts running around to nobble us
    4322           0 :         gtk_editable_set_editable(GTK_EDITABLE(GTK_COMBO(gWidgetData[nScreen].gComboWidget)->entry), false);
    4323             : 
    4324           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gComboWidget, nScreen );
    4325             :         // Must realize the ComboBox's children, since GTK
    4326             :         // does not do this for us in GtkCombo::gtk_widget_realize()
    4327           0 :         gtk_widget_realize( GTK_COMBO(gWidgetData[nScreen].gComboWidget)->button );
    4328           0 :         gtk_widget_realize( GTK_COMBO(gWidgetData[nScreen].gComboWidget)->entry );
    4329             :     }
    4330           0 : }
    4331             : 
    4332           0 : static void NWEnsureGTKScrolledWindow( SalX11Screen nScreen )
    4333             : {
    4334           0 :     if ( !gWidgetData[nScreen].gScrolledWindowWidget )
    4335             :     {
    4336           0 :         GtkAdjustment *hadj = GTK_ADJUSTMENT( gtk_adjustment_new(0, 0, 0, 0, 0, 0) );
    4337           0 :         GtkAdjustment *vadj = GTK_ADJUSTMENT( gtk_adjustment_new(0, 0, 0, 0, 0, 0) );
    4338             : 
    4339           0 :         gWidgetData[nScreen].gScrolledWindowWidget = gtk_scrolled_window_new( hadj, vadj );
    4340           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gScrolledWindowWidget, nScreen );
    4341             :     }
    4342           0 : }
    4343             : 
    4344           0 : static void NWEnsureGTKToolbar( SalX11Screen nScreen )
    4345             : {
    4346           0 :     if( !gWidgetData[nScreen].gToolbarWidget )
    4347             :     {
    4348           0 :         gWidgetData[nScreen].gToolbarWidget = gtk_toolbar_new();
    4349           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gToolbarWidget, nScreen );
    4350           0 :         gWidgetData[nScreen].gToolbarButtonWidget = GTK_WIDGET(gtk_toggle_button_new());
    4351           0 :         gWidgetData[nScreen].gSeparator = GTK_WIDGET(gtk_separator_tool_item_new());
    4352           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gSeparator, nScreen );
    4353             : 
    4354           0 :         GtkReliefStyle aRelief = GTK_RELIEF_NORMAL;
    4355           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gToolbarWidget );
    4356           0 :         gtk_widget_style_get( gWidgetData[nScreen].gToolbarWidget,
    4357             :                               "button_relief", &aRelief,
    4358           0 :                               (char *)NULL);
    4359             : 
    4360           0 :         gtk_button_set_relief( GTK_BUTTON(gWidgetData[nScreen].gToolbarButtonWidget), aRelief );
    4361           0 :         GTK_WIDGET_UNSET_FLAGS( gWidgetData[nScreen].gToolbarButtonWidget, GTK_CAN_FOCUS );
    4362           0 :         GTK_WIDGET_UNSET_FLAGS( gWidgetData[nScreen].gToolbarButtonWidget, GTK_CAN_DEFAULT );
    4363           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gToolbarButtonWidget, nScreen );
    4364             : 
    4365             :     }
    4366           0 :     if( ! gWidgetData[nScreen].gHandleBoxWidget )
    4367             :     {
    4368           0 :         gWidgetData[nScreen].gHandleBoxWidget = gtk_handle_box_new();
    4369           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gHandleBoxWidget, nScreen );
    4370             :     }
    4371           0 : }
    4372             : 
    4373           0 : static void NWEnsureGTKMenubar( SalX11Screen nScreen )
    4374             : {
    4375           0 :     if( !gWidgetData[nScreen].gMenubarWidget )
    4376             :     {
    4377           0 :         gWidgetData[nScreen].gMenubarWidget = gtk_menu_bar_new();
    4378           0 :         gWidgetData[nScreen].gMenuItemMenubarWidget = gtk_menu_item_new_with_label( "b" );
    4379           0 :         gtk_menu_shell_append( GTK_MENU_SHELL( gWidgetData[nScreen].gMenubarWidget ), gWidgetData[nScreen].gMenuItemMenubarWidget );
    4380           0 :         gtk_widget_show( gWidgetData[nScreen].gMenuItemMenubarWidget );
    4381           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gMenubarWidget, nScreen );
    4382           0 :         gtk_widget_show( gWidgetData[nScreen].gMenubarWidget );
    4383             : 
    4384             :         // do what NWAddWidgetToCacheWindow does except adding to def container
    4385           0 :         gtk_widget_realize( gWidgetData[nScreen].gMenuItemMenubarWidget );
    4386           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gMenuItemMenubarWidget );
    4387             : 
    4388           0 :         gWidgetDefaultFlags[ reinterpret_cast<long>(gWidgetData[nScreen].gMenuItemMenubarWidget) ] = GTK_WIDGET_FLAGS( gWidgetData[nScreen].gMenuItemMenubarWidget );
    4389             :     }
    4390           0 : }
    4391             : 
    4392           0 : static void NWEnsureGTKMenu( SalX11Screen nScreen )
    4393             : {
    4394           0 :     if( !gWidgetData[nScreen].gMenuWidget )
    4395             :     {
    4396           0 :         gWidgetData[nScreen].gMenuWidget                  = gtk_menu_new();
    4397           0 :         gWidgetData[nScreen].gMenuItemMenuWidget          = gtk_menu_item_new_with_label( "b" );
    4398           0 :         gWidgetData[nScreen].gMenuItemCheckMenuWidget     = gtk_check_menu_item_new_with_label( "b" );
    4399           0 :         gWidgetData[nScreen].gMenuItemRadioMenuWidget     = gtk_radio_menu_item_new_with_label( NULL, "b" );
    4400           0 :         gWidgetData[nScreen].gMenuItemSeparatorMenuWidget = gtk_menu_item_new();
    4401           0 :         gWidgetData[nScreen].gImageMenuItem               = gtk_image_menu_item_new();
    4402             : 
    4403           0 :         g_object_ref_sink (gWidgetData[nScreen].gMenuWidget);
    4404             : 
    4405           0 :         gtk_menu_shell_append( GTK_MENU_SHELL( gWidgetData[nScreen].gMenuWidget ), gWidgetData[nScreen].gMenuItemMenuWidget );
    4406           0 :         gtk_menu_shell_append( GTK_MENU_SHELL( gWidgetData[nScreen].gMenuWidget ), gWidgetData[nScreen].gMenuItemCheckMenuWidget );
    4407           0 :         gtk_menu_shell_append( GTK_MENU_SHELL( gWidgetData[nScreen].gMenuWidget ), gWidgetData[nScreen].gMenuItemRadioMenuWidget );
    4408           0 :         gtk_menu_shell_append( GTK_MENU_SHELL( gWidgetData[nScreen].gMenuWidget ), gWidgetData[nScreen].gMenuItemSeparatorMenuWidget );
    4409           0 :         gtk_menu_shell_append( GTK_MENU_SHELL( gWidgetData[nScreen].gMenuWidget ), gWidgetData[nScreen].gImageMenuItem );
    4410             : 
    4411             :         // do what NWAddWidgetToCacheWindow does except adding to def container
    4412           0 :         gtk_widget_realize( gWidgetData[nScreen].gMenuWidget );
    4413           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gMenuWidget );
    4414             : 
    4415           0 :         gtk_widget_realize( gWidgetData[nScreen].gMenuItemMenuWidget );
    4416           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gMenuItemMenuWidget );
    4417             : 
    4418           0 :         gtk_widget_realize( gWidgetData[nScreen].gMenuItemCheckMenuWidget );
    4419           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gMenuItemCheckMenuWidget );
    4420             : 
    4421           0 :         gtk_widget_realize( gWidgetData[nScreen].gMenuItemRadioMenuWidget );
    4422           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gMenuItemRadioMenuWidget );
    4423             : 
    4424           0 :         gtk_widget_realize( gWidgetData[nScreen].gMenuItemSeparatorMenuWidget );
    4425           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gMenuItemSeparatorMenuWidget );
    4426             : 
    4427           0 :         gtk_widget_realize( gWidgetData[nScreen].gImageMenuItem );
    4428           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gImageMenuItem );
    4429             : 
    4430           0 :         gWidgetDefaultFlags[ reinterpret_cast<long>(gWidgetData[nScreen].gMenuWidget) ] = GTK_WIDGET_FLAGS( gWidgetData[nScreen].gMenuWidget );
    4431           0 :         gWidgetDefaultFlags[ reinterpret_cast<long>(gWidgetData[nScreen].gMenuItemMenuWidget) ] = GTK_WIDGET_FLAGS( gWidgetData[nScreen].gMenuItemMenuWidget );
    4432           0 :         gWidgetDefaultFlags[ reinterpret_cast<long>(gWidgetData[nScreen].gMenuItemCheckMenuWidget) ] = GTK_WIDGET_FLAGS( gWidgetData[nScreen].gMenuItemCheckMenuWidget );
    4433           0 :         gWidgetDefaultFlags[ reinterpret_cast<long>(gWidgetData[nScreen].gMenuItemRadioMenuWidget) ] = GTK_WIDGET_FLAGS( gWidgetData[nScreen].gMenuItemRadioMenuWidget );
    4434           0 :         gWidgetDefaultFlags[ reinterpret_cast<long>(gWidgetData[nScreen].gMenuItemSeparatorMenuWidget) ] = GTK_WIDGET_FLAGS( gWidgetData[nScreen].gMenuItemSeparatorMenuWidget );
    4435           0 :         gWidgetDefaultFlags[ reinterpret_cast<long>(gWidgetData[nScreen].gImageMenuItem) ] = GTK_WIDGET_FLAGS( gWidgetData[nScreen].gImageMenuItem );
    4436             :     }
    4437           0 : }
    4438             : 
    4439           0 : static void NWEnsureGTKTooltip( SalX11Screen nScreen )
    4440             : {
    4441           0 :     if( !gWidgetData[nScreen].gTooltipPopup )
    4442             :     {
    4443           0 :         gWidgetData[nScreen].gTooltipPopup = gtk_window_new (GTK_WINDOW_POPUP);
    4444             :         GdkScreen* pScreen = gdk_display_get_screen( gdk_display_get_default(),
    4445           0 :                                                      nScreen.getXScreen() );
    4446           0 :         if( pScreen )
    4447           0 :             gtk_window_set_screen( GTK_WINDOW(gWidgetData[nScreen].gTooltipPopup), pScreen );
    4448           0 :         gtk_widget_set_name( gWidgetData[nScreen].gTooltipPopup, "gtk-tooltips");
    4449           0 :         gtk_widget_realize( gWidgetData[nScreen].gTooltipPopup );
    4450           0 :         gtk_widget_ensure_style( gWidgetData[nScreen].gTooltipPopup );
    4451             :     }
    4452           0 : }
    4453             : 
    4454           0 : static void NWEnsureGTKDialog( SalX11Screen nScreen )
    4455             : {
    4456           0 :     if( !gWidgetData[nScreen].gDialog )
    4457             :     {
    4458           0 :         gWidgetData[nScreen].gDialog = gtk_dialog_new();
    4459             :         GdkScreen* pScreen = gdk_display_get_screen( gdk_display_get_default(),
    4460           0 :                                                      nScreen.getXScreen() );
    4461           0 :         if( pScreen )
    4462           0 :             gtk_window_set_screen( GTK_WINDOW(gWidgetData[nScreen].gDialog), pScreen );
    4463           0 :         gtk_widget_realize(gWidgetData[nScreen].gDialog);
    4464           0 :         gtk_widget_ensure_style(gWidgetData[nScreen].gDialog);
    4465             :     }
    4466           0 : }
    4467             : 
    4468           0 : static void NWEnsureGTKFrame( SalX11Screen nScreen )
    4469             : {
    4470           0 :     if( !gWidgetData[nScreen].gFrame )
    4471             :     {
    4472           0 :         gWidgetData[nScreen].gFrame = gtk_frame_new(NULL);
    4473           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gFrame, nScreen );
    4474             :     }
    4475           0 : }
    4476             : 
    4477           0 : static void NWEnsureGTKProgressBar( SalX11Screen nScreen )
    4478             : {
    4479           0 :     if( !gWidgetData[nScreen].gProgressBar )
    4480             :     {
    4481           0 :         gWidgetData[nScreen].gProgressBar = gtk_progress_bar_new ();
    4482           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gProgressBar, nScreen );
    4483             :     }
    4484           0 : }
    4485             : 
    4486           0 : static void NWEnsureGTKTreeView( SalX11Screen nScreen )
    4487             : {
    4488           0 :     if( !gWidgetData[nScreen].gTreeView )
    4489             :     {
    4490           0 :         gWidgetData[nScreen].gTreeView = gtk_tree_view_new ();
    4491             : 
    4492             :         // Columns will be used for tree header rendering
    4493           0 :         GtkCellRenderer* renderer=gtk_cell_renderer_text_new();
    4494           0 :         GtkTreeViewColumn* column=gtk_tree_view_column_new_with_attributes("",renderer,"text",0,NULL);
    4495           0 :         gtk_tree_view_column_set_widget(column,gtk_label_new(""));
    4496           0 :         gtk_tree_view_append_column(GTK_TREE_VIEW(gWidgetData[nScreen].gTreeView), column);
    4497             : 
    4498             :         // Add one more column so that some engines like clearlooks did render separators between columns
    4499           0 :         column=gtk_tree_view_column_new_with_attributes("",renderer,"text",0,NULL);
    4500           0 :         gtk_tree_view_append_column(GTK_TREE_VIEW(gWidgetData[nScreen].gTreeView), column);
    4501             : 
    4502           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gTreeView, nScreen );
    4503             :     }
    4504           0 : }
    4505             : 
    4506           0 : static void NWEnsureGTKSlider( SalX11Screen nScreen )
    4507             : {
    4508           0 :     if( !gWidgetData[nScreen].gHScale )
    4509             :     {
    4510           0 :         gWidgetData[nScreen].gHScale = gtk_hscale_new_with_range(0, 10, 1);
    4511           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gHScale, nScreen );
    4512             :     }
    4513           0 :     if( !gWidgetData[nScreen].gVScale )
    4514             :     {
    4515           0 :         gWidgetData[nScreen].gVScale = gtk_vscale_new_with_range(0, 10, 1);
    4516           0 :         NWAddWidgetToCacheWindow( gWidgetData[nScreen].gVScale, nScreen );
    4517             :     }
    4518           0 : }
    4519             : 
    4520             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.10