1 7 package com.sun.java.swing.plaf.gtk; 8 9 import javax.swing.plaf.synth.*; 10 import java.awt.*; 11 import java.awt.image.*; 12 import javax.swing.*; 13 import com.sun.java.swing.plaf.gtk.GTKConstants.ArrowType; 14 import com.sun.java.swing.plaf.gtk.GTKConstants.ExpanderStyle; 15 import com.sun.java.swing.plaf.gtk.GTKConstants.Orientation; 16 import com.sun.java.swing.plaf.gtk.GTKConstants.PositionType; 17 import com.sun.java.swing.plaf.gtk.GTKConstants.ShadowType; 18 import com.sun.java.swing.plaf.gtk.GTKConstants.WidgetType; 19 import com.sun.java.swing.plaf.gtk.GTKConstants.TextDirection; 20 21 import javax.imageio.*; 22 import java.io.*; 23 import java.util.HashMap ; 24 import sun.awt.image.SunWritableRaster; 25 import sun.swing.ImageCache; 26 27 41 public class GTKNativeEngine extends GTKEngine { 42 43 private static final int CACHE_SIZE = 50; 44 45 private static HashMap regionToWidgetTypeMap; 46 private ImageCache cache = new ImageCache(CACHE_SIZE); 47 private int x0, y0, w0, h0; 48 private Graphics graphics; 49 private Object [] cacheArgs; 50 51 private native void native_paint_arrow( 52 int widgetType, int state, int shadowType, String detail, 53 int x, int y, int width, int height, int arrowType); 54 private native void native_paint_box( 55 int widgetType, int state, int shadowType, String detail, 56 int x, int y, int width, int height, int synth_state, int dir); 57 private native void native_paint_box_gap( 58 int widgetType, int state, int shadowType, String detail, 59 int x, int y, int width, int height, 60 int gapSide, int gapX, int gapWidth); 61 private native void native_paint_check( 62 int widgetType, int synthState, String detail, 63 int x, int y, int width, int height); 64 private native void native_paint_expander( 65 int widgetType, int state, String detail, 66 int x, int y, int width, int height, int expanderStyle); 67 private native void native_paint_extension( 68 int widgetType, int state, int shadowType, String detail, 69 int x, int y, int width, int height, int placement); 70 private native void native_paint_flat_box( 71 int widgetType, int state, int shadowType, String detail, 72 int x, int y, int width, int height, boolean hasFocus); 73 private native void native_paint_focus( 74 int widgetType, int state, String detail, 75 int x, int y, int width, int height); 76 private native void native_paint_handle( 77 int widgetType, int state, int shadowType, String detail, 78 int x, int y, int width, int height, int orientation); 79 private native void native_paint_hline( 80 int widgetType, int state, String detail, 81 int x, int y, int width, int height); 82 private native void native_paint_option( 83 int widgetType, int synthState, String detail, 84 int x, int y, int width, int height); 85 private native void native_paint_shadow( 86 int widgetType, int state, int shadowType, String detail, 87 int x, int y, int width, int height, int synthState, int dir); 88 private native void native_paint_slider( 89 int widgetType, int state, int shadowType, String detail, 90 int x, int y, int width, int height, int orientation); 91 private native void native_paint_vline( 92 int widgetType, int state, String detail, 93 int x, int y, int width, int height); 94 private native void native_paint_background( 95 int widgetType, int state, int x, int y, int width, int height); 96 private native Object native_get_gtk_setting(int property); 97 98 private native void nativeStartPainting(int w, int h); 99 private native int nativeFinishPainting(int[] buffer, int width, int height); 100 private native void native_switch_theme(); 101 102 103 static { 104 Toolkit.getDefaultToolkit(); 107 108 regionToWidgetTypeMap = new HashMap (50); 110 regionToWidgetTypeMap.put(Region.ARROW_BUTTON, new WidgetType[] { 111 WidgetType.SPINNER_ARROW_BUTTON, 112 WidgetType.COMBO_BOX_ARROW_BUTTON, 113 WidgetType.HSCROLL_BAR_BUTTON_LEFT, 114 WidgetType.HSCROLL_BAR_BUTTON_RIGHT, 115 WidgetType.VSCROLL_BAR_BUTTON_UP, 116 WidgetType.VSCROLL_BAR_BUTTON_DOWN}); 117 regionToWidgetTypeMap.put(Region.BUTTON, WidgetType.BUTTON); 118 regionToWidgetTypeMap.put(Region.CHECK_BOX, WidgetType.CHECK_BOX); 119 regionToWidgetTypeMap.put(Region.CHECK_BOX_MENU_ITEM, 120 WidgetType.CHECK_BOX_MENU_ITEM); 121 regionToWidgetTypeMap.put(Region.COLOR_CHOOSER, WidgetType.COLOR_CHOOSER); 122 regionToWidgetTypeMap.put(Region.FILE_CHOOSER, WidgetType.OPTION_PANE); 123 regionToWidgetTypeMap.put(Region.COMBO_BOX, WidgetType.COMBO_BOX); 124 regionToWidgetTypeMap.put(Region.DESKTOP_ICON, WidgetType.DESKTOP_ICON); 125 regionToWidgetTypeMap.put(Region.DESKTOP_PANE, WidgetType.DESKTOP_PANE); 126 regionToWidgetTypeMap.put(Region.EDITOR_PANE, WidgetType.EDITOR_PANE); 127 regionToWidgetTypeMap.put(Region.FORMATTED_TEXT_FIELD, new WidgetType[] { 128 WidgetType.FORMATTED_TEXT_FIELD, WidgetType.SPINNER_TEXT_FIELD}); 129 regionToWidgetTypeMap.put(GTKRegion.HANDLE_BOX, WidgetType.HANDLE_BOX); 130 regionToWidgetTypeMap.put(Region.INTERNAL_FRAME, 131 WidgetType.INTERNAL_FRAME); 132 regionToWidgetTypeMap.put(Region.INTERNAL_FRAME_TITLE_PANE, 133 WidgetType.INTERNAL_FRAME_TITLE_PANE); 134 regionToWidgetTypeMap.put(Region.LABEL, new WidgetType[] { 135 WidgetType.LABEL, WidgetType.COMBO_BOX_TEXT_FIELD}); 136 regionToWidgetTypeMap.put(Region.LIST, WidgetType.LIST); 137 regionToWidgetTypeMap.put(Region.MENU, WidgetType.MENU); 138 regionToWidgetTypeMap.put(Region.MENU_BAR, WidgetType.MENU_BAR); 139 regionToWidgetTypeMap.put(Region.MENU_ITEM, WidgetType.MENU_ITEM); 140 regionToWidgetTypeMap.put(Region.MENU_ITEM_ACCELERATOR, 141 WidgetType.MENU_ITEM_ACCELERATOR); 142 regionToWidgetTypeMap.put(Region.OPTION_PANE, WidgetType.OPTION_PANE); 143 regionToWidgetTypeMap.put(Region.PANEL, WidgetType.PANEL); 144 regionToWidgetTypeMap.put(Region.PASSWORD_FIELD, 145 WidgetType.PASSWORD_FIELD); 146 regionToWidgetTypeMap.put(Region.POPUP_MENU, WidgetType.POPUP_MENU); 147 regionToWidgetTypeMap.put(Region.POPUP_MENU_SEPARATOR, 148 WidgetType.POPUP_MENU_SEPARATOR); 149 regionToWidgetTypeMap.put(Region.PROGRESS_BAR, WidgetType.PROGRESS_BAR); 150 regionToWidgetTypeMap.put(Region.RADIO_BUTTON, WidgetType.RADIO_BUTTON); 151 regionToWidgetTypeMap.put(Region.RADIO_BUTTON_MENU_ITEM, 152 WidgetType.RADIO_BUTTON_MENU_ITEM); 153 regionToWidgetTypeMap.put(Region.ROOT_PANE, WidgetType.ROOT_PANE); 154 regionToWidgetTypeMap.put(Region.SCROLL_BAR, new WidgetType[] { 155 WidgetType.HSCROLL_BAR, WidgetType.VSCROLL_BAR}); 156 regionToWidgetTypeMap.put(Region.SCROLL_BAR_THUMB, new WidgetType[] { 157 WidgetType.HSCROLL_BAR_THUMB, WidgetType.VSCROLL_BAR_THUMB}); 158 regionToWidgetTypeMap.put(Region.SCROLL_BAR_TRACK, new WidgetType[] { 159 WidgetType.HSCROLL_BAR_TRACK, WidgetType.VSCROLL_BAR_TRACK}); 160 regionToWidgetTypeMap.put(Region.SCROLL_PANE, WidgetType.SCROLL_PANE); 161 regionToWidgetTypeMap.put(Region.SEPARATOR, new WidgetType[] { 162 WidgetType.HSEPARATOR, WidgetType.VSEPARATOR}); 163 regionToWidgetTypeMap.put(Region.SLIDER, new WidgetType[] { 164 WidgetType.HSLIDER, WidgetType.VSLIDER}); 165 regionToWidgetTypeMap.put(Region.SLIDER_THUMB, new WidgetType[] { 166 WidgetType.HSLIDER_THUMB, WidgetType.VSLIDER_THUMB}); 167 regionToWidgetTypeMap.put(Region.SLIDER_TRACK, new WidgetType[] { 168 WidgetType.HSLIDER_TRACK, WidgetType.VSLIDER_TRACK}); 169 regionToWidgetTypeMap.put(Region.SPINNER, WidgetType.SPINNER); 170 regionToWidgetTypeMap.put(Region.SPLIT_PANE, WidgetType.SPLIT_PANE); 171 regionToWidgetTypeMap.put(Region.SPLIT_PANE_DIVIDER, new WidgetType[] { 172 WidgetType.HSPLIT_PANE_DIVIDER, WidgetType.VSPLIT_PANE_DIVIDER}); 173 regionToWidgetTypeMap.put(Region.TABBED_PANE, WidgetType.TABBED_PANE); 174 regionToWidgetTypeMap.put(Region.TABBED_PANE_CONTENT, 175 WidgetType.TABBED_PANE_CONTENT); 176 regionToWidgetTypeMap.put(Region.TABBED_PANE_TAB, 177 WidgetType.TABBED_PANE_TAB); 178 regionToWidgetTypeMap.put(Region.TABBED_PANE_TAB_AREA, 179 WidgetType.TABBED_PANE_TAB_AREA); 180 regionToWidgetTypeMap.put(Region.TABLE, WidgetType.TABLE); 181 regionToWidgetTypeMap.put(Region.TABLE_HEADER, WidgetType.TABLE_HEADER); 182 regionToWidgetTypeMap.put(Region.TEXT_AREA, WidgetType.TEXT_AREA); 183 regionToWidgetTypeMap.put(Region.TEXT_FIELD, new WidgetType[] { 184 WidgetType.TEXT_FIELD, WidgetType.COMBO_BOX_TEXT_FIELD}); 185 regionToWidgetTypeMap.put(Region.TEXT_PANE, WidgetType.TEXT_PANE); 186 regionToWidgetTypeMap.put(Region.TOGGLE_BUTTON, WidgetType.TOGGLE_BUTTON); 187 regionToWidgetTypeMap.put(Region.TOOL_BAR, WidgetType.TOOL_BAR); 188 regionToWidgetTypeMap.put(Region.TOOL_BAR_CONTENT, WidgetType.TOOL_BAR); 189 regionToWidgetTypeMap.put(Region.TOOL_BAR_DRAG_WINDOW, 190 WidgetType.TOOL_BAR_DRAG_WINDOW); 191 regionToWidgetTypeMap.put(Region.TOOL_BAR_SEPARATOR, 192 WidgetType.TOOL_BAR_SEPARATOR); 193 regionToWidgetTypeMap.put(Region.TOOL_TIP, WidgetType.TOOL_TIP); 194 regionToWidgetTypeMap.put(Region.TREE, WidgetType.TREE); 195 regionToWidgetTypeMap.put(Region.TREE_CELL, WidgetType.TREE_CELL); 196 regionToWidgetTypeMap.put(Region.VIEWPORT, WidgetType.VIEWPORT); 197 } 198 199 200 static WidgetType getWidgetType(JComponent c, Region id) { 201 Object value = regionToWidgetTypeMap.get(id); 202 203 if (value instanceof WidgetType) { 204 return (WidgetType)value; 205 } 206 207 WidgetType[] widgets = (WidgetType[])value; 208 if (c == null ) { 209 return widgets[0]; 210 } 211 212 if (c instanceof JScrollBar) { 213 return (((JScrollBar)c).getOrientation() == JScrollBar.HORIZONTAL) ? 214 widgets[0] : widgets[1]; 215 } else if (c instanceof JSeparator) { 216 JSeparator separator = (JSeparator)c; 217 218 221 if (separator.getParent() instanceof JPopupMenu) { 222 return WidgetType.POPUP_MENU_SEPARATOR; 223 } else if (separator.getParent() instanceof JToolBar) { 224 return WidgetType.TOOL_BAR_SEPARATOR; 225 } 226 227 return (separator.getOrientation() == JSeparator.HORIZONTAL) ? 228 widgets[0] : widgets[1]; 229 } else if (c instanceof JSlider) { 230 return (((JSlider)c).getOrientation() == JSlider.HORIZONTAL) ? 231 widgets[0] : widgets[1]; 232 } else if (c instanceof JSplitPane) { 233 return (((JSplitPane)c).getOrientation() == JSplitPane.HORIZONTAL_SPLIT) ? 234 widgets[1] : widgets[0]; 235 } else if (id == Region.LABEL || id == Region.TEXT_FIELD) { 236 String name = c.getName(); 237 if (name != null && name.startsWith("ComboBox")) { 238 return widgets[1]; 239 } else { 240 return widgets[0]; 241 } 242 } else if (id == Region.FORMATTED_TEXT_FIELD) { 243 String name = c.getName(); 244 if (name != null && name.startsWith("Spinner")) { 245 return widgets[1]; 246 } else { 247 return widgets[0]; 248 } 249 } else if (id == Region.ARROW_BUTTON) { 250 if (c.getParent() instanceof JScrollBar) { 251 Integer prop = (Integer )c.getClientProperty("__arrow_direction__"); 252 int dir = (prop != null) ? 253 prop.intValue() : SwingConstants.WEST; 254 switch (dir) { 255 case SwingConstants.WEST: 256 return WidgetType.HSCROLL_BAR_BUTTON_LEFT; 257 case SwingConstants.EAST: 258 return WidgetType.HSCROLL_BAR_BUTTON_RIGHT; 259 case SwingConstants.NORTH: 260 return WidgetType.VSCROLL_BAR_BUTTON_UP; 261 case SwingConstants.SOUTH: 262 return WidgetType.VSCROLL_BAR_BUTTON_DOWN; 263 default: 264 return null; 265 } 266 } else if (c.getParent() instanceof JComboBox) { 267 return WidgetType.COMBO_BOX_ARROW_BUTTON; 268 } else { 269 return WidgetType.SPINNER_ARROW_BUTTON; 270 } 271 } 272 273 return null; 274 } 275 276 private static int getTextDirection(SynthContext context) { 277 TextDirection dir = TextDirection.NONE; 278 JComponent comp = context.getComponent(); 279 if (comp != null) { 280 ComponentOrientation co = comp.getComponentOrientation(); 281 if (co != null) { 282 dir = co.isLeftToRight() ? 283 TextDirection.LTR : TextDirection.RTL; 284 } 285 } 286 return dir.ordinal(); 287 } 288 289 public void paintArrow(Graphics g, SynthContext context, 290 Region id, int state, ShadowType shadowType, ArrowType direction, 291 String detail, int x, int y, int w, int h) { 292 293 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 294 int widget = getWidgetType(context.getComponent(), id).ordinal(); 295 native_paint_arrow(widget, state, shadowType.ordinal(), 296 detail, x - x0, y - y0, w, h, direction.ordinal()); 297 } 298 299 public void paintBox(Graphics g, SynthContext context, 300 Region id, int state, ShadowType shadowType, 301 String detail, int x, int y, int w, int h) { 302 303 int gtkState = 304 GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 305 int synthState = context.getComponentState(); 306 int dir = getTextDirection(context); 307 int widget = getWidgetType(context.getComponent(), id).ordinal(); 308 native_paint_box(widget, gtkState, shadowType.ordinal(), 309 detail, x - x0, y - y0, w, h, synthState, dir); 310 } 311 312 public void paintBoxGap(Graphics g, SynthContext context, 313 Region id, int state, ShadowType shadowType, 314 String detail, int x, int y, int w, int h, 315 PositionType boxGapType, int tabBegin, int size) { 316 317 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 318 int widget = getWidgetType(context.getComponent(), id).ordinal(); 319 native_paint_box_gap(widget, state, shadowType.ordinal(), detail, 320 x - x0, y - y0, w, h, boxGapType.ordinal(), tabBegin, size); 321 } 322 323 public void paintCheck(Graphics g, SynthContext context, 324 Region id, int state, ShadowType shadowType, String detail, 325 int x, int y, int w, int h) { 326 327 int synthState = context.getComponentState(); 328 int widget = getWidgetType(context.getComponent(), id).ordinal(); 329 native_paint_check(widget, synthState, detail, x - x0, y - y0, w, h); 330 } 331 332 public void paintExpander(Graphics g, SynthContext context, 333 Region id, int state, ExpanderStyle expanderStyle, String detail, 334 int x, int y, int w, int h) { 335 336 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 337 int widget = getWidgetType(context.getComponent(), id).ordinal(); 338 native_paint_expander(widget, state, detail, x - x0, y - y0, w, h, 339 expanderStyle.ordinal()); 340 } 341 342 public void paintExtension(Graphics g, SynthContext context, 343 Region id, int state, ShadowType shadowType, String detail, 344 int x, int y, int w, int h, PositionType placement, int tabIndex) { 345 346 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 347 int widget = getWidgetType(context.getComponent(), id).ordinal(); 348 native_paint_extension(widget, state, shadowType.ordinal(), detail, 349 x - x0, y - y0, w, h, placement.ordinal()); 350 } 351 352 public void paintFlatBox(Graphics g, SynthContext context, 353 Region id, int state, ShadowType shadowType, String detail, 354 int x, int y, int w, int h, ColorType colorType) { 355 356 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 357 int widget = getWidgetType(context.getComponent(), id).ordinal(); 358 native_paint_flat_box(widget, state, shadowType.ordinal(), detail, 359 x - x0, y - y0, w, h, 360 context.getComponent().hasFocus()); 361 } 362 363 public void paintFocus(Graphics g, SynthContext context, 364 Region id, int state, String detail, int x, int y, int w, int h) { 365 366 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 367 int widget = getWidgetType(context.getComponent(), id).ordinal(); 368 native_paint_focus(widget, state, detail, x - x0, y - y0, w, h); 369 } 370 371 public void paintHandle(Graphics g, SynthContext context, 372 Region id, int state, ShadowType shadowType, String detail, 373 int x, int y, int w, int h, Orientation orientation) { 374 375 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 376 int widget = getWidgetType(context.getComponent(), id).ordinal(); 377 native_paint_handle(widget, state, shadowType.ordinal(), detail, 378 x - x0, y - y0, w, h, orientation.ordinal()); 379 } 380 381 public void paintHline(Graphics g, SynthContext context, 382 Region id, int state, String detail, int x, int y, int w, int h) { 383 384 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 385 int widget = getWidgetType(context.getComponent(), id).ordinal(); 386 native_paint_hline(widget, state, detail, x - x0, y - y0, w, h); 387 } 388 389 public void paintOption(Graphics g, SynthContext context, 390 Region id, int state, ShadowType shadowType, String detail, 391 int x, int y, int w, int h) { 392 393 int synthState = context.getComponentState(); 394 int widget = getWidgetType(context.getComponent(), id).ordinal(); 395 native_paint_option(widget, synthState, detail, x - x0, y - y0, w, h); 396 } 397 398 public void paintShadow(Graphics g, SynthContext context, 399 Region id, int state, ShadowType shadowType, String detail, 400 int x, int y, int w, int h) { 401 402 int gtkState = 403 GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 404 int synthState = context.getComponentState(); 405 int dir = getTextDirection(context); 406 int widget = getWidgetType(context.getComponent(), id).ordinal(); 407 native_paint_shadow(widget, gtkState, shadowType.ordinal(), detail, 408 x - x0, y - y0, w, h, synthState, dir); 409 } 410 411 public void paintSlider(Graphics g, SynthContext context, 412 Region id, int state, ShadowType shadowType, String detail, 413 int x, int y, int w, int h, Orientation orientation) { 414 415 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 416 int widget = getWidgetType(context.getComponent(), id).ordinal(); 417 native_paint_slider(widget, state, shadowType.ordinal(), detail, 418 x - x0, y - y0, w, h, orientation.ordinal()); 419 } 420 421 public void paintVline(Graphics g, SynthContext context, 422 Region id, int state, String detail, int x, int y, int w, int h) { 423 424 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 425 int widget = getWidgetType(context.getComponent(), id).ordinal(); 426 native_paint_vline(widget, state, detail, x - x0, y - y0, w, h); 427 } 428 429 public void paintBackground(Graphics g, SynthContext context, 430 Region id, int state, Color color, int x, int y, int w, int h) { 431 432 state = GTKLookAndFeel.synthStateToGTKStateType(state).ordinal(); 433 int widget = getWidgetType(context.getComponent(), id).ordinal(); 434 native_paint_background(widget, state, x - x0, y - y0, w, h); 435 } 436 437 private final static ColorModel[] COLOR_MODELS = { 438 new DirectColorModel(24, 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00000000), 440 new DirectColorModel(25, 0x00ff0000, 0x0000ff00, 0x000000ff, 0x01000000), 442 ColorModel.getRGBdefault(), 444 }; 445 446 private final static int[][] BAND_OFFSETS = { 447 { 0x00ff0000, 0x0000ff00, 0x000000ff }, { 0x00ff0000, 0x0000ff00, 0x000000ff, 0x01000000 }, { 0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000 } }; 451 452 453 459 public boolean paintCachedImage(Graphics g, 460 int x, int y, int w, int h, Object ... args) { 461 if (w <= 0 || h <= 0) { 462 return true; 463 } 464 465 Image img = cache.getImage(getClass(), null, w, h, args); 467 if (img != null) { 468 g.drawImage(img, x, y, null); 469 return true; 470 } 471 return false; 472 } 473 474 477 public void startPainting(Graphics g, 478 int x, int y, int w, int h, Object ... args) { 479 nativeStartPainting(w, h); 480 x0 = x; 481 y0 = y; 482 w0 = w; 483 h0 = h; 484 graphics = g; 485 cacheArgs = args; 486 } 487 488 492 public void finishPainting() { 493 int[] data = new int[w0 * h0]; 494 int transparency = nativeFinishPainting(data, w0, h0); 495 496 int[] bands = BAND_OFFSETS[transparency - 1]; 497 DataBuffer dataBuffer = new DataBufferInt(data, data.length); 498 WritableRaster raster = Raster.createPackedRaster( 499 dataBuffer, w0, h0, w0, bands, null); 500 501 if (raster instanceof SunWritableRaster) { 504 ((SunWritableRaster)raster).setStolen(false); 505 } 506 507 ColorModel cm = COLOR_MODELS[transparency - 1]; 508 Image img = new BufferedImage(cm, raster, false, null); 509 cache.setImage(getClass(), null, w0, h0, cacheArgs, img); 510 graphics.drawImage(img, x0, y0, null); 511 } 512 513 516 public void themeChanged() { 517 synchronized(sun.awt.UNIXToolkit.GTK_LOCK) { 518 native_switch_theme(); 519 } 520 cache.flush(); 521 } 522 523 524 public Object getSetting(Settings property) { 525 synchronized(sun.awt.UNIXToolkit.GTK_LOCK) { 526 return native_get_gtk_setting(property.ordinal()); 527 } 528 } 529 } 530 | Popular Tags |