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

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-dev/] [or1k-gcc/] [libjava/] [classpath/] [gnu/] [java/] [awt/] [peer/] [x/] [XGraphics2D.java] - Blame information for rev 769

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 769 jeremybenn
/* XGraphics2D.java -- A Java based Graphics2D impl for X
2
   Copyright (C) 2006 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
package gnu.java.awt.peer.x;
39
 
40
import java.awt.Color;
41
import java.awt.Font;
42
import java.awt.Graphics;
43
import java.awt.GraphicsConfiguration;
44
import java.awt.Image;
45
import java.awt.Paint;
46
import java.awt.Rectangle;
47
import java.awt.Shape;
48
import java.awt.Toolkit;
49
import java.awt.Transparency;
50
import java.awt.geom.AffineTransform;
51
import java.awt.image.BufferedImage;
52
import java.awt.image.ColorModel;
53
import java.awt.image.DataBuffer;
54
import java.awt.image.ImageObserver;
55
import java.awt.image.Raster;
56
import java.awt.peer.FontPeer;
57
import java.util.HashMap;
58
import java.util.WeakHashMap;
59
 
60
import gnu.java.awt.image.AsyncImage;
61
import gnu.java.awt.java2d.AbstractGraphics2D;
62
import gnu.java.awt.java2d.ScanlineCoverage;
63
import gnu.x11.Colormap;
64
import gnu.x11.Drawable;
65
import gnu.x11.GC;
66
import gnu.x11.image.ZPixmap;
67
 
68
public class XGraphics2D
69
  extends AbstractGraphics2D
70
{
71
 
72
  /**
73
   * When this property is set to true, then images are always rendered as
74
   * opaque images, ignoring their translucence. This is intended for
75
   * debugging and demonstration purposes.
76
   */
77
  private static final boolean RENDER_OPAQUE =
78
    Boolean.getBoolean("escherpeer.renderopaque");
79
 
80
  /**
81
   * The X Drawable to draw on.
82
   */
83
  private Drawable xdrawable;
84
 
85
  /**
86
   * The X graphics context (GC).
87
   */
88
  private GC xgc;
89
 
90
  /**
91
   * Indicates if this graphics has already been disposed.
92
   */
93
  private boolean disposed;
94
 
95
  /**
96
   * The current foreground color, possibly null.
97
   */
98
  private Color foreground;
99
 
100
  XGraphics2D(Drawable d)
101
  {
102
    super();
103
    xdrawable = d;
104
    xgc = new GC(d);
105
    init();
106
    disposed = false;
107
    //setClip(new Rectangle(0, 0, xdrawable.width, xdrawable.height));
108
  }
109
 
110
  @Override
111
  protected void rawDrawLine(int x0, int y0, int x1, int y1)
112
  {
113
    xdrawable.segment(xgc, x0, y0, x1, y1);
114
  }
115
 
116
  @Override
117
  protected void rawDrawRect(int x, int y, int w, int h)
118
  {
119
    xdrawable.rectangle(xgc, x, y, w, h, false);
120
  }
121
 
122
  @Override
123
  protected void rawFillRect(int x, int y, int w, int h)
124
  {
125
    xdrawable.rectangle(xgc, x, y, w, h, true);
126
  }
127
 
128
  /**
129
   * Returns the color model of this Graphics object.
130
   *
131
   * @return the color model of this Graphics object
132
   */
133
  protected ColorModel getColorModel()
134
  {
135
    return Toolkit.getDefaultToolkit().getColorModel();
136
  }
137
 
138
  /**
139
   * Returns the color model of the target device.
140
   *
141
   * @return the color model of the target device
142
   */
143
  protected ColorModel getDestinationColorModel()
144
  {
145
    return Toolkit.getDefaultToolkit().getColorModel();
146
  }
147
 
148
  /**
149
   * Returns the bounds of the target.
150
   *
151
   * @return the bounds of the target
152
   */
153
  protected Rectangle getDeviceBounds()
154
  {
155
    return new Rectangle(0, 0, xdrawable.width, xdrawable.height);
156
  }
157
 
158
  public GraphicsConfiguration getDeviceConfiguration()
159
  {
160
    // FIXME: Implement this.
161
    throw new UnsupportedOperationException("Not yet implemented");
162
  }
163
 
164
  public void dispose()
165
  {
166
    if (!disposed)
167
      {
168
        xgc.free();
169
        xdrawable.display.flush();
170
        disposed = true;
171
      }
172
  }
173
 
174
  public Graphics create()
175
  {
176
    // super.create() returns a copy created by clone(), so it should
177
    // be a XGraphics2D.
178
    XGraphics2D copy = (XGraphics2D) super.create();
179
    copy.xgc = xgc.copy();
180
    return copy;
181
  }
182
 
183
  public void setClip(Shape c)
184
  {
185
    super.setClip(c);
186
    if (c instanceof Rectangle)
187
      {
188
        Rectangle r = (Rectangle) c;
189
        AffineTransform t = getTransform();
190
        int translateX = (int) t.getTranslateX();
191
        //System.err.println("translateX: " + translateX);
192
        int translateY = (int) t.getTranslateY();
193
        //System.err.println("translateY: " + translateY);
194
        //System.err.println("clip: " + c);
195
        gnu.x11.Rectangle clip = new gnu.x11.Rectangle(r.x, r.y, r.width,
196
                                                       r.height);
197
        xgc.set_clip_rectangles(translateX, translateY,
198
                                new gnu.x11.Rectangle[]{clip}, GC.UN_SORTED);
199
      }
200
  }
201
 
202
  /**
203
   * Notifies the backend that the raster has changed in the specified
204
   * rectangular area. The raster that is provided in this method is always
205
   * the same as the one returned in {@link #getDestinationRaster}.
206
   * Backends that reflect changes to this raster directly don't need to do
207
   * anything here.
208
   *
209
   * @param raster the updated raster, identical to the raster returned
210
   *        by {@link #getDestinationRaster()}
211
   * @param x the upper left corner of the updated region, X coordinate
212
   * @param y the upper lef corner of the updated region, Y coordinate
213
   * @param w the width of the updated region
214
   * @param h the height of the updated region
215
   */
216
  protected void updateRaster(Raster raster, int x, int y, int w, int h)
217
  {
218
    if (w > 0 && h > 0)
219
      {
220
        ZPixmap zPixmap = new ZPixmap(xdrawable.display, w, h,
221
                                      xdrawable.display.default_pixmap_format);
222
        int[] pixel = null;
223
        int x1 = x + w;
224
        int y1 = y + h;
225
        for (int tx = x; tx < x1; tx++)
226
          {
227
            for (int ty = y; ty < y1; ty++)
228
              {
229
                pixel = raster.getPixel(tx, ty, pixel);
230
                //System.err.println("tx: " + tx + ", ty: " + ty + ", pixel: " + pixel[0] + ", " + pixel[1] + ", " + pixel[2]);
231
//              System.err.print("r: " + pixel[0]);
232
//              System.err.print(", g: " + pixel[1]);
233
//              System.err.println(", b: " + pixel[2]);
234
                zPixmap.set_red(tx - x, ty - y, pixel[0]);
235
                zPixmap.set_green(tx - x, ty - y, pixel[1]);
236
                zPixmap.set_blue(tx - x, ty - y, pixel[2]);
237
              }
238
          }
239
        xdrawable.put_image(xgc, zPixmap, x, y);
240
      }
241
  }
242
 
243
  @Override
244
  public void renderScanline(int y, ScanlineCoverage c)
245
  {
246
    if (y >= xdrawable.height)
247
      return;
248
 
249
    // TODO: Handle Composite and Paint.
250
    ScanlineCoverage.Iterator iter = c.iterate();
251
    int coverageAlpha = 0;
252
    int maxCoverage = c.getMaxCoverage();
253
    while (iter.hasNext())
254
      {
255
        ScanlineCoverage.Range range = iter.next();
256
 
257
        coverageAlpha = range.getCoverage();
258
        int x0 = range.getXPos();
259
        int l = range.getLength();
260
        if (coverageAlpha == c.getMaxCoverage())
261
          {
262
            // Simply paint the current color over the existing pixels.
263
            xdrawable.fill_rectangle(xgc, x0, y, l, 1);
264
          }
265
        else if (coverageAlpha > 0)
266
          {
267
            // Composite the current color with the existing pixels.
268
            int x1 = x0 + l;
269
            x0 = Math.min(Math.max(0, x0), xdrawable.width - 1);
270
            x1 = Math.min(Math.max(0, x1), xdrawable.width - 1);
271
            if ((x1 - x0) < 1)
272
              continue;
273
            l = x1 - x0;
274
            gnu.x11.image.ZPixmap existing = (ZPixmap)
275
            xdrawable.image(x0, y, l, 1, 0xFFFFFFFF,
276
                            gnu.x11.image.Image.Format.ZPIXMAP);
277
            for (int x = 0; x < l; x++)
278
              {
279
                Color col = getColor();
280
                if (col == null)
281
                  {
282
                    col = Color.BLACK;
283
                  }
284
                int red = col.getRed();
285
                int green = col.getGreen();
286
                int blue = col.getBlue();
287
                int redOut = existing.get_red(x, 0);
288
                int greenOut = existing.get_green(x, 0);
289
                int blueOut = existing.get_blue(x, 0);
290
                int outAlpha = maxCoverage - coverageAlpha;
291
                redOut = redOut * outAlpha + red * coverageAlpha;
292
                redOut = redOut / maxCoverage;
293
                greenOut = greenOut * outAlpha + green * coverageAlpha;
294
                greenOut = greenOut / maxCoverage;
295
                blueOut = blueOut * outAlpha + blue * coverageAlpha;
296
                blueOut = blueOut / maxCoverage;
297
                existing.set(x, 0, redOut, greenOut, blueOut);
298
              }
299
            xdrawable.put_image(xgc, existing, x0, y);
300
          }
301
      }
302
  }
