2

I have a recursive loop that performs calculations on an image and want to display the progress of the image through each iteration.

This is what I have:

static JFrame colFrame = new JFrame();
main() {}

loop() {

        JLabel label = null;
        ImageIcon colIcon = new ImageIcon(blockImg);
        label = new JLabel(colIcon);
        colFrame.getContentPane().add(label);
        colFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); // close canvas once the window is closed
        colFrame.pack();
        colFrame.setVisible(true);

}

Does anyone know how to change my code so that it will display the image through each iteration?

QQCompi
  • 225
  • 4
  • 14

2 Answers2

4

Use a Swing Timer to schedule the animation of changing the image.

Here is my simple example that changes the text of the label every second:

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

public class TimerTime extends JPanel implements ActionListener
{
    private JLabel timeLabel;
    private int count = 0;

    public TimerTime()
    {
        timeLabel = new JLabel( new Date().toString() );
        add( timeLabel );

        Timer timer = new Timer(1000, this);
        timer.setInitialDelay(1);
        timer.start();
    }

    @Override
    public void actionPerformed(ActionEvent e)
    {
        //System.out.println(e.getSource());
        timeLabel.setText( new Date().toString() );
//      timeLabel.setText( String.valueOf(System.currentTimeMillis() ) );
        count++;
        System.out.println(count);

        if (count == 10)
        {
            Timer timer = (Timer)e.getSource();
            timer.stop();
        }
    }

    private static void createAndShowUI()
    {
        JFrame frame = new JFrame("TimerTime");
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.add( new TimerTime() );
        frame.setLocationByPlatform( true );
        frame.pack();
        frame.setVisible( true );
    }

    public static void main(String[] args)
    {
        EventQueue.invokeLater(new Runnable()
        {
            public void run()
            {
                createAndShowUI();
            }
        });
    }
}

In your case you would want to change the Icon (not create a new label).

camickr
  • 321,443
  • 19
  • 166
  • 288
  • `javax.swing.Timer` is a good choice, but it may be awkward for recursion. – trashgod Nov 20 '15 at 17:01
  • @trashgod, missed the recursion part. The SwingWorker with a Thread.sleep() and publish() at the appropriate time would probably be easier to code (+1). – camickr Nov 20 '15 at 17:41
4

Because your algorithm is recursive, invoke it in the doInBackground() implementation of a SwingWorker. At each level, publish() a BufferedImage representing the current state, and process() it using label.setIcon(). An example that generates a BufferedImage is shown here, and a related example that generates a TexturePaint is shown here.

Community
  • 1
  • 1
trashgod
  • 203,806
  • 29
  • 246
  • 1,045