Source code: gnu/java/awt/peer/gtk/GdkGraphics.java
1 /* GdkGraphics.java
2 Copyright (C) 1998, 1999, 2002, 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 gnu.classpath.Configuration;
42
43 import java.awt.Color;
44 import java.awt.Dimension;
45 import java.awt.Font;
46 import java.awt.FontMetrics;
47 import java.awt.Graphics;
48 import java.awt.Image;
49 import java.awt.Rectangle;
50 import java.awt.Shape;
51 import java.awt.SystemColor;
52 import java.awt.image.ImageObserver;
53 import java.text.AttributedCharacterIterator;
54
55 public class GdkGraphics extends Graphics
56 {
57 static
58 {
59 if (Configuration.INIT_LOAD_LIBRARY)
60 {
61 System.loadLibrary("gtkpeer");
62 }
63 initStaticState ();
64 }
65
66 static native void initStaticState();
67 private final int native_state = GtkGenericPeer.getUniqueInteger ();
68
69 Color color, xorColor;
70 GtkComponentPeer component;
71 Font font;
72 Rectangle clip;
73 GtkImage image;
74
75 int xOffset = 0;
76 int yOffset = 0;
77
78 static final int GDK_COPY = 0, GDK_XOR = 2;
79
80 native void initState (GtkComponentPeer component);
81 native void initStateUnlocked (GtkComponentPeer component);
82 native void initState (int width, int height);
83 native void initFromImage (GtkImage image);
84 native void copyState (GdkGraphics g);
85
86 GdkGraphics (GdkGraphics g)
87 {
88 color = g.color;
89 xorColor = g.xorColor;
90 font = g.font;
91 clip = new Rectangle (g.clip);
92 component = g.component;
93
94 copyState (g);
95 }
96
97 GdkGraphics (int width, int height)
98 {
99 initState (width, height);
100 color = Color.black;
101 clip = new Rectangle (0, 0, width, height);
102 font = new Font ("Dialog", Font.PLAIN, 12);
103 }
104
105 GdkGraphics (GtkImage image)
106 {
107 this.image = image;
108 initFromImage (image);
109 color = Color.black;
110 clip = new Rectangle (0, 0,
111 image.getWidth(null), image.getHeight(null));
112 font = new Font ("Dialog", Font.PLAIN, 12);
113 }
114
115 GdkGraphics (GtkComponentPeer component)
116 {
117 this.component = component;
118 font = component.awtComponent.getFont ();
119 color = Color.black;
120
121 if (component.isRealized ())
122 initComponentGraphics ();
123 else
124 connectSignals (component);
125 }
126
127 void initComponentGraphics ()
128 {
129 initState (component);
130 color = component.awtComponent.getForeground ();
131 Dimension d = component.awtComponent.getSize ();
132 clip = new Rectangle (0, 0, d.width, d.height);
133 }
134
135 // called back by native side: realize_cb
136 void initComponentGraphicsUnlocked ()
137 {
138 initStateUnlocked (component);
139 color = component.awtComponent.getForeground ();
140 Dimension d = component.awtComponent.getSize ();
141 clip = new Rectangle (0, 0, d.width, d.height);
142 }
143
144 native void connectSignals (GtkComponentPeer component);
145
146 public native void clearRect(int x, int y, int width, int height);
147
148 public void clipRect (int x, int y, int width, int height)
149 {
150 if (component != null && ! component.isRealized ())
151 return;
152
153 clip = clip.intersection (new Rectangle (x, y, width, height));
154 setClipRectangle (clip.x, clip.y, clip.width, clip.height);
155 }
156
157 public native void copyArea(int x, int y, int width, int height,
158 int dx, int dy);
159
160 public Graphics create ()
161 {
162 return new GdkGraphics (this);
163 }
164
165 public native void dispose();
166
167 public boolean drawImage (Image img, int x, int y,
168 Color bgcolor, ImageObserver observer)
169 {
170 return drawImage(img, x, y, img.getWidth(null), img.getHeight(null),
171 bgcolor, observer);
172 }
173
174 public boolean drawImage (Image img, int x, int y, ImageObserver observer)
175 {
176 return drawImage (img, x, y, null, observer);
177 }
178
179 public boolean drawImage (Image img, int x, int y, int width, int height,
180 Color bgcolor, ImageObserver observer)
181 {
182 if (img instanceof GtkImage)
183 return ((GtkImage)img).drawImage (this, x, y, width, height,
184 bgcolor, observer);
185 else
186 return (new GtkImage(img.getSource())).drawImage (this, x, y,
187 width, height,
188 bgcolor, observer);
189 }
190
191 public boolean drawImage (Image img, int x, int y, int width, int height,
192 ImageObserver observer)
193 {
194 return drawImage (img, x, y, width, height, null, observer);
195 }
196
197 public boolean drawImage (Image img, int dx1, int dy1, int dx2, int dy2,
198 int sx1, int sy1, int sx2, int sy2,
199 Color bgcolor, ImageObserver observer)
200 {
201 if (img instanceof GtkImage)
202 return ((GtkImage)img).drawImage(this, dx1, dy1, dx2, dy2,
203 sx1, sy1, sx2, sy2, bgcolor, observer);
204 else
205 return (new GtkImage(img.getSource())).drawImage(this, dx1, dy1,
206 dx2, dy2,
207 sx1, sy1, sx2, sy2,
208 bgcolor, observer);
209 }
210
211 public boolean drawImage (Image img, int dx1, int dy1, int dx2, int dy2,
212 int sx1, int sy1, int sx2, int sy2,
213 ImageObserver observer)
214 {
215 return drawImage (img, dx1, dy1, dx2, dy2,
216 sx1, sy1, sx2, sy2,
217 null, observer);
218 }
219
220 public native void drawLine(int x1, int y1, int x2, int y2);
221
222 public native void drawArc(int x, int y, int width, int height,
223 int startAngle, int arcAngle);
224 public native void fillArc(int x, int y, int width, int height,
225 int startAngle, int arcAngle);
226 public native void drawOval(int x, int y, int width, int height);
227 public native void fillOval(int x, int y, int width, int height);
228
229 public native void drawPolygon(int[] xPoints, int[] yPoints, int nPoints);
230 public native void fillPolygon(int[] xPoints, int[] yPoints, int nPoints);
231
232 public native void drawPolyline(int[] xPoints, int[] yPoints, int nPoints);
233
234 public native void drawRect(int x, int y, int width, int height);
235 public native void fillRect(int x, int y, int width, int height);
236
237 GdkFontPeer getFontPeer()
238 {
239 return (GdkFontPeer) getFont().getPeer();
240 }
241
242 native void drawString (GdkFontPeer f, String str, int x, int y);
243 public void drawString (String str, int x, int y)
244 {
245 drawString(getFontPeer(), str, x, y);
246 }
247
248
249 public void drawString (AttributedCharacterIterator ci, int x, int y)
250 {
251 throw new Error ("not implemented");
252 }
253
254 public void drawRoundRect(int x, int y, int width, int height,
255 int arcWidth, int arcHeight)
256 {
257 if (arcWidth > width)
258 arcWidth = width;
259 if (arcHeight > height)
260 arcHeight = height;
261
262 int xx = x + width - arcWidth;
263 int yy = y + height - arcHeight;
264
265 drawArc (x, y, arcWidth, arcHeight, 90, 90);
266 drawArc (xx, y, arcWidth, arcHeight, 0, 90);
267 drawArc (xx, yy, arcWidth, arcHeight, 270, 90);
268 drawArc (x, yy, arcWidth, arcHeight, 180, 90);
269
270 int y1 = y + arcHeight / 2;
271 int y2 = y + height - arcHeight / 2;
272 drawLine (x, y1, x, y2);
273 drawLine (x + width, y1, x + width, y2);
274
275 int x1 = x + arcWidth / 2;
276 int x2 = x + width - arcWidth / 2;
277 drawLine (x1, y, x2, y);
278 drawLine (x1, y + height, x2, y + height);
279 }
280
281 public void fillRoundRect (int x, int y, int width, int height,
282 int arcWidth, int arcHeight)
283 {
284 if (arcWidth > width)
285 arcWidth = width;
286 if (arcHeight > height)
287 arcHeight = height;
288
289 int xx = x + width - arcWidth;
290 int yy = y + height - arcHeight;
291
292 fillArc (x, y, arcWidth, arcHeight, 90, 90);
293 fillArc (xx, y, arcWidth, arcHeight, 0, 90);
294 fillArc (xx, yy, arcWidth, arcHeight, 270, 90);
295 fillArc (x, yy, arcWidth, arcHeight, 180, 90);
296
297 fillRect (x, y + arcHeight / 2, width, height - arcHeight + 1);
298 fillRect (x + arcWidth / 2, y, width - arcWidth + 1, height);
299 }
300
301 public Shape getClip ()
302 {
303 return getClipBounds ();
304 }
305
306 public Rectangle getClipBounds ()
307 {
308 if (clip == null)
309 return null;
310 else
311 return clip.getBounds();
312 }
313
314 public Color getColor ()
315 {
316 return color;
317 }
318
319 public Font getFont ()
320 {
321 return font;
322 }
323
324 public FontMetrics getFontMetrics (Font font)
325 {
326 return new GdkFontMetrics (font);
327 }
328
329 native void setClipRectangle (int x, int y, int width, int height);
330
331 public void setClip (int x, int y, int width, int height)
332 {
333 if ((component != null && ! component.isRealized ())
334 || clip == null)
335 return;
336
337 clip.x = x;
338 clip.y = y;
339 clip.width = width;
340 clip.height = height;
341
342 setClipRectangle (x, y, width, height);
343 }
344
345 public void setClip (Rectangle clip)
346 {
347 setClip (clip.x, clip.y, clip.width, clip.height);
348 }
349
350 public void setClip (Shape clip)
351 {
352 if (clip == null)
353 {
354 // Reset clipping.
355 Dimension d = component.awtComponent.getSize();
356 setClip(new Rectangle (0, 0, d.width, d.height));
357 }
358 else
359 setClip(clip.getBounds());
360 }
361
362 private native void setFGColor(int red, int green, int blue);
363
364 public void setColor (Color c)
365 {
366 if (c == null)
367 color = Color.BLACK;
368 else
369 color = c;
370
371 if (xorColor == null) /* paint mode */
372 setFGColor (color.getRed (), color.getGreen (), color.getBlue ());
373 else /* xor mode */
374 setFGColor (color.getRed () ^ xorColor.getRed (),
375 color.getGreen () ^ xorColor.getGreen (),
376 color.getBlue () ^ xorColor.getBlue ());
377 }
378
379 public void setFont (Font font)
380 {
381 this.font = font;
382 }
383
384 native void setFunction (int gdk_func);
385
386 public void setPaintMode ()
387 {
388 xorColor = null;
389
390 setFunction (GDK_COPY);
391 setFGColor (color.getRed (), color.getGreen (), color.getBlue ());
392 }
393
394 public void setXORMode (Color c)
395 {
396 xorColor = c;
397
398 setFunction (GDK_XOR);
399 setFGColor (color.getRed () ^ xorColor.getRed (),
400 color.getGreen () ^ xorColor.getGreen (),
401 color.getBlue () ^ xorColor.getBlue ());
402 }
403
404 public native void translateNative(int x, int y);
405
406 public void translate (int x, int y)
407 {
408 if (component != null && ! component.isRealized ())
409 return;
410
411 clip.x -= x;
412 clip.y -= y;
413
414 translateNative (x, y);
415 }
416 }