303
 
304
  protected void init()
305
  {
306
    super.init();
307
  }
308
 
309
  public void setPaint(Paint p)
310
  {
311
    super.setPaint(p);
312
    if (p instanceof Color)
313
      {
314
        // TODO: Optimize for different standard bit-depths.
315
        Color c = (Color) p;
316
       /* XToolkit tk = (XToolkit) Toolkit.getDefaultToolkit();
317
        HashMap colorMap = tk.colorMap;
318
        gnu.x11.Color col = (gnu.x11.Color) colorMap.get(c);
319
        if (col == null)
320
          {
321
            Colormap map = xdrawable.display.default_colormap;
322
            col = map.alloc_color (c.getRed() * 256,
323
                                   c.getGreen() * 256,
324
                                   c.getBlue() * 256);
325
            colorMap.put(c, col);
326
          }*/
327
        //xgc.set_foreground(col);
328
 
329
        xgc.set_foreground(c.getRGB());
330
        foreground = c;
331
      }
332
  }
333
 
334
  protected void fillShape(Shape s, boolean isFont)
335
  {
336
    synchronized (xdrawable.display) {
337
      super.fillShape(s, isFont);
338
    }
339
  }
340
 
341
  private static WeakHashMap<Image,ZPixmap> imageCache = new WeakHashMap<Image,ZPixmap>();
342
 
343
  protected boolean rawDrawImage(Image image, int x, int y, ImageObserver obs)
