如何在不使用JProgressBar的情况下制作进度条?

我正在考虑将进度条放入我正在制作的游戏中,从5到20之间的随机数减少到0。这是我的代码到目前为止:

包软件;

import java.awt.Color; import java.awt.Graphics; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import javax.swing.JPanel; import javax.swing.Timer; public class CountDownProgressBar extends JPanel { RandomValues randomNum; int timeValue; Timer timer; int length, newLength; public CountDownProgressBar() { timer = new Timer(24, new ActionListener() { @Override public void actionPerformed(ActionEvent e) { for (int i = timeValue; i > 0; --i) { newLength = length - (length / timeValue); length = newLength; repaint(); } } }); randomNum = new RandomValues(); this.timeValue = 0; this.setBackground(Color.GRAY); } @Override public void paint(Graphics g) { super.paintComponent(g); g.setColor(Color.green); g.fillRect(0, 0, length, 50); } public void setTimeLength() { this.timeValue = randomNum.integer(5, 20); } public int getTimeLength() { return this.timeValue; } } 

我知道大部分都是错的,我只是想弄清楚怎么做。 它不需要使用JProgressBar,而是使用图形(绿色矩形),它变得越来越小,时间倒计时。 我将如何制作它以使屏幕可以resize,并且条形图仍将相对于屏幕尺寸倒计时。 所以它不是一个固定的大小,而只是穿过屏幕的底部。

这是我很久以前制作的自定义JProgressBar的代码(我知道问题表明不使用JProgressBar但你可以从中获取代码思想),它的设计类似于“人类”的进度条外观和感觉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; } } 

这是组件的测试程序:

 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(); } }); } } 

在此处输入图像描述

您可能能够调整ProgressIcon ,如JTabbedPane的选项卡中所示。

图片

+1给AndrewThompsons评论。

这是我做的一个简短示例,不是最好的,但显示了使用JPanel从头创建自己的JProgressBar所需的逻辑:

在此处输入图像描述

它也可以设置为不确定:

在此处输入图像描述

通过取消注释:

  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 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(rx, ry, 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; } } 

这是我为我的游戏所做的。 随意使用这个可能像我一样找到这个问题的人。

请享用。

 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; } }