如何创建交互式画布基本几何形状

时间:2017-03-14 17:45:32

标签: java canvas vector graph physics

我现在正在春假,因为我每周只工作25个小时,所以我的手上有太多的空闲时间。我是一名计算机科学专业的学生,​​我决定利用我的空闲时间来提高我的编码技能和对电磁物理的理解,创建一个非常简单的计算器,用于解决库仑定律,用于解决任何两个充电之间的力带电粒子系统中的粒子。

现在我有一个有点准确的计算器工作,我仍然有一些我需要解决的小错误,但代码可以在下面找到,但它仍然适用于我想要实现的下一步。

我的下一步是创建一个GUI和一个交互式图表供用户查看。我说互动是因为我的理想程序会让用户能够在画布上一直拖放点,同时程序正在计算用户放置在空间上的点之间存在的力矢量和净力。我也很满意能够在给定电荷和XY坐标的情况下绘制图形。

我的问题是,有没有人知道我可以研究任何好的教程或受人尊敬的图书馆来实现这两个想法中的任何一个?我有一个强大的Java背景,所以我更喜欢用Java完成,但是在我需要的时候,我永远不会离开学习一门新语言。

代码:

Charge.java

    package objects;

/**
 * Charge is an object used to represent an arbitrarily charged particle in some
 * XY-plane. This class will store the value of the charge, the XY-coordinates
 * of that charge's location, and functions to access these values.
 * 
 * @author Seth
 *
 */
public class Charge {
    private double q; // the charge of the particle in Coulombs
    private double x; // the location along the x-axis of the charge
    private double y; // the location along the y-axis of the charge

    public Charge(double x, double y, double q) {
        this.x = x;
        this.y = y;
        this.q = q;
    }

    /**
     * public method to get q
     * 
     * @return 
     *      double - value of the Charge object
     */
    public double getQ() {
        if (this != null)
            return q;
        else
            return 0;
    }

    /**
     * public method to get x
     * 
     * @return 
     *      double - value of the x coordinate
     */
    public double getX() {
        if (this != null)
            return x;
        else
            return 0;
    }

    /**
     * public method to get y
     * 
     * @return 
     *      double - value of the y coordinate
     */
    public double getY() {
        if (this != null)
            return y;
        else
            return 0;
    }
}

ElectricForceCalculator.java

   package objects;

/**
 * ElectricForceCalculator is a class that has the ability to solve the net
 * force between two charged particles in a xy-plane
 * 
 * @author Seth
 *
 */
public class ElectricForceCalculator {
    /**
     * Private method used to find the force between two charges
     * 
     * @param Q
     *            Charge - The charged we are focused on
     * @param q
     *            Charge - The second charge effecting Q
     * @return double array - the force vectors found where i = 0 is the x
     *         direction and i = 1 is the y direction
     */
    private double[] calcForceHelper(Charge Q, Charge q) {
        double radius, quanOfCharge;
        double[] radiusVector = new double[2], forceVector = new double[2];

        double x1 = Q.getX(), y1 = Q.getY();
        double x2 = q.getX(), y2 = q.getY();
        double q1 = Q.getQ(), q2 = q.getQ();

        System.out.print("Calculating radius of Q and q...\n\t");
        radius = calcRadius(x1, x2, y1, y2);

        System.out.print("Calculating radiusVector of Q and q...\n\t");
        radiusVector = calcRadiusVector(x1, x2, y1, y2, radius);

        System.out.print("Calculating quantityOfCharge of Q and q...\n\t");
        quanOfCharge = calcCharge(q1, q2, radius);

        System.out.print("Calculating Force Vector of Q and q...\n\t");
        forceVector = calcForceVector(radius, radiusVector, quanOfCharge);

        return forceVector;
    }

    /**
     * Public method used to find the overall net force of a system of charged
     * particles
     * 
     * @param Q
     *            Charge - the Charge object we are focused on
     * @param q
     *            Charge array - the list of all the other Charge object
     *            effecting Q
     * @param numCharges
     *            int - the number of indices found in the list of Charge
     *            objects q
     * @return double - value of the net force experienced by Charge object Q
     */
    public double calcForce(Charge Q, Charge[] q, int numCharges) {
        double result;
        double[] sum = { 0.0, 0.0 }, tempSum = new double[2];
        for (int i = 0; i < numCharges - 1; i++) {
            tempSum = calcForceHelper(Q, q[i]); // Help with readability to call
                                                // method helper
            fixSigns(Q, q[i], tempSum);
            sum[0] += tempSum[0];
            sum[1] += tempSum[1];
        }
        System.out.println("\nOverall force Vector on Q = (" + sum[0] + ")x + (" + sum[1] + ")y.");

        result = Math.pow(sum[0], 2) + Math.pow(sum[1], 2);
        result = Math.sqrt(result);
        double theta = calcTheta(sum);
        System.out.print("Force on charge Q by all other charges = " + result + " at ");

        if (sum[1] > 0) {
            if (sum[0] > 0)
                System.out.print((float) Math.round(90 - theta) + " degrees.");
            else
                System.out.print((float) Math.round(180 - theta) + " degrees.");
        } else {
            if (sum[0] > 0)
                System.out.print((float) Math.round(180 + theta) + " degrees.");
            else
                System.out.print((float) Math.round(270 + theta) + " degrees.");
        }
        return result;
    }

    /**
     * Method used to assign negative values to any forces that should be
     * negative
     * 
     * @param Q
     *            Charge - the charge we are focused on
     * @param q
     *            charge - the charge effecting Q
     * @param tempSum
     *            the force vectors we are fixing, if needed
     */
    private void fixSigns(Charge Q, Charge q, double[] tempSum) {
        if (Q.getQ() < 0 && q.getQ() < 0) {
            if (q.getX() > Q.getX())
                tempSum[0] *= -1;
            if (q.getY() > Q.getY())
                tempSum[1] *= -1;
        } else if (Q.getQ() > 0 && q.getQ() > 0) {
            if (q.getX() > Q.getX())
                tempSum[0] *= -1;
            if (q.getY() > Q.getY())
                tempSum[1] *= -1;
        } else {
            if (q.getX() < Q.getX())
                tempSum[0] *= -1;
            if (q.getY() < Q.getY())
                tempSum[1] *= -1;
        }
    }

    /**
     * Private method used to calculate the angle Theta between two vectors
     * 
     * @param forceVector
     *            double array - the force vectors we are finding the angle
     *            between
     * @return double - the angle between the two force vectors given
     */
    private double calcTheta(double[] vectors) {
        double result = Math.abs(vectors[1]) / Math.abs(vectors[0]);// finds
                                                                    // angle
                                                                    // between 0
                                                                    // and 90
        result = Math.toDegrees(Math.atan(result));

        return result;
    }

    /**
     * Private method used to calculate the force vectors experienced by a
     * charged particle
     * 
     * @param radius
     *            double - distance between two charges
     * @param radiusVector
     *            double array - the radius vectors between two charges
     * @param quanOfCharge
     *            double - the quantity of charge given by k(coulomb's constant)
     *            * charge of Q * charge of q
     * @return double array - the force vectors experienced by two charges
     */
    private double[] calcForceVector(double radius, double[] radiusVector, double quanOfCharge) {
        double[] result = new double[2];
        double theta = calcTheta(radiusVector), magnitude = quanOfCharge;

        result[0] = magnitude * Math.cos(Math.toRadians(theta));
        result[1] = magnitude * Math.sin(Math.toRadians(theta));

        System.out.print("Force Vector = (" + result[0] + ")x + (" + result[1] + ")y.\n");
        return result;
    }

    /**
     * private method used to calculate the quantity of charge between two
     * charged particles(k * charge of Q * charge of q)
     * 
     * @param Q
     *            double - the charge in Coulombs of the Charge object Q
     * @param q
     *            double - the charge in Coulombs of the Charge object q
     * @return double - the quantity of charge
     */
    private double calcCharge(double Q, double q, double d) {
        double result;

        result = (((Q * q) / (d * d)) * 9E9);
        result = Math.abs(result);

        System.out.print("Quantity of charge(Q*q*k) = " + result + "\n");
        return result;
    }

    /**
     * Private method used to calculate the radius vector between two points on
     * a xy-plane
     * 
     * @param x1
     *            double - x coordinate of the Charge object Q
     * @param x2
     *            double - y coordinate of the Charge object q
     * @param y1
     *            double - x coordinate of the Charge object Q
     * @param y2
     *            double - y coordinate of the Charge object q
     * @param radius
     *            double - distance between the two points
     * @return double array - the distance vectors between two charges
     */
    private static double[] calcRadiusVector(double x1, double x2, double y1, double y2, double radius) {

        double[] result = new double[2];

        result[0] = (x2 - x1) / radius;
        result[1] = (y2 - y1) / radius;

        result[0] = Math.abs(result[0]);
        result[1] = Math.abs(result[1]);

        System.out.print("Radius vector = (" + result[0] + ")x + (" + result[1] + ")y\n");
        return result;
    }

    /**
     * Private method used to calculate the distance between two points on a
     * xy-plane using the distance formula or [(x2-x1)+(y2-y1]^(1/2)
     * 
     * @param x1
     *            double - x coordinate of the Charge object Q
     * @param x2
     *            double - y coordinate of the Charge object q
     * @param y1
     *            double - x coordinate of the Charge object Q
     * @param y2
     *            double - y coordinate of the Charge object q
     * @return double - distance between the two points given
     */
    private double calcRadius(double x1, double x2, double y1, double y2) {

        double distance = Math.pow((x2 - x1), 2) + Math.pow((y2 - y1), 2);
        distance = Math.sqrt(distance);

        System.out.print("Radius = " + distance + "\n");
        return distance;
    }

    /**
     * Main
     * 
     * @param args
     */
    public static void main(String[] args) {
        Charge Q = new Charge(-.02, .015, -4E-6);
        Charge[] q = new Charge[2];
        q[0] = new Charge(.035, .005, 3E-6);
        q[1] = new Charge(-.0837, .0262, 4E-6);
        ElectricForceCalculator calc = new ElectricForceCalculator();
        calc.calcForce(Q, q, 3);
    }
}

示例输出:

charge Q is -4.0E-6 C at (x,y) = (-0.02, 0.015).
charge q1 is 3.0E-6 C at (x,y) = (0.035, 0.005).
charge q1 is 4.0E-6 C at (x,y) = (-0.0837, 0.0262).
Calculating radius of Q and q...
    Radius = 0.05590169943749475
Calculating radiusVector of Q and q...
    Radius vector = (0.9838699100999075)x + (0.17888543819998312)y
Calculating quantityOfCharge of Q and q...
    Quantity of charge(Q*q*k) = 34.559999999999995
Calculating Force Vector of Q and q...
    Force Vector = (34.0025440930528)x + (6.182280744191415)y.
Calculating radius of Q and q...
    Radius = 0.06467712114805357
Calculating radiusVector of Q and q...
    Radius vector = (0.984892321570454)x + (0.17316788071568426)y
Calculating quantityOfCharge of Q and q...
    Quantity of charge(Q*q*k) = 34.4239839545986
Calculating Force Vector of Q and q...
    Force Vector = (33.903917474748674)x + (5.96112834720856)y.

Overall force Vector on Q = (0.09862661830412378)x + (-0.2211523969828546)y.
Force on charge Q by all other charges = 0.24214787327038295

0 个答案:

没有答案