i am looking at putting a progress bar into a game i am making with a count down from a random number between 5 and 20 down to 0. this is my code so far:
package Sof
Here is what I made for my game. Feel free to utilize this anyone who may find this question like I did.
Enjoy.
import java.awt.Canvas;
import java.awt.Color;
import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.Graphics;
import javax.swing.JPanel;
import com.jayavon.game.client.MyClient;
public class CustomJProgressBar extends JPanel {
private static final long serialVersionUID = 1L;
private Color color;
private int width, height;
private double minimum = 0.0;
private double maximum = 100.0;
private double value = 100.0;
private Font font = MyClient.theme_font.deriveFont(Font.PLAIN, 12);
public CustomJProgressBar(Color color) {
super();
this.color = color;
setBounds(0, 0, width, height);
setFont(font);
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
//border
g.setColor(MyClient.THEME_LIGHT_TEXT);
g.drawRect(0, 0, getWidth()-1, getHeight()-1);
//progress
int drawAmount = (int) (((value - minimum) / (maximum - minimum)) * getWidth());
g.setColor(color);
g.fillRect(1, 1, drawAmount-2, getHeight()-2); //-2 to account for border
//string painting
String stringToPaint = (int)value + "/" + (int)maximum;
Canvas c = new Canvas();
FontMetrics fm = c.getFontMetrics(font);
final int stringWidth = fm.stringWidth(stringToPaint);
final int stringHeight = fm.getHeight();
g.setColor(MyClient.THEME_LIGHT_TEXT);
g.drawString(stringToPaint, (getWidth()/2) - (stringWidth/2), ((getHeight()/2) + (stringHeight/2))-2); //-2 to account for border
}
public void setColor(Color _color){
this.color = _color;
}
public void setMinimum(double _minimum){
this.minimum = _minimum;
}
public void setMaximum(double _maximum){
this.maximum = _maximum;
}
public void setValue(double _value){
this.value = _value;
}
}
+1 to AndrewThompsons comment.
Here is a short example I made, not the best but shows the logic needed to create your own JProgressBar
from scratch by using JPanel
:
it can also be set to indeterminate:
via uncommenting:
myProgressBar.setBackground(new Color(0, 255, 0, 127));
myProgressBar.setIndeterminate(true); //if progress unknown show ball moving from side to side
CustomProgressBarTest.java:
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.RenderingHints;
import java.awt.event.ActionEvent;
import java.util.ArrayList;
import javax.swing.AbstractAction;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.Timer;
import javax.swing.border.LineBorder;
public class CustomProgressBarTest {
public CustomProgressBarTest() {
createAndShowGui();
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
new CustomProgressBarTest();
}
});
}
private void createAndShowGui() {
JFrame frame = new JFrame();
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
final MyProgressBar myProgressBar = new MyProgressBar(0, 100);
myProgressBar.setProgressColor(new Color(0, 255, 0, 127));
//myProgressBar.setIndeterminate(true); //if progress unknown show ball moving from side to side
JPanel dummyPanel = new JPanel() {
@Override
public Dimension getPreferredSize() {
return new Dimension(300, 300);
}
};
dummyPanel.add(new JLabel("DummyPanel"));
frame.add(dummyPanel);
frame.add(myProgressBar, BorderLayout.SOUTH);
frame.pack();
frame.setVisible(true);
//create timer to decrease progressbar
createAndStartDecrementTimer(myProgressBar);
//create timer to increase progressbar
//myProgressBar.setValue(0);//set to 0 so we can increment
//createAndStartIncrementTimer(myProgressBar);
}
private void createAndStartIncrementTimer(final MyProgressBar myProgressBar) {
Timer progressBarIncrementTimer = new Timer(100, new AbstractAction() {
int count = 0;
@Override
public void actionPerformed(ActionEvent ae) {
if (count == 100) {
System.out.println("Done");
((Timer) ae.getSource()).stop();
} else if (count < 100) {
//System.out.println("Here");
count++;
myProgressBar.setValue(count);
}
}
});
progressBarIncrementTimer.start();
}
private void createAndStartDecrementTimer(final MyProgressBar myProgressBar) {
Timer progressBArCountDownTimer = new Timer(100, new AbstractAction() {
int count = 100;
@Override
public void actionPerformed(ActionEvent ae) {
if (count == 0) {
System.out.println("Done");
((Timer) ae.getSource()).stop();
} else if (count > 0) {
count--;
myProgressBar.setValue(count);
System.out.println(myProgressBar.getValue());
}
}
});
progressBArCountDownTimer.start();
}
}
class MyProgressBar extends JPanel {
private final int minValue, maxValue;
private boolean indeterminate = false;
private int currentValue;
private ArrayList<Rectangle> rects = new ArrayList<>();
private Color PROGRESS_COLOR = Color.blue;
private int removeValue = 0;
private Timer indeterminateTimer;
private int x = 0, y = 0, ballSize = 25;
private boolean changeDirection = false;
public MyProgressBar(int min, int max) {
indeterminateTimer = new Timer(50, new AbstractAction() {
@Override
public void actionPerformed(ActionEvent ae) {
repaint();
}
});
maxValue = max;
minValue = min;
currentValue = maxValue;
setBorder(new LineBorder(Color.BLACK));
}
@Override
protected void paintComponent(Graphics grphcs) {
super.paintComponent(grphcs);
Graphics2D g2d = (Graphics2D) grphcs;
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
if (!indeterminate) {//if normal progress bar
rects.clear();
int rectWidths = getWidth() / maxValue;
int startingX = 0;
if (currentValue < maxValue) {//we started off with a value less than the max
for (int i = minValue; i < currentValue; i++) {
rects.add(new Rectangle(startingX, 0, rectWidths, getHeight()));
startingX += rectWidths;
}
} else {
for (int i = minValue; i < (maxValue - removeValue); i++) {
rects.add(new Rectangle(startingX, 0, rectWidths, getHeight()));
startingX += rectWidths;
}
}
for (Rectangle r : rects) {
g2d.setColor(PROGRESS_COLOR);
g2d.fillRect(r.x, r.y, r.width, r.height);
}
} else {//if indeterminate
if (!indeterminateTimer.isRunning()) {
indeterminateTimer.start();
}
g2d.setColor(PROGRESS_COLOR);
if (!changeDirection) {
if (x + 10 < getWidth() - (ballSize / 2)) {
x += 10;
} else {
changeDirection = true;
}
} else if (changeDirection) {
if (x + 10 > 0) {
x -= 10;
} else {
changeDirection = false;
}
}
g2d.fillOval(x, y, ballSize, getHeight());
}
}
int getValue() {
return currentValue;
}
public void setIndeterminate(boolean indeterminate) {
this.indeterminate = indeterminate;
}
void setValue(int value) {
if (value > maxValue) {
return;
}
if (value < minValue) {
return;
}
if (value < currentValue) {
removeValue++;
} else {
int rem = value - currentValue;
removeValue -= rem;
}
currentValue = value;
repaint();
}
void setProgressColor(Color c) {
PROGRESS_COLOR = c;
}
Color getProgressColor() {
return PROGRESS_COLOR;
}
}
You might be able to adapt ProgressIcon
, illustrated here in the tabs of a JTabbedPane
.
This is the code of a custom JProgressBar
I made long time ago (I know the question states to not use a JProgressBar
but you can grab code ideas from it), it was designed to resemble the progress bar look & feel from the "Human" theme in ubuntu 9.04:
import java.awt.AlphaComposite;
import java.awt.Color;
import java.awt.Composite;
import java.awt.FontMetrics;
import java.awt.GradientPaint;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.JProgressBar;
/**
* A progressBar that looks like the progress bar from Ubuntu 9.04 Human Theme
*/
public class HumanProgressBar extends JProgressBar {
private static final long serialVersionUID = 1L;
private static final String DISABLED_PERCENT_STRING = " --- ";
private static final Color gradientEndingColor = new Color(0xc0c0c0);
private static final Color borderColor = new Color(0x736a60);
private static final Color disabledBorderColor = new Color(0xbebebe);
private static final Composite transparent = AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 0.45f);
private static final Composite veryTransparent = AlphaComposite.getInstance(AlphaComposite.SRC_OVER, 0.25f);
private static GradientPaint gradient;
private int oldWidth;
private int oldHeight;
private int displayWidth;
private int displayHeight;
private int insets[] = new int[4];
private static final int TOP_INSET = 0;
private static final int LEFT_INSET = 1;
private static final int BOTTOM_INSET = 2;
private static final int RIGHT_INSET = 3;
private static final int PREFERRED_PERCENT_STRING_MARGIN_WIDTH = 3;
public static final Color PREFERRED_PROGRESS_COLOR = new Color(0x1869A6);
private boolean percentStringVisible = true;
private Color progressColor;
private String maxPercentString;
public HumanProgressBar() {
progressColor = PREFERRED_PROGRESS_COLOR;
}
public void updateGraphics() {
update(getGraphics());
}
@Override
protected void paintComponent(Graphics g) {
int w = displayWidth != 0 ? displayWidth - 1 : getWidth() - 1;
int h = displayHeight != 0 ? displayHeight - 1 : getHeight() - 1;
int x = insets[LEFT_INSET];
int y = insets[TOP_INSET];
w -= (insets[RIGHT_INSET] << 1);
h -= (insets[BOTTOM_INSET] << 1);
if (gradient == null) {
gradient = new GradientPaint(0.0f, 0.0f, Color.WHITE, 0.0f, h, gradientEndingColor);
}
Graphics2D g2d = (Graphics2D) g;
// Clean background
if (isOpaque()) {
g2d.setColor(getBackground());
g2d.fillRect(0, 0, getWidth(), getHeight());
}
g2d.translate(x, y);
if (percentStringVisible) {
FontMetrics fm = g.getFontMetrics();
int stringW = 0;
int stringH = 0;
g2d.setColor(getForeground());
if (isEnabled()) {
int p = getValue();
String percent = Integer.toString(p, 10) + "%";
if (p < 10) {
percent = "0" + percent;
}
if (maxPercentString == null) {
maxPercentString = Integer.toString(getMaximum(), 10) + "%";
}
stringW = fm.stringWidth(maxPercentString);
stringH = ((h - fm.getHeight()) / 2) + fm.getAscent();
g2d.drawString(percent, w - stringW, stringH);
} else {
stringW = fm.stringWidth(DISABLED_PERCENT_STRING);
stringH = ((h - fm.getHeight()) / 2) + fm.getAscent();
g2d.drawString(DISABLED_PERCENT_STRING, w - stringW, stringH);
}
w -= (stringW + PREFERRED_PERCENT_STRING_MARGIN_WIDTH);
}
// Control Border
g2d.setColor(isEnabled() ? borderColor : disabledBorderColor);
g2d.drawLine(1, 0, w - 1, 0);
g2d.drawLine(1, h, w - 1, h);
g2d.drawLine(0, 1, 0, h - 1);
g2d.drawLine(w, 1, w, h - 1);
// Fill in the progress
int min = getMinimum();
int max = getMaximum();
int total = max - min;
float dx = (float) (w - 2) / (float) total;
int value = getValue();
int progress = 0;
if (value == max) {
progress = w - 1;
} else {
progress = (int) (dx * getValue());
}
g2d.setColor(progressColor);
g2d.fillRect(1, 1, progress, h - 1);
// A gradient over the progress fill
g2d.setPaint(gradient);
g2d.setComposite(transparent);
g2d.fillRect(1, 1, w - 1, (h >> 1));
final float FACTOR = 0.20f;
g2d.fillRect(1, h - (int) (h * FACTOR), w - 1, (int) (h * FACTOR));
if (isEnabled()) {
for (int i = h; i < w; i += h) {
g2d.setComposite(veryTransparent);
g2d.setColor(Color.GRAY);
g2d.drawLine(i, 1, i, h - 1);
g2d.setColor(Color.WHITE);
g2d.drawLine(i + 1, 1, i + 1, h - 1);
}
} else {
for (int i = 0; i < w; i += h) {
g2d.setComposite(veryTransparent);
g2d.setColor(Color.RED);
g2d.drawLine(i, h - 1, i + h, 1);
g2d.setColor(Color.WHITE);
g2d.drawLine(i + 1, h - 1, i + 1 + h, 1);
}
}
}
public void setInsets(int top, int left, int bottom, int right) {
insets[TOP_INSET] = top;
insets[LEFT_INSET] = left;
insets[BOTTOM_INSET] = bottom;
insets[RIGHT_INSET] = right;
}
public void setPercentStringVisible(boolean percentStringVisible) {
this.percentStringVisible = percentStringVisible;
}
@Override
protected void paintBorder(Graphics g) {
}
@Override
public void validate() {
int w = getWidth();
int h = getHeight();
super.validate();
if (oldWidth != w || oldHeight != h) {
oldWidth = w;
oldHeight = h;
gradient = null;
}
}
@Override
public void setMaximum(int n) {
super.setMaximum(n);
maxPercentString = Integer.toString(n, 10) + "%";
}
public void setDisplaySize(int width, int height) {
displayWidth = width;
displayHeight = height;
}
public Color getProgressColor() {
return progressColor;
}
public void setProgressColor(Color progressColor) {
this.progressColor = progressColor;
}
}
Here is a test program for the component:
import javax.swing.JFrame;
import javax.swing.SwingUtilities;
public class T extends JFrame {
public T() {
super();
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
this.setLayout(null);
this.setSize(350, 75);
HumanProgressBar p = new HumanProgressBar();
p.setValue(50);
p.setBounds(15, 15, 300, 15);
this.add(p);
this.setVisible(true);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
public void run() {
new T();
}
});
}
}