在另一个jpanel中嵌入一个运动图像



我一直在尝试移动和显示图像(例如心率图像)。这是我迄今为止所拥有的。图像一直向左移动;到目前为止还不错。但是我需要将这个运动图像嵌入到另一个帧中。我知道我的问题看起来很

import java.awt.EventQueue;
import java.awt.Graphics2D;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.net.URL;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.Timer;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
public class HeartBeat extends JPanel{
    public static void main(String[] args) throws Exception {
        new HeartBeat();    
    }
    public HeartBeat(){
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    ex.printStackTrace();
                }
                JFrame frame = new JFrame("Testing");
                frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
                JPanel j = new JPanel();
                j.add(new HeartBeat2());
                frame.add(j);
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }
    class HeartBeat2 extends JPanel{
        BufferedImage bi;
        public HeartBeat2(){
        try {
            bi = ImageIO.read(new URL("https://i.stack.imgur.com/i8UJD.jpg"));
        } catch (IOException e1) {
            // TODO Auto-generated catch block
            e1.printStackTrace();
        }
        Runnable r = new Runnable() {
            @Override
            public void run() {
                final BufferedImage canvas = new BufferedImage(
                        bi.getWidth(), bi.getHeight(),
                        BufferedImage.TYPE_INT_RGB);
                final JLabel animationLabel = new JLabel(new ImageIcon(canvas));
                ActionListener animator = new ActionListener() {
                    int x = 0;
                    @Override
                    public void actionPerformed(ActionEvent e) {
                        Graphics2D g = canvas.createGraphics();
                        // paint last part of image in left of canvas
                        g.drawImage(bi, x, 0, null);
                        // paint first part of image immediately to the right
                        g.drawImage(bi, x + bi.getWidth(), 0, null);
                        // reset x to prevent hitting integer overflow
                        if (x%bi.getWidth()==0) x = 0;
                        g.dispose();
                        animationLabel.repaint();
                        x--;
                    }
                };
                Timer timer = new Timer(40, animator);
                timer.start();
                JPanel j = new JPanel();
                JOptionPane.showMessageDialog(null, animationLabel);
                timer.stop();
            }
        };
        // Swing GUIs should be created and updated on the EDT
        // http://docs.oracle.com/javase/tutorial/uiswing/concurrency
        SwingUtilities.invokeLater(r);
    }
}}

代码的问题是

  1. animationLabel被添加到JOptionPane,但您从未将其添加到HeartBeat2

  2. JOptionPane.showMessageDialog是一个阻塞(模式)调用,因此它会阻塞它之后发生的任何代码(即timer.stop())。但是,如果移除JOptionPane(尝试将标签添加到面板),则会自动调用timer.stop()(计时器控制图像/动画)。如果您只是JOptionPane留在那里,那么将标签添加到面板将不起作用,因为每个组件只能有一个父

所以你需要

  1. 首先,完全剥离Runnable。你不需要它。

  2. 取出JOptionPane,简单add(animationLabel)HeartBeat2

  3. 取出timer.stop()


public HeartBeat2() {
    try {
        bi = ImageIO.read(new URL("https://i.stack.imgur.com/i8UJD.jpg"));
    } catch (IOException e1) {
        // TODO Auto-generated catch block
        e1.printStackTrace();
    }
    final BufferedImage canvas = new BufferedImage(
            bi.getWidth(), bi.getHeight(),
            BufferedImage.TYPE_INT_RGB);
    final JLabel animationLabel = new JLabel(new ImageIcon(canvas));
    add(animationLabel);
    ActionListener animator = new ActionListener() {
        int x = 0;
        @Override
        public void actionPerformed(ActionEvent e) {
            Graphics2D g = canvas.createGraphics();
            // paint last part of image in left of canvas
            g.drawImage(bi, x, 0, null);
            // paint first part of image immediately to the right
            g.drawImage(bi, x + bi.getWidth(), 0, null);
            // reset x to prevent hitting integer overflow
            if (x % bi.getWidth() == 0) {
                x = 0;
            }
            g.dispose();
            animationLabel.repaint();
            x--;
        }
    };
    Timer timer = new Timer(40, animator);
    timer.start();
}

最新更新