进度条对齐

时间:2015-11-11 20:54:17

标签: java multithreading swing

我是多线程和swing的初学者。我正在尝试使用多个进度条创建一个像图像中那样的表单。到目前为止我已经提出了下面的代码。我在水平对齐中有几个条形但是如何如下图所示,我是将它们竖直堆叠在一起吗?

Progress bar with progress off different threads      import java.awt。;     import java.awt.event。;     import javax.swing。*;

public class ThreadtestApplication extends JPanel
                             implements ActionListener {
    public final static int ONE_SECOND = 1000;

    private JProgressBar progressBar;
    private JProgressBar progressBar2;
    private JProgressBar progressBar3;
    private JProgressBar progressBar4;
    private Timer timer;
    private JButton startButton;
    private JButton ThreadTotal;
    private JButton GrandTotal;
    private SampleTask task;
//    private JTextArea taskOutput;
    private String newline = "\n";

    public ThreadtestApplication() {
        super(new BorderLayout());
        task = new SampleTask();

        //Create the demo's UI.
        startButton = new JButton("Start");
        startButton.setActionCommand("start");
        startButton.addActionListener(this);
//        
//        pauseButton = new JButton("Pause");
//        pauseButton.setActionCommand("pause");
//        pauseButton.addActionListener(this);
//        
//        resumeButton = new JButton("Resume");
//        resumeButton.setActionCommand("resume");
//        resumeButton.addActionListener(this);
//        

        progressBar = new JProgressBar(0, task.getLengthOfTask());
        progressBar.setValue(0);
        progressBar.setStringPainted(true);

        progressBar2 = new JProgressBar(0, task.getLengthOfTask());
        progressBar2.setValue(0);
        progressBar2.setStringPainted(true);

        progressBar3 = new JProgressBar(0, task.getLengthOfTask());
        progressBar3.setValue(0);
        progressBar3.setStringPainted(true);


        progressBar4 = new JProgressBar(0, task.getLengthOfTask());
        progressBar4.setValue(0);
        progressBar4.setStringPainted(true);


//        taskOutput = new JTextArea(5, 20);
//        taskOutput.setMargin(new Insets(5,5,5,5));
//        taskOutput.setEditable(false);
//        taskOutput.setCursor(null); //inherit the panel's cursor
                                    //see bug 4851758

        JPanel panel = new JPanel();
        panel.add(startButton);
//        panel.add(pauseButton);
//        panel.add(resumeButton);s
        panel.add(progressBar);
        panel.add(progressBar2);
        panel.add(progressBar3);
        panel.add(progressBar3);


        add(panel, BorderLayout.EAST);
//        add(progressBar, BorderLayout.NORTH);
//        add(progressBar2, BorderLayout.NORTH);

//        add(progressBar4, BorderLayout.NORTH);
//        add(new JScrollPane(taskOutput), BorderLayout.CENTER);
        setBorder(BorderFactory.createEmptyBorder(20, 800, 200, 20));
        startButton.setBounds(200, 1000, 100, 20);

        //Create a timer.
        timer = new Timer(ONE_SECOND, new ActionListener() {
            public void actionPerformed(ActionEvent evt) {
                progressBar.setValue(task.getCurrent());
                String s = task.getMessage();
                if (s != null) {
//                    taskOutput.append(s + newline);
//                    taskOutput.setCaretPosition(
//                            taskOutput.getDocument().getLength());
                }
                if (task.isDone()) {
                    Toolkit.getDefaultToolkit().beep();
                    timer.stop();
                    startButton.setEnabled(true);
                    setCursor(null); //turn off the wait cursor
                    progressBar.setValue(progressBar.getMinimum());
                }
            }
        });
    }

    /**
     * Called when the user presses the start button.
     */
    public void actionPerformed(ActionEvent evt) {
        startButton.setEnabled(false);
        setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
        task.go();
        timer.start();
    }

    /**
     * Create the GUI and show it.  For thread safety,
     * this method should be invoked from the
     * event-dispatching thread.
     */
    private static void make() {
//        //Make sure we have nice window decorations.
//        JFrame.setDefaultLookAndFeelDecorated(true);

        //Create and set up the window.
        JFrame frame = new JFrame("Thread Test Application");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        //Create and set up the content pane.
        JComponent newContentPane = new ThreadtestApplication();
        newContentPane.setOpaque(true); //content panes must be opaque
        frame.setContentPane(newContentPane);

        //Display the window.
       frame.pack();
        frame.setVisible(true);
    }

    public static void main(String[] args) {
        //Schedule a job for the event-dispatching thread:
        //creating and showing this application's GUI.
        javax.swing.SwingUtilities.invokeLater(new Runnable() {
            public void run() {
                make();
            }
        });
    }
}
class SampleTask {
    private int lengthOfTask;
    private int current = 0;
    private boolean done = false;
    private boolean canceled = false;
    private String statMessage;

    public SampleTask() {
        //Compute length of task...
        lengthOfTask = 1000;
    }

    /**
     * Called from Thread test Application to start the task.
     */
    public void go() {
        final SwingWorker worker = new SwingWorker() {
            public Object construct() {
                current = 0;
                done = false;
                canceled = false;
                statMessage = null;
                return new ActualTask();
            }
        };
        worker.start();
    }

    /**
     * Called from Thread test Application to find out how much work needs
     * to be done.
     */
    public int getLengthOfTask() {
        return lengthOfTask;
    }

    /**
     * Called from ProgressBarDemo to find out how much has been done.
     */
    public int getCurrent() {
        return current;
    }

    public void stop() {
        canceled = true;
        statMessage = null;
    }

    /**
     * Called from Thread test Application to find out if the task has completed.
     */
    public boolean isDone() {
        return done;
    }

