Commit | Line | Data |
---|---|---|
86057589 | 1 | package be.nikiroo.utils.ui; |
8caeb8bd | 2 | |
ef13cd7f NR |
3 | import java.awt.Color; |
4 | import java.awt.GradientPaint; | |
5 | import java.awt.Graphics; | |
6 | import java.awt.Graphics2D; | |
7 | import java.awt.Paint; | |
8 | import java.awt.RadialGradientPaint; | |
9 | import java.awt.RenderingHints; | |
10 | ||
8caeb8bd NR |
11 | import javax.swing.UIManager; |
12 | import javax.swing.UnsupportedLookAndFeelException; | |
13 | ||
14 | /** | |
15 | * Some Java Swing utilities. | |
16 | * | |
17 | * @author niki | |
18 | */ | |
19 | public class UIUtils { | |
20 | /** | |
21 | * Set a fake "native look & feel" for the application if possible | |
22 | * (check for the one currently in use, then try GTK). | |
23 | * <p> | |
24 | * <b>Must</b> be called prior to any GUI work. | |
25 | */ | |
26 | static public void setLookAndFeel() { | |
27 | // native look & feel | |
28 | try { | |
29 | String noLF = "javax.swing.plaf.metal.MetalLookAndFeel"; | |
30 | String lf = UIManager.getSystemLookAndFeelClassName(); | |
31 | if (lf.equals(noLF)) | |
32 | lf = "com.sun.java.swing.plaf.gtk.GTKLookAndFeel"; | |
33 | UIManager.setLookAndFeel(lf); | |
34 | } catch (InstantiationException e) { | |
35 | } catch (ClassNotFoundException e) { | |
36 | } catch (UnsupportedLookAndFeelException e) { | |
37 | } catch (IllegalAccessException e) { | |
38 | } | |
39 | } | |
db0af0d9 NR |
40 | |
41 | /** | |
42 | * Draw a 3D-looking ellipse at the given location, if the given | |
43 | * {@link Graphics} object is compatible (with {@link Graphics2D}); draw a | |
44 | * simple ellipse if not. | |
45 | * | |
46 | * @param g | |
47 | * the {@link Graphics} to draw on | |
48 | * @param color | |
49 | * the base colour | |
50 | * @param x | |
51 | * the X coordinate | |
52 | * @param y | |
53 | * the Y coordinate | |
54 | * @param width | |
55 | * the width radius | |
56 | * @param height | |
57 | * the height radius | |
58 | */ | |
59 | static public void drawEllipse3D(Graphics g, Color color, int x, int y, int width, int height) { | |
60 | drawEllipse3D(g, color, x, y, width, height, true); | |
61 | } | |
ef13cd7f NR |
62 | |
63 | /** | |
64 | * Draw a 3D-looking ellipse at the given location, if the given | |
65 | * {@link Graphics} object is compatible (with {@link Graphics2D}); draw a | |
66 | * simple ellipse if not. | |
67 | * | |
68 | * @param g | |
69 | * the {@link Graphics} to draw on | |
70 | * @param color | |
71 | * the base colour | |
72 | * @param x | |
73 | * the X coordinate | |
74 | * @param y | |
75 | * the Y coordinate | |
76 | * @param width | |
77 | * the width radius | |
78 | * @param height | |
79 | * the height radius | |
db0af0d9 NR |
80 | * @param fill |
81 | * fill the content of the ellipse | |
ef13cd7f NR |
82 | */ |
83 | static public void drawEllipse3D(Graphics g, Color color, int x, int y, | |
db0af0d9 | 84 | int width, int height, boolean fill) { |
ef13cd7f NR |
85 | if (g instanceof Graphics2D) { |
86 | Graphics2D g2 = (Graphics2D) g; | |
87 | g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, | |
88 | RenderingHints.VALUE_ANTIALIAS_ON); | |
89 | ||
90 | // Retains the previous state | |
91 | Paint oldPaint = g2.getPaint(); | |
92 | ||
93 | // Base shape | |
94 | g2.setColor(color); | |
db0af0d9 NR |
95 | if (fill) { |
96 | g2.fillOval(x, y, width, height); | |
97 | } else { | |
98 | g2.drawOval(x, y, width, height); | |
99 | } | |
100 | ||
ef13cd7f NR |
101 | // Compute dark/bright colours |
102 | Paint p = null; | |
db0af0d9 NR |
103 | Color dark = color.darker().darker(); |
104 | Color bright = color.brighter().brighter(); | |
ef13cd7f NR |
105 | Color darkEnd = new Color(dark.getRed(), dark.getGreen(), |
106 | dark.getBlue(), 0); | |
107 | Color darkPartial = new Color(dark.getRed(), dark.getGreen(), | |
108 | dark.getBlue(), 64); | |
109 | Color brightEnd = new Color(bright.getRed(), bright.getGreen(), | |
110 | bright.getBlue(), 0); | |
111 | ||
112 | // Adds shadows at the bottom left | |
113 | p = new GradientPaint(0, height, dark, width, 0, darkEnd); | |
114 | g2.setPaint(p); | |
db0af0d9 NR |
115 | if (fill) { |
116 | g2.fillOval(x, y, width, height); | |
117 | } else { | |
118 | g2.drawOval(x, y, width, height); | |
119 | } | |
ef13cd7f NR |
120 | // Adds highlights at the top right |
121 | p = new GradientPaint(width, 0, bright, 0, height, brightEnd); | |
122 | g2.setPaint(p); | |
db0af0d9 NR |
123 | if (fill) { |
124 | g2.fillOval(x, y, width, height); | |
125 | } else { | |
126 | g2.drawOval(x, y, width, height); | |
127 | } | |
128 | ||
ef13cd7f NR |
129 | // Darken the edges |
130 | p = new RadialGradientPaint(x + width / 2f, y + height / 2f, | |
131 | Math.min(width / 2f, height / 2f), new float[] { 0f, 1f }, | |
132 | new Color[] { darkEnd, darkPartial }, | |
133 | RadialGradientPaint.CycleMethod.NO_CYCLE); | |
134 | g2.setPaint(p); | |
db0af0d9 NR |
135 | if (fill) { |
136 | g2.fillOval(x, y, width, height); | |
137 | } else { | |
138 | g2.drawOval(x, y, width, height); | |
139 | } | |
ef13cd7f NR |
140 | |
141 | // Adds inner highlight at the top right | |
142 | p = new RadialGradientPaint(x + 3f * width / 4f, y + height / 4f, | |
143 | Math.min(width / 4f, height / 4f), | |
144 | new float[] { 0.0f, 0.8f }, | |
145 | new Color[] { bright, brightEnd }, | |
146 | RadialGradientPaint.CycleMethod.NO_CYCLE); | |
147 | g2.setPaint(p); | |
db0af0d9 NR |
148 | if (fill) { |
149 | g2.fillOval(x * 2, y, width, height); | |
150 | } else { | |
151 | g2.drawOval(x * 2, y, width, height); | |
152 | } | |
ef13cd7f NR |
153 | |
154 | // Reset original paint | |
155 | g2.setPaint(oldPaint); | |
156 | } else { | |
157 | g.setColor(color); | |
db0af0d9 NR |
158 | if (fill) { |
159 | g.fillOval(x, y, width, height); | |
160 | } else { | |
161 | g.drawOval(x, y, width, height); | |
162 | } | |
ef13cd7f NR |
163 | } |
164 | } | |
8caeb8bd | 165 | } |