FileDocCategorySizeDatePackage
GTKPainter.javaAPI DocJava SE 6 API58528Tue Jun 10 00:21:56 BST 2008com.sun.java.swing.plaf.gtk

GTKPainter

public class GTKPainter extends SynthPainter
version
1.84, 03/15/07
author
Joshua Outwater
author
Scott Violet

Fields Summary
private static final com.sun.java.swing.plaf.gtk.GTKConstants.PositionType[]
POSITIONS
private static final com.sun.java.swing.plaf.gtk.GTKConstants.ShadowType[]
SHADOWS
private static final GTKEngine
ENGINE
static final GTKPainter
INSTANCE
Constructors Summary
private GTKPainter()


      
    
Methods Summary
private voidfillArea(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h, javax.swing.plaf.synth.ColorType colorType)

        if (context.getComponent().isOpaque()) {
            Region id = context.getRegion();
            int gtkState = GTKLookAndFeel.synthStateToGTKState(id,
                    context.getComponentState());
            GTKStyle style = (GTKStyle)context.getStyle();
            
            g.setColor(style.getGTKColor(context, gtkState, colorType));
            g.fillRect(x, y, w, h);
        }
    
private java.lang.StringgetName(javax.swing.plaf.synth.SynthContext context)

        return (context.getRegion().isSubregion()) ? null :
               context.getComponent().getName();
    
public voidpaintArrowButtonBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        AbstractButton button = (AbstractButton)context.getComponent();

        String name = button.getName();
        String detail = "button";
        int direction = SwingConstants.CENTER;
        if (name == "ScrollBar.button") {
            Integer prop = (Integer) 
                button.getClientProperty("__arrow_direction__"); 
            direction = (prop != null) ? 
                prop.intValue() : SwingConstants.WEST; 
            switch (direction) { 
            default: 
            case SwingConstants.EAST: 
            case SwingConstants.WEST: 
                detail = "hscrollbar"; 
                break; 
            case SwingConstants.NORTH: 
            case SwingConstants.SOUTH: 
                detail = "vscrollbar"; 
                break; 
            }
        } else if (name == "Spinner.previousButton") {
            detail = "spinbutton_down";
        } else if (name == "Spinner.nextButton") {
            detail = "spinbutton_up";
        } else if (name != "ComboBox.arrowButton") { 
            assert false;
        }

        int state = context.getComponentState(); 
        synchronized (UNIXToolkit.GTK_LOCK) { 
            if (ENGINE.paintCachedImage(g, x, y, w, h, id, 
                                        state, detail, direction)) 
            { 
                return; 
            } 
            ENGINE.startPainting(g, x, y, w, h, id, 
                                 state, detail, direction); 

            if (detail.startsWith("spin")) {
                /*
                 * The ubuntulooks engine (and presumably others) expect us to
                 * first draw the full "spinbutton" background, and then draw
                 * the individual "spinbutton_up/down" buttons on top of that.
                 * Note that it is the state of the JSpinner (not its arrow
                 * button) that determines how we draw this background.
                 */
                int spinState = button.getParent().isEnabled() ?
                    SynthConstants.ENABLED : SynthConstants.DISABLED;
                int mody = (detail == "spinbutton_up") ? y : y-h;
                int modh = h*2;
                ENGINE.paintBox(g, context, id, spinState,
                                ShadowType.IN, "spinbutton",
                                x, mody, w, modh);
            }

            int gtkState = GTKLookAndFeel.synthStateToGTKState(id, state); 
            ShadowType shadowType = ShadowType.OUT; 
            if ((gtkState & (SynthConstants.PRESSED | 
                             SynthConstants.SELECTED)) != 0) 
            { 
                shadowType = ShadowType.IN; 
            } 
            ENGINE.paintBox(g, context, id, gtkState, 
                            shadowType, detail, x, y, w, h); 
 
            ENGINE.finishPainting(); 
        }
    
public voidpaintArrowButtonForeground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h, int direction)

        Region id = context.getRegion();
        Component c = context.getComponent();
        String name = c.getName();

        ArrowType arrowType = null;
        switch (direction) {
            case SwingConstants.NORTH:
                arrowType = ArrowType.UP; break;
            case SwingConstants.SOUTH:
                arrowType = ArrowType.DOWN; break;
            case SwingConstants.EAST:
                arrowType = ArrowType.RIGHT; break;
            case SwingConstants.WEST:
                arrowType = ArrowType.LEFT; break;
        }

        String detail = "arrow";
        if (name == "ScrollBar.button") {
            if (arrowType == ArrowType.UP || arrowType == ArrowType.DOWN) {
                detail = "vscrollbar";
            } else {
                detail = "hscrollbar";
            }
        } else if (name == "Spinner.nextButton" ||
                   name == "Spinner.previousButton") {
            detail = "spinbutton";
        } else if (name != "ComboBox.arrowButton") {
            assert false;
        }
        
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                id, context.getComponentState());
        ShadowType shadowType = (gtkState == SynthConstants.PRESSED ?
            ShadowType.IN : ShadowType.OUT);
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (ENGINE.paintCachedImage(g, x, y, w, h,
                    gtkState, name, direction)) {
                return;
            }
            ENGINE.startPainting(g, x, y, w, h, gtkState, name, direction);
            ENGINE.paintArrow(g, context, id, gtkState,
                    shadowType, arrowType, detail, x, y, w, h);
            ENGINE.finishPainting();
        }
    
public voidpaintAscendingSortIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        ENGINE.paintArrow(g, context, Region.TABLE, SynthConstants.ENABLED,
                ShadowType.IN, ArrowType.UP, "arrow", x, y, w, h);
    
public voidpaintButtonBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        String name = getName(context);
        if (name != null && name.startsWith("InternalFrameTitlePane.")) {
            Metacity.INSTANCE.paintButtonBackground(context, g, x, y, w, h);

        } else {
            AbstractButton button = (AbstractButton)context.getComponent();
            boolean paintBG = button.isContentAreaFilled() &&
                              button.isBorderPainted();
            boolean paintFocus = button.isFocusPainted();
            boolean defaultCapable = (button instanceof JButton) &&
                    ((JButton)button).isDefaultCapable();
            boolean toolButton = (button.getParent() instanceof JToolBar);
            paintButtonBackgroundImpl(context, g, Region.BUTTON, "button",
                    x, y, w, h, paintBG, paintFocus, defaultCapable, toolButton);
        }
    
private voidpaintButtonBackgroundImpl(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, javax.swing.plaf.synth.Region id, java.lang.String detail, int x, int y, int w, int h, boolean paintBackground, boolean paintFocus, boolean defaultCapable, boolean toolButton)

        int state = context.getComponentState();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (ENGINE.paintCachedImage(g, x, y, w, h, id, state, detail,
                    paintBackground, paintFocus, defaultCapable, toolButton)) {
                return;
            }
            ENGINE.startPainting(g, x, y, w, h, id, state, detail,
                paintBackground, paintFocus, defaultCapable, toolButton);

            // Paint the default indicator
            GTKStyle style = (GTKStyle)context.getStyle();
            if (defaultCapable && !toolButton) {
                Insets defaultInsets = (Insets)style.getClassSpecificInsetsValue(
                        context, "default-border",
                        GTKStyle.BUTTON_DEFAULT_BORDER_INSETS);
            
                if (paintBackground && (state & SynthConstants.DEFAULT) != 0) {
                    ENGINE.paintBox(g, context, id, SynthConstants.ENABLED,
                            ShadowType.IN, "buttondefault", x, y, w, h);
                }
                x += defaultInsets.left;
                y += defaultInsets.top;
                w -= (defaultInsets.left + defaultInsets.right);
                h -= (defaultInsets.top + defaultInsets.bottom);
            }

            boolean interiorFocus = style.getClassSpecificBoolValue(
                    context, "interior-focus", true);
            int focusSize = style.getClassSpecificIntValue(
                    context, "focus-line-width",1);
            int focusPad = style.getClassSpecificIntValue(
                    context, "focus-padding", 1);
            
            int totalFocusSize = focusSize + focusPad;
            int xThickness = style.getXThickness();
            int yThickness = style.getYThickness();

            // Render the box.
            if (!interiorFocus &&
                    (state & SynthConstants.FOCUSED) == SynthConstants.FOCUSED) {
                x += totalFocusSize;
                y += totalFocusSize;
                w -= 2 * totalFocusSize;
                h -= 2 * totalFocusSize;
            }
        
            int gtkState = GTKLookAndFeel.synthStateToGTKState(id, state);
            boolean paintBg;
            if (toolButton) {
                // Toolbar buttons should only have their background painted
                // in the PRESSED, SELECTED, or MOUSE_OVER states.
                paintBg =
                    (gtkState != SynthConstants.ENABLED) &&
                    (gtkState != SynthConstants.DISABLED);
            } else {
                // Otherwise, always paint the button's background, unless
                // the user has overridden it and we're in the ENABLED state.
                paintBg =
                    paintBackground ||
                    (gtkState != SynthConstants.ENABLED);
            }
            if (paintBg) {
                ShadowType shadowType = ShadowType.OUT;
                if ((state & (SynthConstants.PRESSED |
                              SynthConstants.SELECTED)) != 0) {
                    shadowType = ShadowType.IN;
                }
                ENGINE.paintBox(g, context, id, gtkState,
                        shadowType, detail, x, y, w, h);
            }
            
            // focus
            if (paintFocus && (state & SynthConstants.FOCUSED) != 0) {
                if (interiorFocus) {
                    x += xThickness + focusPad;
                    y += yThickness + focusPad;
                    w -= 2 * (xThickness + focusPad);
                    h -= 2 * (yThickness + focusPad);
                } else {
                    x -= totalFocusSize;
                    y -= totalFocusSize;
                    w += 2 * totalFocusSize;
                    h += 2 * totalFocusSize;
                }
                ENGINE.paintFocus(g, context, id, gtkState, detail, x, y, w, h);
            }
            ENGINE.finishPainting();
        }
    
public voidpaintCheckBoxBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        paintRadioButtonBackground(context, g, x, y, w, h);
    
public voidpaintCheckBoxIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        ShadowType shadowType = ShadowType.OUT;
        if (((JCheckBox)context.getComponent()).isSelected()) {
            shadowType = ShadowType.IN;
        }
        ENGINE.paintCheck(g, context, Region.CHECK_BOX,
                GTKLookAndFeel.synthStateToGTKState(context.getRegion(), state),
                shadowType, "checkbutton", x, y, w, h);
    
public voidpaintCheckBoxMenuItemArrowIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        // Don't paint anything.  We are just reserving space so we align the
        // menu items correctly.
    
public voidpaintCheckBoxMenuItemBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        paintRadioButtonMenuItemBackground(context, g, x, y, w, h);
    
public voidpaintCheckBoxMenuItemCheckIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        ShadowType shadowType = ShadowType.OUT;
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                context.getRegion(), state);
        if ((state & SynthConstants.MOUSE_OVER) != 0) {
            gtkState = SynthConstants.MOUSE_OVER;
        }
        if ((state & SynthConstants.SELECTED) != 0) {
            shadowType = ShadowType.IN;
        }
        ENGINE.paintCheck(g, context, Region.CHECK_BOX_MENU_ITEM,
                gtkState, shadowType, "check", x, y, w, h);
    
public voidpaintDescendingSortIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        ENGINE.paintArrow(g, context, Region.TABLE, SynthConstants.ENABLED,
                ShadowType.IN, ArrowType.DOWN, "arrow", x, y, w, h);
    
public voidpaintDesktopIconBorder(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Metacity.INSTANCE.paintFrameBorder(context, g, x, y, w, h);
    
public voidpaintDesktopPaneBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        // Does not call into ENGINE for better performance
        fillArea(context, g, x, y, w, h, ColorType.BACKGROUND);
    
voidpaintFocus(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, javax.swing.plaf.synth.Region id, int state, java.lang.String detail, int x, int y, int w, int h)

        int gtkState = GTKLookAndFeel.synthStateToGTKState(id, state);
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id, gtkState, "focus")) {
                ENGINE.startPainting(g, x, y, w, h, id, gtkState, "focus");
                ENGINE.paintFocus(g, context, id, gtkState, detail, x, y, w, h);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintFormattedTextFieldBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        paintTextBackground(context, g, x, y, w, h);
    
voidpaintIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, java.lang.reflect.Method paintMethod, int x, int y, int w, int h)

        int state = context.getComponentState();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, state, paintMethod)) {
                ENGINE.startPainting(g, x, y, w, h, state, paintMethod);
                try {
                    paintMethod.invoke(this, context, g, state, x, y, w, h);
                } catch (IllegalAccessException iae) {
                    assert false;
                } catch (InvocationTargetException ite) {
                    assert false;
                }
                ENGINE.finishPainting();
            }
        }
    
voidpaintIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, java.lang.reflect.Method paintMethod, int x, int y, int w, int h, java.lang.Object direction)

        int state = context.getComponentState();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g,
                    x, y, w, h, state, paintMethod, direction)) {
                ENGINE.startPainting(g,
                        x, y, w, h, state, paintMethod, direction);
                try {
                    paintMethod.invoke(this, context,
                            g, state, x, y, w, h, direction);
                } catch (IllegalAccessException iae) {
                    assert false;
                } catch (InvocationTargetException ite) {
                    assert false;
                }
                ENGINE.finishPainting();
            }
        }
    
public voidpaintInternalFrameBorder(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Metacity.INSTANCE.paintFrameBorder(context, g, x, y, w, h);
    
public voidpaintLabelBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        String name = getName(context);
        if (name == "TableHeader.renderer" ||
            name == "GTKFileChooser.directoryListLabel" ||
            name == "GTKFileChooser.fileListLabel") {
            
            paintButtonBackgroundImpl(context, g, Region.BUTTON, "button",
                    x, y, w, h, true, false, false, false);
        } else if (name == "ComboBox.renderer") {
            paintTextBackground(context, g, x, y, w, h);
        }
    
public voidpaintListBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        // Does not call into ENGINE for better performance
        fillArea(context, g, x, y, w, h, GTKColorType.TEXT_BACKGROUND);
    
public voidpaintMenuArrowIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h, com.sun.java.swing.plaf.gtk.GTKConstants.ArrowType dir)

        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                context.getRegion(), state);
        ShadowType shadow = ShadowType.OUT;
        if (gtkState == SynthConstants.MOUSE_OVER) {
            shadow = ShadowType.IN;
        }
        ENGINE.paintArrow(g, context, Region.MENU_ITEM, gtkState, shadow,
                dir, "menuitem", x + 3, y + 3, 7, 7);
    
public voidpaintMenuBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        paintMenuItemBackground(context, g, x, y, w, h);
    
public voidpaintMenuBarBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (ENGINE.paintCachedImage(g, x, y, w, h, id)) {
                return;
            }
            GTKStyle style = (GTKStyle)context.getStyle();
            int shadow = style.getClassSpecificIntValue(
                    context, "shadow-type", 2);
            ShadowType shadowType = SHADOWS[shadow];
            int gtkState = GTKLookAndFeel.synthStateToGTKState(
                    id, context.getComponentState());
            ENGINE.startPainting(g, x, y, w, h, id);
            ENGINE.paintBox(g, context, id, gtkState,
                shadowType, "menubar", x, y, w, h);
            ENGINE.finishPainting();
        }
    
public voidpaintMenuItemArrowIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        // Don't paint anything.  We are just reserving space so we align the
        // menu items correctly.
    
public voidpaintMenuItemBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                context.getRegion(), context.getComponentState());
        if (gtkState == SynthConstants.MOUSE_OVER) {
            Region id = Region.MENU_ITEM;
            synchronized (UNIXToolkit.GTK_LOCK) {
                if (! ENGINE.paintCachedImage(g, x, y, w, h, id)) {
                    ShadowType shadow = (GTKLookAndFeel.is2_2() ?
                        ShadowType.NONE : ShadowType.OUT);
                    ENGINE.startPainting(g, x, y, w, h, id);
                    ENGINE.paintBox(g, context, id, gtkState, shadow,
                            "menuitem", x, y, w, h);
                    ENGINE.finishPainting();
                }
            }
        }
    
voidpaintMetacityElement(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int gtkState, java.lang.String detail, int x, int y, int w, int h, com.sun.java.swing.plaf.gtk.GTKConstants.ShadowType shadow, com.sun.java.swing.plaf.gtk.GTKConstants.ArrowType direction)

        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(
                    g, x, y, w, h, gtkState, detail, shadow, direction)) {
                ENGINE.startPainting(
                        g, x, y, w, h, gtkState, detail, shadow, direction);
                if (detail == "metacity-arrow") {
                    ENGINE.paintArrow(g, context, Region.INTERNAL_FRAME_TITLE_PANE,
                            gtkState, shadow, direction, "", x, y, w, h);
                    
                } else if (detail == "metacity-box") {
                    ENGINE.paintBox(g, context, Region.INTERNAL_FRAME_TITLE_PANE,
                            gtkState, shadow, "", x, y, w, h);
                    
                } else if (detail == "metacity-vline") {
                    ENGINE.paintVline(g, context, Region.INTERNAL_FRAME_TITLE_PANE,
                            gtkState, "", x, y, w, h);
                }
                ENGINE.finishPainting();
            }
        }
    
public voidpaintPasswordFieldBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        paintTextBackground(context, g, x, y, w, h);
    
public voidpaintPopupMenuBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                id, context.getComponentState());
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (ENGINE.paintCachedImage(g, x, y, w, h, id, gtkState)) {
                return;
            }
            ENGINE.startPainting(g, x, y, w, h, id, gtkState);
            ENGINE.paintBox(g, context, id, gtkState,
                    ShadowType.OUT, "menu", x, y, w, h);

            GTKStyle style = (GTKStyle)context.getStyle();
            int xThickness = style.getXThickness();
            int yThickness = style.getYThickness();
            ENGINE.paintBackground(g, context, id, gtkState,
                    style.getGTKColor(context, gtkState, GTKColorType.BACKGROUND),
                    x + xThickness, y + yThickness,
                    w - xThickness - xThickness, h - yThickness - yThickness);
            ENGINE.finishPainting();
        }
    
public voidpaintProgressBarBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id)) {
                ENGINE.startPainting(g, x, y, w, h, id);
                ENGINE.paintBox(g, context, id, SynthConstants.ENABLED,
                        ShadowType.IN, "trough", x, y, w, h);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintProgressBarForeground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h, int orientation)

        Region id = context.getRegion();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id, "fg")) {
                ENGINE.startPainting(g, x, y, w, h, id, "fg");
                ENGINE.paintBox(g, context, id, SynthConstants.MOUSE_OVER,
                        ShadowType.OUT, "bar", x, y, w, h);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintRadioButtonBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                id, context.getComponentState());
        if (gtkState == SynthConstants.MOUSE_OVER) {
            synchronized (UNIXToolkit.GTK_LOCK) {
                if (! ENGINE.paintCachedImage(g, x, y, w, h, id)) {
                    ENGINE.startPainting(g, x, y, w, h, id);
                    ENGINE.paintFlatBox(g, context, id,
                            SynthConstants.MOUSE_OVER, ShadowType.ETCHED_OUT,
                            "checkbutton", x, y, w, h, ColorType.BACKGROUND);
                    ENGINE.finishPainting();
                }
            }
        }
    
public voidpaintRadioButtonIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                context.getRegion(), state);
        ShadowType shadowType = ShadowType.OUT;
        // RadioButton painting appears to be special cased to pass
        // SELECTED into the ENGINE even though text colors are PRESSED.
        if ((state & SynthConstants.SELECTED) != 0) {
            gtkState = SynthConstants.SELECTED;
        }
        if (gtkState == SynthConstants.SELECTED) {
            shadowType = ShadowType.IN;
        }
        ENGINE.paintOption(g, context, Region.RADIO_BUTTON, gtkState,
                shadowType, "radiobutton", x, y, w, h);
    
public voidpaintRadioButtonMenuItemArrowIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        // Don't paint anything.  We are just reserving space so we align the
        // menu items correctly.
    
public voidpaintRadioButtonMenuItemBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                id, context.getComponentState());
        if (gtkState == SynthConstants.MOUSE_OVER) {
            synchronized (UNIXToolkit.GTK_LOCK) {
                if (! ENGINE.paintCachedImage(g, x, y, w, h, id)) {
                    ShadowType shadow = (GTKLookAndFeel.is2_2() ?
                        ShadowType.NONE : ShadowType.OUT);
                    ENGINE.startPainting(g, x, y, w, h, id);
                    ENGINE.paintBox(g, context, id, gtkState,
                            shadow, "menuitem", x, y, w, h);
                    ENGINE.finishPainting();
                }
            }
        }
    
public voidpaintRadioButtonMenuItemCheckIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                context.getRegion(), state);
        if ((state & SynthConstants.MOUSE_OVER) != 0) {
            gtkState = SynthConstants.MOUSE_OVER;
        }
        ShadowType shadowType = ShadowType.OUT;
        if ((state & SynthConstants.SELECTED) != 0) {
            shadowType = ShadowType.IN;
        }
        ENGINE.paintOption(g, context, Region.RADIO_BUTTON_MENU_ITEM,
                gtkState, shadowType, "option", x, y, w, h);
    
public voidpaintRootPaneBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        // Does not call into ENGINE for better performance
        fillArea(context, g, x, y, w, h, GTKColorType.BACKGROUND);
    
public voidpaintScrollBarBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        boolean focused = 
                (context.getComponentState() & SynthConstants.FOCUSED) != 0;
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (ENGINE.paintCachedImage(g, x, y, w, h, id, focused)) {
                return;
            }
            ENGINE.startPainting(g, x, y, w, h, id, focused);

            // Note: the scrollbar insets already include the "trough-border",
            // which is needed to position the scrollbar buttons properly.
            // But when we render, we need to take the trough border out
            // of the equation so that we paint the entire area covered by
            // the trough border and the scrollbar content itself.
            Insets insets = context.getComponent().getInsets();
            GTKStyle style = (GTKStyle)context.getStyle();
            int troughBorder = 
                style.getClassSpecificIntValue(context, "trough-border", 1); 
            insets.left   -= troughBorder; 
            insets.right  -= troughBorder; 
            insets.top    -= troughBorder; 
            insets.bottom -= troughBorder; 
            
            ENGINE.paintBox(g, context, id, SynthConstants.PRESSED,
                            ShadowType.IN, "trough", 
                            x + insets.left, 
                            y + insets.top, 
                            w - insets.left - insets.right, 
                            h - insets.top - insets.bottom);
            
            if (focused) {
                ENGINE.paintFocus(g, context, id,
                        SynthConstants.ENABLED, "trough", x, y, w, h);
            }
            ENGINE.finishPainting();
        }
    
public voidpaintScrollBarThumbBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h, int dir)

        Region id = context.getRegion();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                id, context.getComponentState());
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id, gtkState, dir)) {
                ENGINE.startPainting(g, x, y, w, h, id, gtkState, dir);
                Orientation orientation = (dir == JScrollBar.HORIZONTAL ?
                    Orientation.HORIZONTAL : Orientation.VERTICAL);
                ENGINE.paintSlider(g, context, id, gtkState,
                        ShadowType.OUT, "slider", x, y, w, h, orientation);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintScrollPaneBorder(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        paintViewportBorder(context, g, x, y, w, h);
    
public voidpaintSeparatorBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h, int orientation)

        Region id = context.getRegion();
        int state = context.getComponentState();
        JComponent c = context.getComponent();

        /*
         * Note: In theory, the style's x/y thickness values would determine
         * the width of the separator content.  In practice, however, some
         * engines will render a line that is wider than the corresponding
         * thickness value.  For example, ubuntulooks reports x/y thickness
         * values of 1 for separators, but always renders a 2-pixel wide line.
         * As a result of all this, we need to be careful not to restrict
         * the w/h values below too much, so that the full thickness of the
         * rendered line will be captured by our image caching code.
         */
        String detail;
        if (c instanceof JToolBar.Separator) {
            /*
             * GTK renders toolbar separators differently in that an
             * artificial padding is added to each end of the separator.
             * The value of 0.2f below is derived from the source code of
             * gtktoolbar.c in the current version of GTK+ (2.8.20 at the
             * time of this writing).  Specifically, the relevant values are:
             *     SPACE_LINE_DIVISION 10.0
             *     SPACE_LINE_START     2.0
             *     SPACE_LINE_END       8.0
             * These are used to determine the distance from the top (or left)
             * edge of the toolbar to the other edge.  So for example, the
             * starting/top point of a vertical separator is 2/10 of the
             * height of a horizontal toolbar away from the top edge, which
             * is how we arrive at 0.2f below.  Likewise, the ending/bottom
             * point is 8/10 of the height away from the top edge, or in other
             * words, it is 2/10 away from the bottom edge, which is again
             * how we arrive at the 0.2f value below.
             *
             * The separator is also centered horizontally or vertically,
             * depending on its orientation.  This was determined empirically
             * and by examining the code referenced above.
             */
            detail = "toolbar";
            float pct = 0.2f;
            JToolBar.Separator sep = (JToolBar.Separator)c;
            Dimension size = sep.getSeparatorSize();
            GTKStyle style = (GTKStyle)context.getStyle();
            if (orientation == JSeparator.HORIZONTAL) {
                x += (int)(w * pct);
                w -= (int)(w * pct * 2);
                y += (size.height - style.getYThickness()) / 2;
            } else {
                y += (int)(h * pct);
                h -= (int)(h * pct * 2);
                x += (size.width - style.getXThickness()) / 2;
            }
        } else {
            // For regular/menu separators, we simply subtract out the insets.
            detail = "separator";
            Insets insets = c.getInsets();
            x += insets.left;
            y += insets.top;
            if (orientation == JSeparator.HORIZONTAL) {
                w -= (insets.left + insets.right);
            } else {
                h -= (insets.top + insets.bottom);
            }
        }

        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id,
                                          state, detail, orientation)) {
                ENGINE.startPainting(g, x, y, w, h, id,
                                     state, detail, orientation);
                if (orientation == JSeparator.HORIZONTAL) {
                    ENGINE.paintHline(g, context, id, state,
                                      detail, x, y, w, h);
                } else {
                    ENGINE.paintVline(g, context, id, state,
                                      detail, x, y, w, h);
                }
                ENGINE.finishPainting();
            }
        }
    
public voidpaintSliderThumbBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h, int dir)

        Region id = context.getRegion();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                id, context.getComponentState());
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id, gtkState, dir)) {
                Orientation orientation = (dir == JSlider.HORIZONTAL ?
                    Orientation.HORIZONTAL : Orientation.VERTICAL);
                String detail = (dir == JSlider.HORIZONTAL ?
                    "hscale" : "vscale");
                ENGINE.startPainting(g, x, y, w, h, id, gtkState, dir);
                ENGINE.paintSlider(g, context, id, gtkState,
                        ShadowType.OUT, detail, x, y, w, h, orientation);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintSliderTrackBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        int state = context.getComponentState();

        // For focused sliders, we paint focus rect outside the bounds passed.
        // Need to adjust for that.
        boolean focused = ((state & SynthConstants.FOCUSED) != 0);
        int focusSize = 0;
        if (focused) {
            GTKStyle style = (GTKStyle)context.getStyle();
            focusSize = style.getClassSpecificIntValue(
                                context, "focus-line-width", 1) +
                        style.getClassSpecificIntValue(
                                context, "focus-padding", 1);
            x -= focusSize;
            y -= focusSize;
            w += focusSize * 2;
            h += focusSize * 2;
        }

        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id, state)) {
                ENGINE.startPainting(g, x, y, w, h, id, state);
                int gtkState = GTKLookAndFeel.synthStateToGTKState(id, state);
                ENGINE.paintBox(g, context, id, gtkState, ShadowType.IN,
                        "trough", x + focusSize, y + focusSize,
                        w - 2 * focusSize, h - 2 * focusSize);

                if (focused) {
                    ENGINE.paintFocus(g, context, id, SynthConstants.ENABLED,
                            "trough", x, y, w, h);
                }
                ENGINE.finishPainting();
            }
        }
    
public voidpaintSpinnerBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        // This is handled in paintTextFieldBackground
    
public voidpaintSplitPaneDividerBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                id, context.getComponentState());
        JSplitPane splitPane = (JSplitPane)context.getComponent();
        Orientation orientation =
                (splitPane.getOrientation() == JSplitPane.HORIZONTAL_SPLIT ?
                    Orientation.VERTICAL : Orientation.HORIZONTAL);
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h,
                    id, gtkState, orientation)) {
                ENGINE.startPainting(g, x, y, w, h, id, gtkState, orientation);
                ENGINE.paintHandle(g, context, id, gtkState,
                        ShadowType.OUT, "paned", x, y, w, h, orientation);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintSplitPaneDragDivider(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h, int orientation)

        paintSplitPaneDividerForeground(context, g, x, y, w, h, orientation);
    
public voidpaintTabbedPaneContentBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        JTabbedPane pane = (JTabbedPane)context.getComponent();
        int selectedIndex = pane.getSelectedIndex();
        PositionType placement = GTKLookAndFeel.SwingOrientationConstantToGTK(
                                                        pane.getTabPlacement());

        int gapStart = 0;
        int gapSize = 0;
        if (selectedIndex != -1) {
            Rectangle tabBounds = pane.getBoundsAt(selectedIndex);

            if (placement == PositionType.TOP ||
                placement == PositionType.BOTTOM) {
                
                gapStart = tabBounds.x - 1;
                gapSize = tabBounds.width;
            }
            else {
                gapStart = tabBounds.y - 1;
                gapSize = tabBounds.height;
            }
        }

        Region id = context.getRegion();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                id, context.getComponentState());
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h,
                    id, gtkState, placement, gapStart, gapSize)) {
                ENGINE.startPainting(g, x, y, w, h,
                        id, gtkState, placement, gapStart, gapSize);
                ENGINE.paintBoxGap(g, context, id, gtkState, ShadowType.OUT,
                        "notebook", x, y, w, h, placement, gapStart, gapSize);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintTabbedPaneTabBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h, int tabIndex)

        Region id = context.getRegion();
        int state = context.getComponentState();
        int gtkState = ((state & SynthConstants.SELECTED) != 0 ?
            SynthConstants.ENABLED : SynthConstants.PRESSED);
        JTabbedPane pane = (JTabbedPane)context.getComponent();
        int placement = pane.getTabPlacement();

        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h,
                    id, gtkState, placement, tabIndex)) {
                PositionType side = POSITIONS[placement - 1];
                ENGINE.startPainting(g, x, y, w, h,
                        id, gtkState, placement, tabIndex);
                ENGINE.paintExtension(g, context, id, gtkState,
                        ShadowType.OUT, "tab", x, y, w, h, side, tabIndex);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintTextAreaBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        // Does not call into ENGINE for better performance
        fillArea(context, g, x, y, w, h, GTKColorType.TEXT_BACKGROUND);
    
private voidpaintTextBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        // Text is odd in that it uses the TEXT_BACKGROUND vs BACKGROUND.
        JComponent c = context.getComponent();
        GTKStyle style = (GTKStyle)context.getStyle();

        Region id = context.getRegion();
        int state = context.getComponentState();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (ENGINE.paintCachedImage(g, x, y, w, h, id, state)) {
                return;
            }
            
            int gtkState = GTKLookAndFeel.synthStateToGTKState(id, state);
            int focusSize = 0;
            boolean interiorFocus = style.getClassSpecificBoolValue(
                    context, "interior-focus", true);
            if (!interiorFocus && (state & SynthConstants.FOCUSED) != 0) {
                focusSize = style.getClassSpecificIntValue(context,
                        "focus-line-width",1);
                x += focusSize;
                y += focusSize;
                w -= 2 * focusSize;
                h -= 2 * focusSize;
            }
                
            int xThickness = style.getXThickness();
            int yThickness = style.getYThickness();
                
            ENGINE.startPainting(g, x, y, w, h, id, state);
            ENGINE.paintShadow(g, context, id, gtkState,
                    ShadowType.IN, "entry", x, y, w, h);
            ENGINE.paintFlatBox(g, context, id,
                                gtkState, ShadowType.NONE, "entry_bg", 
                                x + xThickness, 
                                y + yThickness, 
                                w - (2 * xThickness), 
                                h - (2 * yThickness), 
                                ColorType.TEXT_BACKGROUND); 

            if (focusSize > 0) {
                x -= focusSize;
                y -= focusSize;
                w += 2 * focusSize;
                h += 2 * focusSize;
                ENGINE.paintFocus(g, context, id, gtkState,
                        "entry", x, y, w, h);
            }
            ENGINE.finishPainting();
        }
    
public voidpaintTextFieldBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        if (getName(context) == "Tree.cellEditor") {
            paintTreeCellEditorBackground(context, g, x, y, w, h);
        } else {
            paintTextBackground(context, g, x, y, w, h);
        }
    
public voidpaintToggleButtonBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        JToggleButton toggleButton = (JToggleButton)context.getComponent();
        boolean paintBG = toggleButton.isContentAreaFilled() &&
                          toggleButton.isBorderPainted();
        boolean paintFocus = toggleButton.isFocusPainted();
        boolean toolButton = (toggleButton.getParent() instanceof JToolBar);
        paintButtonBackgroundImpl(context, g, id, "button",
                                  x, y, w, h,
                                  paintBG, paintFocus, false, toolButton);
    
public voidpaintToolBarBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        int state = context.getComponentState();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(id, state);
        int orientation = ((JToolBar)context.getComponent()).getOrientation();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id,
                                          state, orientation))
            {
                ENGINE.startPainting(g, x, y, w, h, id, state, orientation);
                ENGINE.paintBox(g, context, id, gtkState, ShadowType.OUT,
                                "handlebox_bin", x, y, w, h);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintToolBarContentBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        int orientation = ((JToolBar)context.getComponent()).getOrientation();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id, orientation)) {
                ENGINE.startPainting(g, x, y, w, h, id, orientation);
                ENGINE.paintBox(g, context, id, SynthConstants.ENABLED,
                                ShadowType.OUT, "toolbar", x, y, w, h);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintToolBarDragWindowBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        paintToolBarBackground(context, g, x, y, w, h);
    
public voidpaintToolBarHandleIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h, com.sun.java.swing.plaf.gtk.GTKConstants.Orientation orientation)

        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                context.getRegion(), state);

        // The orientation parameter passed down by Synth refers to the
        // orientation of the toolbar, but the one we pass to GTK refers
        // to the orientation of the handle.  Therefore, we need to swap
        // the value here: horizontal toolbars have vertical handles, and
        // vice versa.
        orientation = (orientation == Orientation.HORIZONTAL) ?
            Orientation.VERTICAL : Orientation.HORIZONTAL;

        ENGINE.paintHandle(g, context, Region.TOOL_BAR, gtkState,
                ShadowType.OUT, "handlebox", x, y, w, h, orientation);
    
public voidpaintToolTipBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id)) {
                ENGINE.startPainting(g, x, y, w, h, id);
                ENGINE.paintFlatBox(g, context, id, SynthConstants.ENABLED,
                        ShadowType.OUT, "tooltip", x, y, w, h,
                        ColorType.BACKGROUND);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintTreeBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        // As far as I can tell, these don't call into the ENGINE.
        fillArea(context, g, x, y, w, h, GTKColorType.TEXT_BACKGROUND);
    
public voidpaintTreeCellBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        int state = context.getComponentState();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(id, state);
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id, state)) {
                ENGINE.startPainting(g, x, y, w, h, id, state);
                // the string arg should alternate based on row being painted,
                // but we currently don't pass that in.
                ENGINE.paintFlatBox(g, context, id, gtkState, ShadowType.NONE,
                        "cell_odd", x, y, w, h, ColorType.TEXT_BACKGROUND);
                ENGINE.finishPainting();
            }
        }
    
private voidpaintTreeCellEditorBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        int gtkState = GTKLookAndFeel.synthStateToGTKState(
                id, context.getComponentState());
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id, gtkState)) {
                ENGINE.startPainting(g, x, y, w, h, id, gtkState);
                ENGINE.paintFlatBox(g, context, id, gtkState, ShadowType.NONE,
                        "entry_bg", x, y, w, h, ColorType.TEXT_BACKGROUND);
                ENGINE.finishPainting();
            }
        }
    
public voidpaintTreeCellFocus(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = Region.TREE_CELL;
        int state = context.getComponentState();
        paintFocus(context, g, id, state, "treeview", x, y, w, h);
    
public voidpaintTreeCollapsedIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        ENGINE.paintExpander(g, context, Region.TREE,
                GTKLookAndFeel.synthStateToGTKState(context.getRegion(), state),
                ExpanderStyle.COLLAPSED, "treeview", x, y, w, h);
    
public voidpaintTreeExpandedIcon(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int state, int x, int y, int w, int h)

        ENGINE.paintExpander(g, context, Region.TREE,
                GTKLookAndFeel.synthStateToGTKState(context.getRegion(), state),
                ExpanderStyle.EXPANDED, "treeview", x, y, w, h);
    
public voidpaintViewportBackground(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        // As far as I can tell, these don't call into the ENGINE.
        // Also note that you don't want this to call into the ENGINE
        // as if it where to paint a background JViewport wouldn't scroll
        // correctly.
        fillArea(context, g, x, y, w, h, GTKColorType.TEXT_BACKGROUND);
    
public voidpaintViewportBorder(javax.swing.plaf.synth.SynthContext context, java.awt.Graphics g, int x, int y, int w, int h)

        Region id = context.getRegion();
        synchronized (UNIXToolkit.GTK_LOCK) {
            if (! ENGINE.paintCachedImage(g, x, y, w, h, id)) {
                ENGINE.startPainting(g, x, y, w, h, id);
                ENGINE.paintShadow(g, context, id, SynthConstants.ENABLED,
                        ShadowType.IN, "scrolled_window", x, y, w, h);
                ENGINE.finishPainting();
            }
        }