    /**
     * Returns the most recent status message, or null
     * if there is no current status message.
     */
    public String getMessage() {
        return statMessage;
    }


    class ActualTask {
        ActualTask() {

            //making a random amount of progress every second.
            while (!canceled && !done) {
                try {
                    Thread.sleep(50); //sleep for a second
                    current += Math.random() * 100; //make some progress
                    if (current >= lengthOfTask) {
                        done = true;
                        current = lengthOfTask;
                    }
                    statMessage = "Completed " + current +
                                  " out of " + lengthOfTask + ".";
                } catch (InterruptedException e) {
                    System.out.println("ActualTask interrupted");
                }
            }
        }
    }
}

abstract class SwingWorker {
    private Object value;  // see getValue(), setValue()

    /** 
     * Class to maintain reference to current worker thread
     * under separate synchronization control.
     */
    private static class ThreadVar {
        private Thread thread;
        ThreadVar(Thread t) { thread = t; }
        synchronized Thread get() { return thread; }
        synchronized void clear() { thread = null; }
    }

    private ThreadVar threadVar;

    /** 
     * Get the value produced by the worker thread, or null if it 
     * hasn't been constructed yet.
     */
    protected synchronized Object getValue() { 
        return value; 
    }

    /** 
     * Set the value produced by worker thread 
     */
    private synchronized void setValue(Object x) { 
        value = x; 
    }

    /** 
     * Compute the value to be returned by the <code>get</code> method. 
     */
    public abstract Object construct();

    /**
     * Called on the event dispatching thread (not on the worker thread)
     * after the <code>construct</code> method has returned.
     */
    public void finished() {
    }

    /**
     * A new method that interrupts the worker thread.  Call this method
     * to force the worker to stop what it's doing.
     */
    public void interrupt() {
        Thread t = threadVar.get();
        if (t != null) {
            t.interrupt();
        }
        threadVar.clear();
    }


    public Object get() {
        while (true) {  
            Thread t = threadVar.get();
            if (t == null) {
                return getValue();
            }
            try {
                t.join();
            }
            catch (InterruptedException e) {
                Thread.currentThread().interrupt(); // propagate
                return null;
            }
        }
    }



//      Start a thread that will call the <code>construct</code> method
//      and then exit.

    public SwingWorker() {
        final Runnable doFinished = new Runnable() {
           public void run() { finished(); }
        };

        Runnable doConstruct = new Runnable() { 
            public void run() {
                try {
                    setValue(construct());
                }
                finally {
                    threadVar.clear();
                }

                SwingUtilities.invokeLater(doFinished);
            }
        };

        Thread t = new Thread(doConstruct);
        threadVar = new ThreadVar(t);
    }

    /**
     * Start the worker thread.
     */
    public void start() {
        Thread t = threadVar.get();
        if (t != null) {
            t.start();
        }
    }

//    public void pause() {
//        Thread t = threadVar.get();
//        if (t != null) {
//            t.start();
//        }
//    }
//    
//    public void resume() {
//        Thread t = threadVar.get();
//        if (t != null) {
//            t.start();
//        }
//    }
   }

2 个答案:

答案 0 :(得分:5)

JPanel panel = new JPanel();

JPanel的默认布局管理器是FlowLayout,它会水平显示组件。

如果您想要垂直布局,则需要使用不同的布局管理器或布局管理器组合。

也许您使用GridLayout创建了一个面板。然后将进度条添加到该面板。然后使用不同的布局管理器将面板添加到另一个面板,以获得所需的布局。

可能是这样的:

JPanel progressPanel = new JPanel( new GridLayout(0, 1) );
progressPanel.add( progressBar1 );
progressPanel.add( progressBar2 );
progresspanel.add( progressBar2 );
someOtherPanel.add( progressPanel );

阅读Layout Managers上Swing教程中的部分,了解更多信息和工作示例。

编辑:

setBorder(BorderFactory.createEmptyBorder(20, 800, 200, 20));

为什么使用值为800和200的边框。

尝试更合理的事情:

setBorder(BorderFactory.createEmptyBorder(20, 20, 20, 20));

答案 1 :(得分:3)

您需要使用layout managers

这里有一个简单的示例,GridBagLayout向您展示当前代码的效果,但一般用户界面很难看,因为我没有花时间修复所有代码但只花了很多时间时间告诉你你想做什么:

    JPanel panel = new JPanel(new GridBagLayout());

    GridBagConstraints gbc = new GridBagConstraints();
    gbc.fill = GridBagConstraints.BOTH;
    gbc.weightx = 1;
    gbc.weighty = 1;
    gbc.gridx = 0;
    gbc.gridy = 0;
    panel.add(startButton, gbc);
    gbc = new GridBagConstraints();
    gbc.fill = GridBagConstraints.BOTH;
    gbc.weightx = 1;
    gbc.weighty = 1;
    gbc.gridx = 1;
    gbc.gridy = 0;
//        panel.add(pauseButton);
//        panel.add(resumeButton);s
    panel.add(progressBar, gbc);
    gbc = new GridBagConstraints();
    gbc.fill = GridBagConstraints.BOTH;
    gbc.weightx = 1;
    gbc.weighty = 1;
    gbc.gridx = 1;
    gbc.gridy = 1;
    panel.add(progressBar2, gbc);
    gbc = new GridBagConstraints();
    gbc.fill = GridBagConstraints.BOTH;
    gbc.weightx = 1;
    gbc.weighty = 1;
    gbc.gridx = 1;
    gbc.gridy = 2;
    panel.add(progressBar3, gbc);
    gbc = new GridBagConstraints();
    gbc.fill = GridBagConstraints.BOTH;
    gbc.weightx = 1;
    gbc.weighty = 1;
    gbc.gridx = 1;
    gbc.gridy = 3;

这给出了这个:

enter image description here