// Math functions (methods, parameters)
//-----------------------------------------------------------------------------
// Mathods solves Quadratic equations.  
// It also demonstrates the use of PARAMETERS and FUNCTIONS.a
// A FUNCTION is a method that returns a value, such as Square Root.
//=============================================================================

 import java.awt.*;
 import java.awt.event.*;
 import javax.swing.*;
 import java.io.*;

 public class SolveQuads extends EasyApp     // EasyApp contains IBIO
                                           //  + standard constructor stuff
 { public static void main(String[] args)  
   {  new SolveQuads(); }                    // Instantiate an object = start program
   
   Label  lTitle  = addLabel("     Solving Quadratic Equations",0,30,390,35,this);
   Label lFormula = addLabel("    A x" + (char)178 + " + B x + C = 0",30,70,250,30,this);
   Button bSolve  = addButton("Solve",240,100,80,40,this);
   TextField  tA  = addTextField("",40,100,50,40,this);
   TextField  tB  = addTextField("",110,100,50,40,this);
   TextField  tC  = addTextField("",180,100,50,40,this);
   Label     lX1  = addLabel("x1=",40,150,50,40,this);
   TextField tX1  = addTextField("",90,150,100,40,this);
   Label     lX2  = addLabel("x2=",200,150,50,40,this);
   TextField tX2  = addTextField("",250,150,100,40,this);
   Label   lInfo  = addLabel("Type A,B,C then press [Solve]",30,200,350,40,this);
   
   public SolveQuads()
   {
       Font bigFont = new Font("Arial",0,24);   // sets all the components to use
       lTitle.setFont(bigFont);                 // a large font
       lTitle.setBackground(new Color(192,224,255));
       lFormula.setFont(bigFont);
       tA.setFont(bigFont);
       tB.setFont(bigFont);
       tC.setFont(bigFont);
       lX1.setFont(bigFont);
       tX1.setFont(bigFont);
       lX2.setFont(bigFont);
       tX2.setFont(bigFont);
       lInfo.setFont(bigFont);
       setSize(390,280);
   }
   
   public void actionPerformed(ActionEvent evt)
   {   Object source = evt.getSource();
       if (source == bSolve)
       { calcRoots();}
   }
       
   public void calcRoots()
   {
       double a = toDouble( tA.getText());   // get the value of a from textField tA
       double b = toDouble( tB.getText());   // get the value of b
       double c = toDouble( tC.getText());   // get the value of c
       
       if ( bad(a) || bad(b) || bad(c) )     // if any of the numbers are missing or bad
       {   tX1.setText("Error");             //   display "error"
           tX2.setText("Error");
       }    
       else
       {   double d = Math.pow(b,2) - 4*a*c; // calculate the discriminant
           if (d < 0)                        // if it's negative
           {   tX1.setText("no root");       //   the equation has no roots
               tX2.setText("no root");
           }
           else
           {   double x1 = (-b + root(d)) / (2*a);     // calculate roots
               double x2 = (-b - root(d)) / (2*a);
               tX1.setText(x1 + "");                   // display roots
               tX2.setText(x2 + "");
           }
       }    
   }
   
   public double toDouble(String s)          // converts a string to a double number
   {   try                                   // accepts a String parameter, return a double
       {   double d = Double.parseDouble(s);
           return d;
       }
       catch (Exception e)
       {   return Double.NaN;}               // if not successful, return Not-a-Number
   }  
   
   public boolean bad(double num)            // check whether num equals NaN
   { return Double.isNaN(num);}              // accept double parameter, return boolean
   
   public double root(double num)            // safe square-root function
   {   double ans;                           // accept double parameter, return double
       try
       {   ans = Math.sqrt(num);}            // calculate square root
       catch (Exception e)
       {   ans = Double.NaN;}                // if an error occurs, return NaN
       return ans;
   }
}