简体   繁体   English

SwingWorker进程()更新gui Generics

[英]SwingWorker process() updating gui Generics

Im trying to use SwingWorker to update my gui. 我试图使用SwingWorker来更新我的gui。

The part of my gui that I'm trying to update is a JPanel (gridPanel) with a GridLayout [50][50]. 我想要更新的gui部分是带有GridLayout [50] [50]的JPanel(gridPanel)。
Each grid in the GridLayout has a custom GridGraphic JComponent. GridLayout中的每个网格都有一个自定义GridGraphic JComponent。

In the doInBackground() of my SwingWorker, I update each GridGraphic which represents some color. 在SwingWorker的doInBackground()中,我更新了表示某种颜色的每个GridGraphic。 Then, I publish it to a List that the process() uses to update the gui. 然后,我将它发布到进程()用来更新gui的List。 Though, the gui isn't updating. 虽然,gui没有更新。

Is there a way to do this without calling repaint(). 有没有办法在不调用repaint()的情况下执行此操作。

How do I fix my SwingWorker so the gui is responsive. 如何修复SwingWorker,以便gui响应。 What do I want to return in order for the gridPanel, which is a [50][50] GridLayout of GridGraphic components responsive to changes 我想为gridPanel返回什么,gridPanel是响应变化的GridGraphic组件的[50] [50] GridLayout

The SwingWorker is executed in the stepButton.addActionListener(new ActionListener()...............in SlimeGui SwingWorker在stepButton.addActionListener中执行(新的ActionListener()............... in SlimeGui

import java.awt.*;
import javax.swing.*;
import java.awt.event.*;
import javax.swing.event.*;


public class SlimeGui extends JFrame{

    private JPanel buttonPanel, populationPanel, velocityPanel;
    private JPanel gridPanel = new JPanel(new GridLayout(50, 50));
    private JButton setupButton, stepButton, goButton;
    private JLabel populationNameLabel, velocityNameLabel, populationSliderValueLabel, velocitySliderValueLabel;
    private JSlider populationSlider, velocitySlider;
    private GridGraphic [] [] gridGraphic;
    private GridGraphic test;
    private int agents = 125;
    private int velocity = 500;
    private boolean resetGrid;


    public SlimeGui() {

        setLayout(new GridBagLayout());
        GridBagConstraints c = new GridBagConstraints();


        //Set up JButtons
        buttonPanel = new JPanel();
        setupButton = new JButton("Setup");
        stepButton = new JButton("Step");
        goButton = new JButton("Go");

        buttonPanel.add(setupButton);
        buttonPanel.add(stepButton);
        buttonPanel.add(goButton);

        c.gridx = 0;
        c.gridy = 1;
        c.gridwidth = 3;
        add(buttonPanel, c);


        //Set up population JSlider     
        populationPanel = new JPanel();
        populationNameLabel = new JLabel("     Population");
        populationSliderValueLabel = new JLabel(Integer.toString(agents));
        populationSlider = new JSlider(JSlider.HORIZONTAL,0, 1000, 125);
        populationSlider.setMajorTickSpacing(125);
        populationSlider.setPaintTicks(true);
        populationSlider.addChangeListener(new PopulationSliderListener());

        populationPanel.add(populationNameLabel);
        populationPanel.add(populationSlider);
        populationPanel.add(populationSliderValueLabel);

        c.gridx = 0;
        c.gridy = 2;
        add(populationPanel, c);    


        //Set up veolicty JSlider
        velocityPanel = new JPanel();
        velocityNameLabel = new JLabel("        Velocity");
        velocitySliderValueLabel = new JLabel(Integer.toString(velocity));
        velocitySlider = new JSlider(JSlider.HORIZONTAL,0, 1000, 500);
        velocitySlider.setMajorTickSpacing(125);
        velocitySlider.setPaintTicks(true);
        velocitySlider.addChangeListener(new VelocitySliderListener());

        velocityPanel.add(velocityNameLabel);
        velocityPanel.add(velocitySlider);
        velocityPanel.add(velocitySliderValueLabel);

        c.gridx = 0;
        c.gridy = 3;
        add(velocityPanel, c);  


        //Set up grid with GridGraphic objects
        gridGraphic = new GridGraphic[50][50];

        for(int i = 0; i < 50; i++){
            for(int j = 0; j < 50; j++){
                gridGraphic[i][j] = new GridGraphic();
                gridPanel.add(gridGraphic[i][j]);
            }
        }

        c.gridx = 0;
        c.gridy = 0;
        c.gridwidth = 3;

        add(gridPanel, c);


        //Set up ActionListener for the 'Setup' JButton
        setupButton.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e) {
                int n1=0;
                int n2=0;

                //resets the grid so there are no agents
                if(resetGrid){
                    for(int i = 0; i < 50; i++){
                        for(int j = 0; j < 50; j++){
                            gridGraphic[i][j].setDefault();
                        }
                    }
                }

                //sets a random number of positions for GridGraphics
                for (int numOfAgenets = 0; numOfAgenets < agents; numOfAgenets++){
                    int lowerB = 0;
                    int upperB = 50;                    

                    n1 = (lowerB + (int)(Math.random()*(upperB-lowerB))); //random number 1
                    n2 = (lowerB + (int)(Math.random()*(upperB-lowerB))); //random number 2

                    System.out.println("Choosing random agent "+(numOfAgenets+1)+":  "+n1 +" "+n2);

                    //sets the GridGraphic to an agent if it's available
                    if (gridGraphic[n1][n2].getIntensity() == 0)
                        gridGraphic[n1][n2].setAgent();

                    //if the GridGraphic is already an agent, it continues to search 
                    else if(gridGraphic[n1][n2].getIntensity() == 5){
                        while(gridGraphic[n1][n2].getIntensity() == 5){
                            n1 = (lowerB + (int)(Math.random()*(upperB-lowerB)));
                            n2 = (lowerB + (int)(Math.random()*(upperB-lowerB)));
                        }
                        gridGraphic[n1][n2].setAgent();
                    }                   
                }   

                repaint();
                resetGrid = true;
            }
        }); 


        //Set up ActionListener for the 'Step' JButton
        stepButton.addActionListener(new ActionListener(){
            public void actionPerformed(ActionEvent e) {
                StepManager step = new StepManager(SlimeGui.this);
                step.execute();
                //repaint();
            }
        });

    }


    class PopulationSliderListener implements ChangeListener{
        public void stateChanged(ChangeEvent e){
            agents = ((JSlider)e.getSource()).getValue();

            populationSliderValueLabel.setText(Integer.toString(agents));
            System.out.println("Population of agents:  " + agents);
        }
    }


    class VelocitySliderListener implements ChangeListener{
        public void stateChanged(ChangeEvent e){
            velocity = ((JSlider)e.getSource()).getValue();

            velocitySliderValueLabel.setText(Integer.toString(velocity));
            System.out.println("Velocity(ms) of agents:  " + velocity);
        }
    }


    public Integer getVelocity(){
        return velocity;
    }

    public GridGraphic getGridGraphic(int n1, int n2){
        return gridGraphic[n1][n2];
    }

    public GridGraphic [][] getGridGraphic(){
        return gridGraphic;
    }

    public void setGridGraphicArray(GridGraphic xxx, int n1, int n2 ){
        gridGraphic[n1][n2] = xxx;
    }

    public void setGridPanel(GridGraphic[][] xxx){
        for(int i = 0; i < 50; i++){
            for(int j = 0; j < 50; j++){
               gridPanel.add(xxx[i][j]);
            }
        }
    }



    /**
     * Create the GUI and show it.  For thread safety,
     * this method should be invoked from the
     * event-dispatching thread.
     */
    private static void createAndShowGUI() {
        //Create and set up the window.
        SlimeGui slime = new SlimeGui();
        slime.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

        //Display the window.
        slime.pack();
        slime.setVisible(true);
        slime.setResizable(false);
    }

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

