OpenCores
URL https://opencores.org/ocsvn/scarts/scarts/trunk

Subversion Repositories scarts

[/] [scarts/] [trunk/] [toolchain/] [scarts-gcc/] [gcc-4.1.1/] [libjava/] [classpath/] [gnu/] [java/] [awt/] [peer/] [gtk/] [GtkComponentPeer.java] - Blame information for rev 14

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 14 jlechner
/* GtkComponentPeer.java -- Implements ComponentPeer with GTK
2
   Copyright (C) 1998, 1999, 2002, 2004, 2005  Free Software Foundation, Inc.
3
 
4
This file is part of GNU Classpath.
5
 
6
GNU Classpath is free software; you can redistribute it and/or modify
7
it under the terms of the GNU General Public License as published by
8
the Free Software Foundation; either version 2, or (at your option)
9
any later version.
10
 
11
GNU Classpath is distributed in the hope that it will be useful, but
12
WITHOUT ANY WARRANTY; without even the implied warranty of
13
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14
General Public License for more details.
15
 
16
You should have received a copy of the GNU General Public License
17
along with GNU Classpath; see the file COPYING.  If not, write to the
18
Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
19
02110-1301 USA.
20
 
21
Linking this library statically or dynamically with other modules is
22
making a combined work based on this library.  Thus, the terms and
23
conditions of the GNU General Public License cover the whole
24
combination.
25
 
26
As a special exception, the copyright holders of this library give you
27
permission to link this library with independent modules to produce an
28
executable, regardless of the license terms of these independent
29
modules, and to copy and distribute the resulting executable under
30
terms of your choice, provided that you also meet, for each linked
31
independent module, the terms and conditions of the license of that
32
module.  An independent module is a module which is not derived from
33
or based on this library.  If you modify this library, you may extend
34
this exception to your version of the library, but you are not
35
obligated to do so.  If you do not wish to do so, delete this
36
exception statement from your version. */
37
 
38
 
39
package gnu.java.awt.peer.gtk;
40
 
41
import java.awt.AWTEvent;
42
import java.awt.AWTException;
43
import java.awt.BufferCapabilities;
44
import java.awt.Color;
45
import java.awt.Component;
46
import java.awt.Container;
47
import java.awt.Cursor;
48
import java.awt.Dimension;
49
import java.awt.Font;
50
import java.awt.FontMetrics;
51
import java.awt.Graphics;
52
import java.awt.Graphics2D;
53
import java.awt.GraphicsConfiguration;
54
import java.awt.Image;
55
import java.awt.Insets;
56
import java.awt.ItemSelectable;
57
import java.awt.Point;
58
import java.awt.Rectangle;
59
import java.awt.Toolkit;
60
import java.awt.Window;
61
import java.awt.event.FocusEvent;
62
import java.awt.event.ItemEvent;
63
import java.awt.event.KeyEvent;
64
import java.awt.event.MouseEvent;
65
import java.awt.event.PaintEvent;
66
import java.awt.event.TextEvent;
67
import java.awt.image.BufferedImage;
68
import java.awt.image.ColorModel;
69
import java.awt.image.ImageObserver;
70
import java.awt.image.ImageProducer;
71
import java.awt.image.VolatileImage;
72
import java.awt.peer.ComponentPeer;
73
import java.awt.peer.ContainerPeer;
74
import java.awt.peer.WindowPeer;
75
import java.util.Timer;
76
import java.util.TimerTask;
77
 
78
public class GtkComponentPeer extends GtkGenericPeer
79
  implements ComponentPeer
