Нарисуйте синусоидальную кривую - PullRequest
0 голосов
/ 08 января 2019

Выход - прямая линия, но должна быть кривой. Не уверен, что проблема в математике или коде. Я знаю, что проблема в том, где говорится (Math.sin(sum3.getValue()), однако я не могу понять, что это должно быть ...

Я по какой-то причине получил сообщение, в котором говорится, что я (V) = SIN (V); я представляю, что я пытаюсь реализовать, чтобы получить кривую I (V). Sum3 - это (V) из другого класса.

import java.awt.Color;
import java.awt.Graphics;
import javax.swing.JFrame;

public class GraphApp extends JFrame {

    int x,y;
    int ax,by;
    IVChar sum3 = new IVChar();

    //create a window in which the graph will be shown

    public GraphApp(){
        setTitle("Graph App");
        setSize(700,700);
        setResizable(true);
        setVisible(true);
        setDefaultCloseOperation (JFrame.EXIT_ON_CLOSE);
        x =  30;
        y = 300;
    }

    // create the axis
    @Override
    public void paint(Graphics g){
        g.drawLine(300, 30, 300, 600); // y axis
        g.drawLine(30, 300, 600, 300); // x axis
        g.setColor(Color.blue);//colour of drawLine
        g.fillOval(x, y, 3, 3);
        g.drawString("I", 310, 40);
        g.drawString("V'", 600, 314);
        run();
        repaint(); //makes it run again
    }
    // implement and draw graphical functions
    public void run(){

        try{
            Thread.sleep(10); //speed line is drawn
            float ax,by;
            ax = x-300;
            by = y-300;
            //specify the function
            by = (float) Math.sin(sum3.getValue());//makes a sin wave
            x = (int) (ax + 300);
            y = (int) (300 - by);
            x++;

        }catch(Exception e){
            System.out.println("Error!");
        }
    }
    public static void main(String[]args){
        new GraphApp();
    }
}

1 Ответ

0 голосов
/ 09 января 2019

Вы можете использовать javax.swing.Timer для анимации рисования кривой:

import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Shape;
import java.awt.geom.Ellipse2D;
import java.awt.geom.Line2D;
import java.awt.geom.Point2D;
import java.util.ArrayList;
import java.util.List;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.Timer;

public class GraphApp extends JFrame {

    public GraphApp(){
        setDefaultCloseOperation (JFrame.EXIT_ON_CLOSE);
        add(new SineWave());
        pack();
        setVisible(true);
    }

    public static void main(String[]args){
        SwingUtilities.invokeLater(()->new GraphApp());
    }
}

class SineWave extends JPanel{

    //use constants for better readability
    private static final double W = 600, H = 700, AMPLITUDE = H/3;
    private static final int MARGIN =30, GAP = 15,DOT_SIZE = 3, SPEED = 10;

    //starting point
    private double x = MARGIN;
    private final double y = H/2;
    private final int dX = 1; //x increment

    //you need to use doubles to avoid rounding error and have use non integer coordinates
    private final List<Point2D.Double> points;
    private final Timer timer;

    public SineWave() {
        setPreferredSize(new Dimension((int)W, (int)H));
        points = new ArrayList<>();
        timer = new Timer(SPEED, e->addPoints()); //timer to add sine points
        timer.start();
    }

    @Override
    public void paintComponent(Graphics g){
        super.paintComponent(g);
        Graphics2D g2 = (Graphics2D)g;

        Shape xAxis = new Line2D.Double(MARGIN, H/2, W-MARGIN, H/2);
        g2.draw(xAxis);
        Shape yAxis = new Line2D.Double(W/2, MARGIN, W/2, H-MARGIN);
        g2.draw(yAxis);
        g.drawString("I", (int)(W/2-GAP),MARGIN);
        g.drawString("V'", (int)(W-GAP), (int)(H/2+GAP));

        g2.setColor(Color.blue);//colour of graph
        for(Point2D.Double p : points){
            Shape point = new Ellipse2D.Double(p.getX(), p.getY(),DOT_SIZE , DOT_SIZE);
            g2.draw(point);
        }
    }

    private void addPoints() {

        double angel = - Math.PI + 2* Math.PI * ((x-MARGIN)/(W- 2*MARGIN));//angle in radians
        double newY = y + AMPLITUDE  * Math.sin(angel);
        points.add(new Point2D.Double(x, newY));
        x += dX;
        if(x >= W-MARGIN) {
            timer.stop();
        }
        repaint();
    }
}

enter image description here

...