My SwingWorker 我的SwingWorker

import java.util.List;
import java.awt.*;
import javax.swing.*;
import java.util.concurrent.ExecutionException;

public class StepManager extends SwingWorker<Void, GridGraphic>{

    private SlimeGui gui;

    public StepManager(SlimeGui sg){
         gui=sg;
    }

    @Override
    protected Void doInBackground() throws Exception{   
        for(int i = 0; i < 50; i++){
            for(int j = 0; j < 50; j++){

                if(gui.getGridGraphic(i,j).getIntensity()==5){
                    if (i==0){
                        gui.getGridGraphic(i,j).setDefault();
                        gui.getGridGraphic(49,j).setAgent();
                    }
                    else{
                        gui.getGridGraphic(i,j).setDefault();
                        gui.getGridGraphic(i-1,j).setAgent();
                    }
                }
                publish(gui.getGridGraphic(i,j));
            }
        }
        return null;
    }

    @Override
    protected void process(List <GridGraphic> gg){                  
        int k=0;
        for ( int i = 0; i < 50; i++ ){
            for(int j = 0; j < 50; j++){
                gui.setGridGraphicArray(gg.get(k),i,j);
                k++;
            }
        }
        gui.setGridPanel(gui.getGridGraphicArray());
        System.out.println("process has completed");
    }

    @Override
    protected void done(){          
        System.out.println("doInBackground has completed");
    }
}

My GridGraphic 我的GridGraphic

import java.awt.*;
import javax.swing.*;

public class GridGraphic extends JComponent {

    private int intensity = 0;

    public GridGraphic() {
        //setBorder(BorderFactory.createLineBorder(Color.BLUE));
    }

    public void paintComponent(Graphics g) {

        //paints the GridGraphic black
        if (intensity == 0){
            super.paintComponent(g);
            g.setColor(Color.BLACK);
            g.fillRect(0, 0, getWidth(), getHeight());
        }

        //paints the GridGraphic black with a yellow dot
        else if (intensity == 5){
            super.paintComponent(g);
            g.setColor(Color.BLACK);
            g.fillRect(0, 0, getWidth(), getHeight());
            g.setColor(Color.YELLOW);
            g.fillOval(3, 3, getWidth()/2, getHeight()/2);
        }

        //paints the GridGraphic dark yellow (pheromone)
        if (intensity == 2){
            super.paintComponent(g);
            g.setColor(Color.BLACK.brighter());
            g.fillRect(0, 0, getWidth(), getHeight());
        }     
    }


    public Dimension getPreferredSize() {
        return new Dimension(10, 10);
    }

    public void setAgent(){
        intensity = 5;
    }

    public void setPheromone1(){
        intensity = 2;
    }

    public void setDefault(){
        intensity = 0;
    }

    public int getIntensity(){
        return intensity;
    }
}

The line number in the stack trace indicates where the exception occurs. 堆栈跟踪中的行号指示发生异常的位置。 Your gui attribute in StepManager is null. 您在StepManager gui属性为null。 It's never initialized. 它从未被初始化。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM