2 * Copyright 2000-2009 JetBrains s.r.o.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
16 package com
.intellij
.openapi
.progress
.util
;
18 import com
.intellij
.util
.ui
.UIUtil
;
22 import java
.awt
.event
.ActionEvent
;
23 import java
.awt
.event
.ActionListener
;
24 import java
.awt
.event
.WindowAdapter
;
25 import java
.awt
.event
.WindowEvent
;
26 import java
.awt
.geom
.Rectangle2D
;
29 * @author Eugene Belyaev
31 public class ColorProgressBar
extends JComponent
{
32 private static final Dimension PREFERRED_SIZE
= new Dimension(146, 17);
34 public static final Color GREEN
= new Color(47, 212, 50);
35 public static final Color RED
= new Color(210, 69, 30);
36 public static final Color BLUE
= new Color(1, 68, 208);
37 public static final Color YELLOW
= new Color(212, 183, 33);
39 private static final Color SHADOW1
= new Color(190, 190, 188);
40 private static final Color SHADOW2
= new Color(105, 103, 106);
42 private static final int BRICK_WIDTH
= 6;
43 private static final int BRICK_SPACE
= 1;
45 private static final int INDETERMINATE_BRICKS_DRAW
= 5;
46 private static final double INDETERMINATE_INC_OFFSET
= 0.02;
48 private double myFraction
= 0.0;
49 private Color myColor
= BLUE
;
51 private double myIndeterminateInc
= INDETERMINATE_INC_OFFSET
;
52 private boolean myIndeterminate
= false;
54 public boolean isIndeterminate() {
55 return myIndeterminate
;
58 public void setIndeterminate(boolean indeterminate
) {
59 this.myIndeterminate
= indeterminate
;
62 public ColorProgressBar() {
66 public void setColor(Color color
) {
68 if (isDisplayable()) repaint();
71 public double getFraction() {
75 public void setFraction(double fraction
) {
76 if (myIndeterminate
) {
77 if (myFraction
>= 1.0) {
78 myIndeterminateInc
= -INDETERMINATE_INC_OFFSET
;
80 else if (myFraction
<= 0) {
81 myIndeterminateInc
= INDETERMINATE_INC_OFFSET
;
84 final boolean changed
= myFraction
== 0 || getBricksToDraw(myFraction
) != getBricksToDraw(myFraction
+ myIndeterminateInc
);
85 myFraction
+= myIndeterminateInc
;
92 boolean changed
= myFraction
== 0 || getBricksToDraw(myFraction
) != getBricksToDraw(fraction
);
93 myFraction
= fraction
;
100 private int getBricksToDraw(double fraction
) {
101 int bricksTotal
= (getWidth() - 8) / (BRICK_WIDTH
+ BRICK_SPACE
);
102 return (int)(bricksTotal
* fraction
) + 1;
105 protected void paintComponent(Graphics g
) {
106 super.paintComponent(g
);
107 if (myFraction
== 0) return;
109 Graphics2D g2
= (Graphics2D
)g
;
110 Object oldAntialiasing
= g2
.getRenderingHint(RenderingHints
.KEY_ANTIALIASING
);
111 g2
.setRenderingHint(RenderingHints
.KEY_ANTIALIASING
, RenderingHints
.VALUE_ANTIALIAS_ON
);
113 if (myFraction
> 1) {
117 Dimension size
= getSize();
119 g2
.setPaint(Color
.WHITE
);
120 Rectangle2D rect
= new Rectangle2D
.Double(2, 2, size
.width
- 4, size
.height
- 4);
123 g2
.setPaint(SHADOW1
);
124 rect
.setRect(1, 1, size
.width
- 3, size
.height
- 3);
126 UIUtil
.drawLine(g2
, 2, 2, 2, 2);
127 UIUtil
.drawLine(g2
, 2, size
.height
- 2, 2, size
.height
- 2);
128 UIUtil
.drawLine(g2
, size
.width
- 2, 2, size
.width
- 2, 2);
129 UIUtil
.drawLine(g2
, 0, 2, 0, 2);
130 UIUtil
.drawLine(g2
, 2, 0, 2, 0);
132 g2
.setPaint(SHADOW2
);
133 UIUtil
.drawLine(g2
, 0, 2, 0, size
.height
- 4);
134 UIUtil
.drawLine(g2
, 1, 1, 1, 1);
135 UIUtil
.drawLine(g2
, 2, 0, size
.width
- 3, 0);
136 UIUtil
.drawLine(g2
, 1, size
.height
- 3, 1, size
.height
- 3);
137 UIUtil
.drawLine(g2
, 2, size
.height
- 2, size
.width
- 3, size
.height
- 2);
138 UIUtil
.drawLine(g2
, size
.width
- 2, 1, size
.width
- 2, 1);
139 UIUtil
.drawLine(g2
, size
.width
- 1, 2, size
.width
- 1, size
.height
- 4);
140 UIUtil
.drawLine(g2
, size
.width
- 2, size
.height
- 3, size
.width
- 2, size
.height
- 3);
142 int y_center
= size
.height
/ 2;
143 int y_steps
= size
.height
/ 2 - 3;
144 int alpha_step
= y_steps
> 0 ?
(255 - 70) / y_steps
: 255 - 70;
147 g
.setClip(4, 3, size
.width
- 8, size
.height
- 6);
149 int bricksToDraw
= getBricksToDraw(myFraction
);
151 if (myIndeterminate
) {
153 int startFrom
= bricksToDraw
< INDETERMINATE_BRICKS_DRAW ?
0 : bricksToDraw
- INDETERMINATE_BRICKS_DRAW
;
154 int endTo
= bricksToDraw
+ INDETERMINATE_BRICKS_DRAW
< getBricksToDraw(1) ? bricksToDraw
+ INDETERMINATE_BRICKS_DRAW
: getBricksToDraw(1);
156 for (int i
= startFrom
; i
<= endTo
; i
++) {
157 g2
.setPaint(myColor
);
159 int startXOffset
= x_offset
+ (BRICK_WIDTH
+ BRICK_SPACE
) * i
;
160 UIUtil
.drawLine(g2
, startXOffset
, y_center
, startXOffset
+ BRICK_WIDTH
- 1, y_center
);
162 for (int j
= 0; j
< y_steps
; j
++) {
163 Color color
= new Color(myColor
.getRed(), myColor
.getGreen(), myColor
.getBlue(), 255 - alpha_step
* (j
+ 1));
165 UIUtil
.drawLine(g2
, startXOffset
, y_center
- 1 - j
, startXOffset
+ BRICK_WIDTH
- 1, y_center
- 1 - j
);
167 if (!(y_center
% 2 != 0 && j
== y_steps
- 1)) {
168 UIUtil
.drawLine(g2
, startXOffset
, y_center
+ 1 + j
, startXOffset
+ BRICK_WIDTH
- 1, y_center
+ 1 + j
);
172 new Color(myColor
.getRed(), myColor
.getGreen(), myColor
.getBlue(), 255 - alpha_step
* (y_steps
/ 2 + 1)));
173 g2
.drawRect(startXOffset
, y_center
- y_steps
, BRICK_WIDTH
- 1, size
.height
- 7);
177 for (int i
= 0; i
< bricksToDraw
; i
++) {
178 g2
.setPaint(myColor
);
179 UIUtil
.drawLine(g2
, x_offset
, y_center
, x_offset
+ BRICK_WIDTH
- 1, y_center
);
180 for (int j
= 0; j
< y_steps
; j
++) {
181 Color color
= new Color(myColor
.getRed(), myColor
.getGreen(), myColor
.getBlue(), 255 - alpha_step
* (j
+ 1));
183 UIUtil
.drawLine(g2
, x_offset
, y_center
- 1 - j
, x_offset
+ BRICK_WIDTH
- 1, y_center
- 1 - j
);
184 if (!(y_center
% 2 != 0 && j
== y_steps
- 1)) {
185 UIUtil
.drawLine(g2
, x_offset
, y_center
+ 1 + j
, x_offset
+ BRICK_WIDTH
- 1, y_center
+ 1 + j
);
189 new Color(myColor
.getRed(), myColor
.getGreen(), myColor
.getBlue(), 255 - alpha_step
* (y_steps
/ 2 + 1)));
190 g2
.drawRect(x_offset
, y_center
- y_steps
, BRICK_WIDTH
- 1, size
.height
- 7);
191 x_offset
+= BRICK_WIDTH
+ BRICK_SPACE
;
195 g2
.setRenderingHint(RenderingHints
.KEY_ANTIALIASING
, oldAntialiasing
);
198 public Dimension
getPreferredSize() {
199 return PREFERRED_SIZE
;
202 public Dimension
getMaximumSize() {
203 Dimension dimension
= getPreferredSize();
204 dimension
.width
= Short
.MAX_VALUE
;
208 public Dimension
getMinimumSize() {
209 Dimension dimension
= getPreferredSize();
210 dimension
.width
= 13;
214 public Color
getColor() {
218 @SuppressWarnings({"HardCodedStringLiteral"})
219 public static void main(String
[] args
) {
220 JFrame frame
= new JFrame("ColorProgressBar Test");
221 frame
.addWindowListener(
222 new WindowAdapter() {
223 public void windowClosing(WindowEvent e
) {
228 frame
.setSize(800, 600);
229 frame
.setLocation(0, 0);
230 Container contentPane
= frame
.getContentPane();
231 contentPane
.setLayout(new BorderLayout());
232 final ColorProgressBar colorProgressBar
= new ColorProgressBar();
233 colorProgressBar
.setFraction(0.5);
234 colorProgressBar
.setIndeterminate(true);
235 contentPane
.add(colorProgressBar
, BorderLayout
.NORTH
);
236 frame
.setVisible(true);
237 JButton b
= new JButton ("X");
238 b
.addActionListener(new ActionListener () {
239 public void actionPerformed(ActionEvent e
) {
240 colorProgressBar
.setFraction(1);
243 contentPane
.add(b
, BorderLayout
.SOUTH
);