在JPanel线上绘画没有连接

时间:2017-04-12 17:09:54

标签: jpanel double line draw

我试图使用带有Graphics2D绘制形状的JPanel绘制方法制作图表。但是,我的线路没有连接,它们的斜率为0.我的期望是像信号波一样绘制线条。这是我的代码:

package action;

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Toolkit;
import java.awt.geom.Line2D;
import java.util.Random;

import javax.swing.JFrame;
import javax.swing.JPanel;

public class Starter extends JFrame {
double Xoffset = 30, Yoffset = 20, Xold = 40, Ycurr = 40, Xcurr = Xold, 
Ytarget = Ycurr, Xgap = 10, Ygap = 60;
double sh = Toolkit.getDefaultToolkit().getScreenSize().getHeight();
double sw = Toolkit.getDefaultToolkit().getScreenSize().getWidth();
int panelOffSet = 20;

double[] value_old = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
double[] value_curr = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 
};// new

// double[17];
    int counter = 0;

public static void main(String[] args) {
    // TODO Auto-generated method stub
    Starter mainThread = new Starter();
}

public Starter() {
    super("EEG Recorder");
    // //set the frame to center of screen
    setLayout(null);
    this.getContentPane().setBackground(new Color(32, 32, 32));
    setSize((int) sw, (int) sh);
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);

    // add the painting panel
    EEGRecorder plotter = new EEGRecorder();
    add(plotter);
    this.setVisible(true);
    while (true) {
        plotter.run();
    }
}

class EEGRecorder extends JPanel implements Runnable {

    public EEGRecorder() {
        setLayout(null);
        setBackground(new Color(32, 32, 32));
        setBounds(0, panelOffSet, (int) sw, (int) (sh - panelOffSet));
    }

    @Override
    public void run() {
        // TODO Auto-generated method stub
        try {
            this.updateUI();
            repaint();
            Thread.sleep(50);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        // System.out.println("hello");
    }

    @Override
    public void paint(Graphics g) {
        Graphics2D gg = (Graphics2D) g;
        for (int i = 1; i < 17; i++) {

            Random rn = new Random();
            Ytarget = rn.nextDouble() * 30;
            value_curr[i] = Ytarget;
            // System.out.println(value_curr[i]);

            if (Xcurr + Xgap - 1 > sw) {
                gg.clearRect((int) Xoffset, (int) Yoffset, (int) (sw - Xoffset - 20), (int) (sh - panelOffSet));
                gg.setColor(new Color(32, 32, 32));
                gg.fillRect(0, 0, (int) (sw), (int) (sh - panelOffSet));
                Xold = Xoffset;
                Xcurr = Xold + Xgap;
            } else {
                gg.setColor(Color.yellow);
                gg.drawString("ch" + i, 4, (int) (Yoffset + (i - 1) * Ygap));
                if (counter == 0) {
                    value_old[i] = 0;// value_curr[i];
                    Xcurr = Xold + Xgap;

                }
                gg.setColor(Color.BLUE);
                gg.draw(new Line2D.Double(Xold, (i - 1) * Ygap - value_old[i], Xcurr,
                        (i - 1) * Ygap - value_curr[i]));
                double Yold=(i - 1) * Ygap - value_old[i];
                double Ynew=(i - 1) * Ygap - value_curr[i];
                System.out.println(Xold+","+Yold+","+ Xcurr+","+Ynew);
            }
        }

        value_old = value_curr;

        // Ycurr = Ytarget;

        Xold = Xcurr;
        Xcurr += Xgap;
        counter++;
    }
}

}

1 个答案:

答案 0 :(得分:1)

我可以花很多时间向你解释为什么你的代码没有工作以及如何解决它,不用说,你需要退后一步做出很多改变。

我强烈建议您花点时间阅读:

现在,由于绘画在Swing中的工作方式,你有两个选择。

要么使用某种模型来维护您想要绘制的信息,当出现绘制周期时,使用此信息更新组件,或者绘制到后备缓冲区并在发生绘制周期时将其绘制到组件

我选择使用数据模型,它更简单,因为我不需要监控组件的状态并更新缓冲区,但这就是我。

import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.geom.Line2D;
import java.awt.geom.Point2D;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Random;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.Timer;

public class Starter {

    public static void main(String[] args) {
        SwingUtilities.invokeLater(new Runnable() {
            @Override
            public void run() {
                Starter mainThread = new Starter();
            }
        });
    }

    public Starter() {
        JFrame frame = new JFrame("EEG Recorder");
        EEGRecorder plotter = new EEGRecorder();
        frame.add(plotter);
        frame.pack();
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
//        frame.setExtendedState(JFrame.MAXIMIZED_BOTH);
        frame.setVisible(true);
    }

    class EEGRecorder extends JPanel {

        double Xoffset = 30, Yoffset = 20, Xold = 40, Ycurr = 40, Xcurr = Xold,
                Ytarget = Ycurr, Xgap = 10, Ygap = 60;

        private List<List<Point2D>> series;

        public EEGRecorder() {
            series = new ArrayList<>(16);
            for (int line = 0; line < 16; line++) {
                series.add(new ArrayList<>(100));
            }
            setBackground(new Color(32, 32, 32));
            Timer timer = new Timer(50, new ActionListener() {
                @Override
                public void actionPerformed(ActionEvent e) {
                    update();
                    repaint();
                }
            });
            timer.start();
        }

        @Override
        public Dimension getPreferredSize() {
            return new Dimension(200, 200);
        }

        protected void update() {
            int count = 1;
            for (List<Point2D> line : series) {
                Point2D last = new Point2D.Double(0, 0);
                if (line.size() > 0) {
                    last = line.get(line.size() - 1);
                }

                Random rn = new Random();
                double y = (rn.nextDouble() * 30) + (Yoffset + (count - 1) * Ygap);
                double x = Xoffset;

                int sw = getWidth();
                if (last.getX() + Xgap - 1 > sw) {
                    line.clear();
                } else {
                    x = last.getX() + Xgap;
                }

                line.add(new Point2D.Double(x, y));
                count++;
            }
        }

        @Override
        protected void paintComponent(Graphics g) {
            super.paintComponent(g); //To change body of generated methods, choose Tools | Templates.

            Graphics2D gg = (Graphics2D) g.create();
            int count = 1;
            for (List<Point2D> line : series) {
                gg.setColor(Color.yellow);
                gg.drawString("ch" + count, 4, (int) (Yoffset + (count - 1) * Ygap));
                gg.setColor(Color.BLUE);
                Point2D fromPoint = null;
                for (Point2D toPoint : line) {
                    if (fromPoint != null) {
                        gg.draw(new Line2D.Double(fromPoint, toPoint));
                    }
                    fromPoint = toPoint;
                }
                count++;
            }
            gg.dispose();
        }
    }
}

这不是从头开始编辑系列,但是当你到达组件的末尾时保留一些旧的信息,我只需清除系列并重新开始。

让它&#34;重叠&#34;需要一个更复杂的模型,而且我需要懒惰