344
  {
345
    image = unwrap(image);
346
    boolean ret;
347
    if (image instanceof XImage)
348
      {
349
        XImage xImage = (XImage) image;
350
        xdrawable.copy_area(xImage.pixmap, xgc, 0, 0, xImage.getWidth(obs),
351
                            xImage.getHeight(obs), x, y);
352
        ret = true;
353
      }
354
    else if (image instanceof PixmapVolatileImage)
355
      {
356
        PixmapVolatileImage pvi = (PixmapVolatileImage) image;
357
        xdrawable.copy_area(pvi.getPixmap(), xgc, 0, 0, pvi.getWidth(obs),
358
                            pvi.getHeight(obs), x, y);
359
        ret = true;
360
      }
361
    else if (image instanceof BufferedImage)
362
      {
363
        BufferedImage bi = (BufferedImage) image;
364
        DataBuffer db = bi.getRaster().getDataBuffer();
365
        if (db instanceof ZPixmapDataBuffer)
366
          {
367
            ZPixmapDataBuffer zpmdb = (ZPixmapDataBuffer) db;
368
            ZPixmap zpixmap = zpmdb.getZPixmap();
369
            xdrawable.put_image(xgc, zpixmap, x, y);
370
            ret = true;
371
          }
372
        else
373
          {
374
            int transparency = bi.getTransparency();
375
            int w = bi.getWidth();
376
            int h = bi.getHeight();
377
            if (imageCache.containsKey(image))
378
              {
379
                ZPixmap zpixmap = imageCache.get(image);
380
                xdrawable.put_image(xgc, zpixmap, x, y);
381
              }
382
            else if (transparency == Transparency.OPAQUE || RENDER_OPAQUE)
383
              {
384
                XGraphicsDevice gd = XToolkit.getDefaultDevice();
385
                ZPixmap zpixmap = new ZPixmap(gd.getDisplay(), w, h);
386
                for (int yy = 0; yy < h; yy++)
387
                  {
388
                    for (int xx = 0; xx < w; xx++)
389
                      {
390
                        int rgb = bi.getRGB(xx, yy);
391
                        zpixmap.set(xx, yy, rgb);
392
                      }
393
                  }
394
                xdrawable.put_image(xgc, zpixmap, x, y);
395
                imageCache.put(image, zpixmap);
396
              } else {
397
 
398
                // TODO optimize reusing the rectangles
399
                Rectangle source =
400
                  new Rectangle(0, 0, xdrawable.width, xdrawable.height);
401
                Rectangle target = new Rectangle(x, y, w, h);
402
 
403
                Rectangle destination = source.intersection(target);
404
 
405
                x = destination.x;
406
                y = destination.y;
407
                w = destination.width;
408
                h = destination.height;
409
 
410
                ZPixmap zpixmap =
411
                  (ZPixmap) xdrawable.image(x, y, w, h,
412
                                            0xffffffff,
413
                                            gnu.x11.image.Image.Format.ZPIXMAP);
414
                for (int yy = 0; yy < h; yy++)
415
                  {
416
                    for (int xx = 0; xx < w; xx++)
417
                      {
418
                        int rgb = bi.getRGB(xx, yy);
419
                        int alpha = 0xff & (rgb >> 24);
420
                        if (alpha == 0)
421
                          {
422
                            // Completely translucent.
423
                            rgb = zpixmap.get_red(xx, yy) << 16
424
                                  | zpixmap.get_green(xx, yy) << 8
425
                                  | zpixmap.get_blue(xx, yy);
426
                          }
427
                        else if (alpha < 255)
428
                          {
429
                            // Composite pixels.
430
                            int red = 0xff & (rgb >> 16);
431
                            red = red * alpha
432
                                     + (255 - alpha) * zpixmap.get_red(xx, yy);
433
                            red = red / 255;
434
                            int green = 0xff & (rgb >> 8);
435
                            green = green * alpha
436
                                   + (255 - alpha) * zpixmap.get_green(xx, yy);
437
                            green = green / 255;
438
                            int blue = 0xff & rgb;
439
                            blue = blue * alpha
440
                                    + (255 - alpha) * zpixmap.get_blue(xx, yy);
441
                            blue = blue / 255;
442
                            rgb = red << 16 | green << 8 | blue;
443
                          }
444
                        // else keep rgb value from source image.
445
 
446
                        zpixmap.set(xx, yy, rgb);
447
                      }
448
                  }
449
                xdrawable.put_image(xgc, zpixmap, x, y);
450
                // We can't cache prerendered translucent images, because
451
                // we never know how the background changes.
452
              }
453
            ret = true;
454
          }
455
      }
456
    else
457
      {
458
        ret = super.rawDrawImage(image, x, y, obs);
459
      }
460
    return ret;
461
  }
462
 
463
  public void setFont(Font f)
464
  {
465
    super.setFont(f);
466
    FontPeer p = getFont().getPeer();
467
    if (p instanceof XFontPeer)
468
      {
469
        XFontPeer xFontPeer = (XFontPeer) p;
470
        xgc.set_font(xFontPeer.getXFont());
471
      }
472
  }
473
 
474
  public void drawString(String s, int x, int y)
475
  {
476
    FontPeer p = getFont().getPeer();
477
    if (p instanceof XFontPeer)
478
      {
479
        int tx = (int) transform.getTranslateX();
480
        int ty = (int) transform.getTranslateY();
481
        xdrawable.text(xgc, x + tx, y + ty, s);
482
      }
483
    else
484
      {
485
        super.drawString(s, x, y);
486
      }
487
  }
488
 
489
  /**
490
   * Extracts an image instance out of an AsyncImage. If the image isn't
491
   * an AsyncImage, then the original instance is returned.
492
   *
493
   * @param im the image
494
   *
495
   * @return the image to render
496
   */
497
  private Image unwrap(Image im)
498
  {
499
    Image image = im;
500
    if (image instanceof AsyncImage)
501
      {
502
        AsyncImage aIm = (AsyncImage) image;
503
        image = aIm.getRealImage();
504
      }
505
    return image;
506
  }
507
 
508
}

powered by: WebSVN 2.1.0

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