80
{
81
  VolatileImage backBuffer;
82
  BufferCapabilities caps;
83
 
84
  Component awtComponent;
85
 
86
  Insets insets;
87
 
88
  boolean isInRepaint;
89
 
90
  static final Timer repaintTimer = new Timer (true);
91
 
92
  /* this isEnabled differs from Component.isEnabled, in that it
93
     knows if a parent is disabled.  In that case Component.isEnabled
94
     may return true, but our isEnabled will always return false */
95
  native boolean isEnabled ();
96
  static native boolean modalHasGrab();
97
 
98
  native int[] gtkWidgetGetForeground ();
99
  native int[] gtkWidgetGetBackground ();
100
  native void gtkWidgetGetDimensions (int[] dim);
101
  native void gtkWidgetGetPreferredDimensions (int[] dim);
102
  native void gtkWindowGetLocationOnScreen (int[] point);
103
  native void gtkWidgetGetLocationOnScreen (int[] point);
104
  native void gtkWidgetSetCursor (int type);
105
  native void gtkWidgetSetCursorUnlocked (int type);
106
  native void gtkWidgetSetBackground (int red, int green, int blue);
107
  native void gtkWidgetSetForeground (int red, int green, int blue);
108
  native void gtkWidgetSetSensitive (boolean sensitive);
109
  native void gtkWidgetSetParent (ComponentPeer parent);
110
  native void gtkWidgetRequestFocus ();
111
  native void gtkWidgetDispatchKeyEvent (int id, long when, int mods,
112
                                         int keyCode, int keyLocation);
113
 
114
  native boolean isRealized ();
115
 
116
  void realize ()
117
  {
118
    // Default implementation does nothing
119
  }
120
 
121
  native void setNativeEventMask ();
122
 
123
  void create ()
124
  {
125
    throw new RuntimeException ();
126
  }
127
 
128
  native void connectSignals ();
129
 
130
  protected GtkComponentPeer (Component awtComponent)
131
  {
132
    super (awtComponent);
133
    this.awtComponent = awtComponent;
134
    insets = new Insets (0, 0, 0, 0);
135
 
136
    create ();
137
 
138
    connectSignals ();
139
 
140
    if (awtComponent.getForeground () != null)
141
      setForeground (awtComponent.getForeground ());
142
    if (awtComponent.getBackground () != null)
143
      setBackground (awtComponent.getBackground ());
144
    if (awtComponent.getFont() != null)
145
      setFont(awtComponent.getFont());
146
 
147
    Component parent = awtComponent.getParent ();
148
 
149
    // Only set our parent on the GTK side if our parent on the AWT
150
    // side is not showing.  Otherwise the gtk peer will be shown
151
    // before we've had a chance to position and size it properly.
152
    if (awtComponent instanceof Window
153
        || (parent != null && ! parent.isShowing ()))
154
      setParentAndBounds ();
155
 
156
    setNativeEventMask ();
157
 
158
    realize ();
159
  }
160
 
161
  void setParentAndBounds ()
162
  {
163
    setParent ();
164
 
165
    setComponentBounds ();
166
 
167
    setVisibleAndEnabled ();
168
  }
169
 
170
  void setParent ()
171
  {
172
    ComponentPeer p;
173
    Component component = awtComponent;
174
    do
175
      {
176
        component = component.getParent ();
177
        p = component.getPeer ();
178
      }
179
    while (p instanceof java.awt.peer.LightweightPeer);
180
 
181
    if (p != null)
182
      gtkWidgetSetParent (p);
183
  }
184
 
185
  void beginNativeRepaint ()
186
  {
187
    isInRepaint = true;
188
  }
189
 
190
  void endNativeRepaint ()
191
  {
192
    isInRepaint = false;
193
  }
194
 
195
  /*
196
   * Set the bounds of this peer's AWT Component based on dimensions
197
   * returned by the native windowing system.  Most Components impose
198
   * their dimensions on the peers which is what the default
199
   * implementation does.  However some peers, like GtkFileDialogPeer,
200
   * need to pass their size back to the AWT Component.
201
   */
202
  void setComponentBounds ()
203
  {
204
    Rectangle bounds = awtComponent.getBounds ();
205
 
206
    if (bounds.x == 0 && bounds.y == 0
207
        && bounds.width == 0 && bounds.height == 0)
208
      return;
209
 
210
    setBounds (bounds.x, bounds.y, bounds.width, bounds.height);
211
  }
212
 
213
  void setVisibleAndEnabled ()
214
  {
215
    setVisible (awtComponent.isVisible ());
216
    setEnabled (awtComponent.isEnabled ());
217
  }
218
 
219
  public int checkImage (Image image, int width, int height,
220
                         ImageObserver observer)
221
  {
222
    return getToolkit().checkImage(image, width, height, observer);
223
  }
224
 
225
  public Image createImage (ImageProducer producer)
226
  {
227
    return new GtkImage (producer);
228
  }
229
 
230
  public Image createImage (int width, int height)
231
  {
232
    Image image;
233
    if (GtkToolkit.useGraphics2D ())
234
      image = new BufferedImage (width, height, BufferedImage.TYPE_INT_RGB);
235
    else
236
      image = new GtkImage (width, height);
237
 
238
    Graphics g = image.getGraphics();
239
    g.setColor(getBackground());
240
    g.fillRect(0, 0, width, height);
241
    return image;
242
  }
243
 
244
  public void disable ()
245
  {
246
    setEnabled (false);
247
  }
248
 
249
  public void enable ()
250
  {
251
    setEnabled (true);
252
  }
253
 
254
  public ColorModel getColorModel ()
255
  {
256
    return ColorModel.getRGBdefault ();
257
  }
258
 
259
  public FontMetrics getFontMetrics (Font font)
260
  {
261
    return getToolkit().getFontMetrics(font);
262
  }
263
 
264
  public Graphics getGraphics ()
265
  {
266
    if (GtkToolkit.useGraphics2D ())
267
        return new GdkGraphics2D (this);
268
    else
269
        return new GdkGraphics (this);
270
  }
271
 
272
  public Point getLocationOnScreen ()
273
  {
274
    int point[] = new int[2];
275
    if( this instanceof WindowPeer )
276
      gtkWindowGetLocationOnScreen (point);
277
    else
278
      gtkWidgetGetLocationOnScreen (point);
279
    return new Point (point[0], point[1]);
280
  }
281
 
282
  public Dimension getMinimumSize ()
283
  {
284
    return minimumSize ();
285
  }
286
 
287
  public Dimension getPreferredSize ()
288
  {
289
    return preferredSize ();
290
  }
291
 
292
  public Toolkit getToolkit ()
293
  {
294
    return Toolkit.getDefaultToolkit();
295
  }
296
 
297
  public void handleEvent (AWTEvent event)
298
  {
299
    int id = event.getID();
300
    KeyEvent ke = null;
301
 
302
    switch (id)
303
      {
304
      case PaintEvent.PAINT:
305
      case PaintEvent.UPDATE:
306
        {
307
          try
308
            {
309
              Graphics g = getGraphics ();
310
 
311
              // Some peers like GtkFileDialogPeer are repainted by Gtk itself
312
              if (g == null)
313
                break;
314
 
315
              g.setClip (((PaintEvent) event).getUpdateRect());
316
 
317
              if (id == PaintEvent.PAINT)
318
                awtComponent.paint (g);
319
              else
320
                awtComponent.update (g);
321
 
322
              g.dispose ();
323
            }
324
          catch (InternalError e)
325
            {
326
              System.err.println (e);
327
            }
328
        }
329
        break;
330
      case KeyEvent.KEY_PRESSED:
331
        ke = (KeyEvent) event;
332
        gtkWidgetDispatchKeyEvent (ke.getID (), ke.getWhen (), ke.getModifiersEx (),
333
                                   ke.getKeyCode (), ke.getKeyLocation ());
334
        break;
335
      case KeyEvent.KEY_RELEASED:
336
        ke = (KeyEvent) event;
337
        gtkWidgetDispatchKeyEvent (ke.getID (), ke.getWhen (), ke.getModifiersEx (),
338
                                   ke.getKeyCode (), ke.getKeyLocation ());
339
        break;
340
      }
341
  }
342
 
343
  public boolean isFocusTraversable ()
344
  {
345
    return true;
346
  }
347
 
348
  public Dimension minimumSize ()
349
  {
350
    int dim[] = new int[2];
351
 
352
    gtkWidgetGetPreferredDimensions (dim);
353
 
354
    return new Dimension (dim[0], dim[1]);
355
  }
356
 
357
  public void paint (Graphics g)
358
  {
359
  }
360
 
361
  public Dimension preferredSize ()
362
  {
363
    int dim[] = new int[2];
364
 
365
    gtkWidgetGetPreferredDimensions (dim);
366
 
367
    return new Dimension (dim[0], dim[1]);
368
  }
369
 
370
  public boolean prepareImage (Image image, int width, int height,
371
                               ImageObserver observer)
372
  {
373
    return getToolkit().prepareImage(image, width, height, observer);
374
  }
375
 
376
  public void print (Graphics g)
377
  {
378
    throw new RuntimeException ();
379
  }
380
 
381
  public void repaint (long tm, int x, int y, int width, int height)
382
  {
383
    if (x == 0 && y == 0 && width == 0 && height == 0)
384
      return;
385
 
386
    repaintTimer.schedule(new RepaintTimerTask(x, y, width, height), tm);
387
  }
388
 
389
  private class RepaintTimerTask extends TimerTask
390
  {
391
    private int x, y, width, height;
392
 
393
    RepaintTimerTask(int x, int y, int width, int height)
394
    {
395
      this.x = x;
396
      this.y = y;
397
      this.width = width;
398
      this.height = height;
399
    }
400
 
401
    public void run()
402
    {
403
      q().postEvent (new PaintEvent (awtComponent, PaintEvent.UPDATE,
404
                                     new Rectangle (x, y, width, height)));
405
    }
406
  }
407
 
408
  public void requestFocus ()
409
  {
410
    gtkWidgetRequestFocus();
411
    postFocusEvent(FocusEvent.FOCUS_GAINED, false);
412
  }
413
 
414
  public void reshape (int x, int y, int width, int height)
415
  {
416
    setBounds (x, y, width, height);
417
  }
418
 
419
  public void setBackground (Color c)
420
  {
421
    gtkWidgetSetBackground (c.getRed(), c.getGreen(), c.getBlue());
422
  }
423
 
424
  native void setNativeBounds (int x, int y, int width, int height);
425
 
426
  public void setBounds (int x, int y, int width, int height)
427
  {
428
    int new_x = x;
429
    int new_y = y;
430
 
431
    Component parent = awtComponent.getParent ();
432
    Component next_parent;
433
 
434
    // Heavyweight components that are children of one or more
435
    // lightweight containers have to be handled specially.  Because
436
    // calls to GLightweightPeer.setBounds do nothing, GTK has no
437
    // knowledge of the lightweight containers' positions.  So we have
438
    // to add the offsets manually when placing a heavyweight
439
    // component within a lightweight container.  The lightweight
440
    // container may itself be in a lightweight container and so on,
441
    // so we need to continue adding offsets until we reach a
442
    // container whose position GTK knows -- that is, the first
443
    // non-lightweight.
444
    boolean lightweightChild = false;
445
    Insets i;
446
    while (parent.isLightweight ())
447
      {
448
        lightweightChild = true;
449
 
450
        next_parent = parent.getParent ();
451
 
452
        i = ((Container) parent).getInsets ();
453
 
454
        if (next_parent instanceof Window)
455
          {
456
            new_x += i.left;
457
            new_y += i.top;
458
          }
459
        else
460
          {
461
            new_x += parent.getX () + i.left;
462
            new_y += parent.getY () + i.top;
463
          }
464
 
465
        parent = next_parent;
466
      }
467
 
468
    // We only need to convert from Java to GTK coordinates if we're
469
    // placing a heavyweight component in a Window.
470
    if (parent instanceof Window && !lightweightChild)
471
      {
472
        GtkWindowPeer peer = (GtkWindowPeer) parent.getPeer ();
473
        // important: we want the window peer's insets here, not the
474
        // window's, since user sub-classes of Window can override
475
        // getInset and we only want to correct for the frame borders,
476
        // not for any user-defined inset values
477
        Insets insets = peer.getInsets ();
478
 
479
        int menuBarHeight = 0;
480
        if (peer instanceof GtkFramePeer)
481
          menuBarHeight = ((GtkFramePeer) peer).getMenuBarHeight ();
482
 
483
        new_x = x - insets.left;
484
        new_y = y - insets.top + menuBarHeight;
485
      }
486
 
487
    setNativeBounds (new_x, new_y, width, height);
488
  }
489
 
490
  void setCursor ()
491
  {
492
    setCursor (awtComponent.getCursor ());
493
  }
494
 
495
  public void setCursor (Cursor cursor)
496
  {
497
    if (Thread.currentThread() == GtkToolkit.mainThread)
498
      gtkWidgetSetCursorUnlocked (cursor.getType ());
499
    else
500
      gtkWidgetSetCursor (cursor.getType ());
501
  }
502
 
503
  public void setEnabled (boolean b)
504
  {
505
    gtkWidgetSetSensitive (b);
506
  }
507
 
508
  public void setFont (Font f)
509
  {
510
    // FIXME: This should really affect the widget tree below me.
511
    // Currently this is only handled if the call is made directly on
512
    // a text widget, which implements setFont() itself.
513
    gtkWidgetModifyFont(f.getName(), f.getStyle(), f.getSize());
514
  }
515
 
516
  public void setForeground (Color c)
517
  {
518
    gtkWidgetSetForeground (c.getRed(), c.getGreen(), c.getBlue());
519
  }
520
 
521
  public Color getForeground ()
522
  {
523
    int rgb[] = gtkWidgetGetForeground ();
524
    return new Color (rgb[0], rgb[1], rgb[2]);
525
  }
526
 
527
  public Color getBackground ()
528
  {
529
    int rgb[] = gtkWidgetGetBackground ();
530
    return new Color (rgb[0], rgb[1], rgb[2]);
531
  }
532
 
533
  public native void setVisibleNative (boolean b);
534
  public native void setVisibleNativeUnlocked (boolean b);
535
 
536
  public void setVisible (boolean b)
537
  {
538
    if (Thread.currentThread() == GtkToolkit.mainThread)
539
      setVisibleNativeUnlocked (b);
540
    else
541
      setVisibleNative (b);
542
  }
543
 
544
  public void hide ()
545
  {
546
    setVisible (false);
547
  }
548
 
549
  public void show ()
550
  {
551
    setVisible (true);
552
  }
553
 
554
  protected void postMouseEvent(int id, long when, int mods, int x, int y,
555
                                int clickCount, boolean popupTrigger)
556
  {
557
    q().postEvent(new MouseEvent(awtComponent, id, when, mods, x, y,
558
                               clickCount, popupTrigger));
559
  }
560
 
561
  protected void postExposeEvent (int x, int y, int width, int height)
562
  {
563
    if (!isInRepaint)
564
      q().postEvent (new PaintEvent (awtComponent, PaintEvent.PAINT,
565
                                   new Rectangle (x, y, width, height)));
566
  }
567
 
568
  protected void postKeyEvent (int id, long when, int mods,
569
                               int keyCode, char keyChar, int keyLocation)
570
  {
571
    KeyEvent keyEvent = new KeyEvent (awtComponent, id, when, mods,
572
                                      keyCode, keyChar, keyLocation);
573
 
574
    // Also post a KEY_TYPED event if keyEvent is a key press that
575
    // doesn't represent an action or modifier key.
576
    if (keyEvent.getID () == KeyEvent.KEY_PRESSED
577
        && (!keyEvent.isActionKey ()
578
            && keyCode != KeyEvent.VK_SHIFT
579
            && keyCode != KeyEvent.VK_CONTROL
580
            && keyCode != KeyEvent.VK_ALT))
581
      {
582
        synchronized (q)
583
          {
584
            q().postEvent (keyEvent);
585
            q().postEvent (new KeyEvent (awtComponent, KeyEvent.KEY_TYPED, when, mods,
586
                                        KeyEvent.VK_UNDEFINED, keyChar, keyLocation));
587
          }
588
      }
589
    else
590
      q().postEvent (keyEvent);
591
  }
592
 
593
  protected void postFocusEvent (int id, boolean temporary)
594
  {
595
    q().postEvent (new FocusEvent (awtComponent, id, temporary));
596
  }
597
 
598
  protected void postItemEvent (Object item, int stateChange)
599
  {
600
    q().postEvent (new ItemEvent ((ItemSelectable)awtComponent,
601
                                ItemEvent.ITEM_STATE_CHANGED,
602
                                item, stateChange));
603
  }
604
 
605
  protected void postTextEvent ()
606
  {
607
    q().postEvent (new TextEvent (awtComponent, TextEvent.TEXT_VALUE_CHANGED));
608
  }
609
 
610
  public GraphicsConfiguration getGraphicsConfiguration ()
611
  {
612
    // FIXME: just a stub for now.
613
    return null;
614
  }
615
 
616
  public void setEventMask (long mask)
617
  {
618
    // FIXME: just a stub for now.
619
  }
620
 
621
  public boolean isFocusable ()
622
  {
623
    return false;
624
  }
625
 
626
  public boolean requestFocus (Component source, boolean b1,
627
                               boolean b2, long x)
628
  {
629
    return false;
630
  }
631
 
632
  public boolean isObscured ()
633
  {
634
    return false;
635
  }
636
 
637
  public boolean canDetermineObscurity ()
638
  {
639
    return false;
640
  }
641
 
642
  public void coalescePaintEvent (PaintEvent e)
643
  {
644
 
645
  }
646
 
647
  public void updateCursorImmediately ()
648
  {
649
    if (awtComponent.getCursor() != null)
650
      setCursor(awtComponent.getCursor());
651
  }
652
 
653
  public boolean handlesWheelScrolling ()
654
  {
655
    return false;
656
  }
657
 
658
  // Convenience method to create a new volatile image on the screen
659
  // on which this component is displayed.
660
  public VolatileImage createVolatileImage (int width, int height)
661
  {
662
    return new GtkVolatileImage (width, height);
663
  }
664
 
665
  // Creates buffers used in a buffering strategy.
666
  public void createBuffers (int numBuffers, BufferCapabilities caps)
667
    throws AWTException
668
  {
669
    // numBuffers == 2 implies double-buffering, meaning one back
670
    // buffer and one front buffer.
671
    if (numBuffers == 2)
672
      backBuffer = new GtkVolatileImage(awtComponent.getWidth(),
673
                                        awtComponent.getHeight(),
674
                                        caps.getBackBufferCapabilities());
675
    else
676
      throw new AWTException("GtkComponentPeer.createBuffers:"
677
                             + " multi-buffering not supported");
678
    this.caps = caps;
679
  }
680
 
681
  // Return the back buffer.
682
  public Image getBackBuffer ()
683
  {
684
    return backBuffer;
685
  }
686
 
687
  // FIXME: flip should be implemented as a fast native operation
688
  public void flip (BufferCapabilities.FlipContents contents)
689
  {
690
    getGraphics().drawImage(backBuffer,
691
                            awtComponent.getWidth(),
692
                            awtComponent.getHeight(),
693
                            null);
694
 
695
    // create new back buffer and clear it to the background color.
696
    if (contents == BufferCapabilities.FlipContents.BACKGROUND)
697
        {
698
          backBuffer = createVolatileImage(awtComponent.getWidth(),
699
                                           awtComponent.getHeight());
700
          backBuffer.getGraphics().clearRect(0, 0,
701
                                             awtComponent.getWidth(),
702
                                             awtComponent.getHeight());
703
        }
704
    // FIXME: support BufferCapabilities.FlipContents.PRIOR
705
  }
706
 
707
  // Release the resources allocated to back buffers.
708
  public void destroyBuffers ()
709
  {
710
    backBuffer.flush();
711
  }
712
 
713
  public String toString ()
714
  {
715
    return "peer of " + awtComponent.toString();
716
  }
717
  public Rectangle getBounds()
718
  {
719
      // FIXME: implement
720
    return null;
721
  }
722
  public void reparent(ContainerPeer parent)
723
  {
724
    // FIXME: implement
725
 
726
  }
727
  public void setBounds(int x, int y, int width, int height, int z)
728
  {
729
    // FIXME: implement
730
      setBounds (x, y, width, height);
731
 
732
  }
733
  public boolean isReparentSupported()
734
  {
735
    // FIXME: implement
736
 
737
    return false;
738
  }
739
  public void layout()
740
  {
741
    // FIXME: implement
742
 
743
  }
744
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.