// Source Code for ClientFrame.class   //
// Client Code for Desktop Calendar    //

// Code based on using Server #18     //
// Written by Khalid Mufti - Group 31 //

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

// This class handles the frame which enables a user to log into the //
// server by entering a login name and password.		     //	
// Inherits from the Frame class and requires the frame title and a  //
// socket connected to the server, as parameters                     //  
public class ClientFrame extends Frame implements ActionListener
{
   private CalendarFrame calframe;
   private AdminFrame adminframe;
   private ClientSocket clientsocket;
   private MsgBox msgbox;
   private String username, userpassword, buf;
   private Button login, help, quit;
   private GridBagLayout gbLayout;
   private GridBagConstraints gbConstraints; 
   private TextField loginname, password;
   private Label loginlabel, passwordlabel;
   private Label dummylabel; //this is a dummy label used to place space between components; 
   private AdminHelpBox helpbox;
   private StringBuffer str;

   // The constructor for the class.  Requires a frame title and socket connected  //
   // to the server as parameters.                                                 //
   public ClientFrame(String s, ClientSocket cs)
   {
     // Call Dialog class constructor //
     super(s);

     // Set window size and copy parameters to local variables //
     setSize(500,300);
     clientsocket = cs;
     username = new String();
     userpassword = new String();  
 
     // Instantiate grid for layout purposes //
     gbLayout = new GridBagLayout();
     gbConstraints = new GridBagConstraints();
     setLayout (gbLayout);       
     
     // Allocate memory for all new items in Dialog, and add action listeners //
     gbConstraints.fill = GridBagConstraints.NONE;  
     login = new Button ("Login");
     login.addActionListener (this);
     help  = new Button ("Help");
     help.addActionListener (this);
     quit  = new Button ("Quit");
     quit.addActionListener (this);
     loginname = new TextField (20);
     loginname.addActionListener (this);
     password = new TextField (20);
     password.addActionListener (this);
     password.setEchoChar ('*');     
     loginlabel = new Label ("Login ID:");
     passwordlabel = new Label ("Password:");
     dummylabel = new Label ("");   //used to provide spacing//

     // Now place the components in the Dialog, based on the grid bag layout // 
     gbConstraints.weightx=0;
     gbConstraints.weighty=0;
     addObj (loginlabel,    0, 0, 1, 1);
     addObj (loginname,     0, 1, 2, 1);
     addObj (passwordlabel, 1, 0, 1, 1);
     addObj (password,      1, 1, 2, 1);
     addObj (dummylabel,    2, 0, 2, 1);
     gbConstraints.weightx=0;
     gbConstraints.weighty=0;
     gbConstraints.fill = GridBagConstraints.BOTH;
     addObj (help,          3, 1, 1, 2);
     gbConstraints.weightx=0;
     gbConstraints.weighty=0;
     addObj (login,         3, 2, 1, 1);
     addObj (quit,          4, 2, 1, 1);

     // Add a listener for closing the window prematurely and set the textfields //
     // to an empty value                                                        //
     addWindowListener (new CloseWindow());
     loginname.setText("");
     password.setText("");    
   } 

   // This function handles any action events from the user //
   public void actionPerformed (ActionEvent e)
   {   
      // If user pressed the login button //
      if ((e.getSource())==login)
      {
         LoginHandler();
      }

      // If user pressed the help button //
      else if ((e.getSource())==help)
      {
         helper();
      }	
 
      // If user pressed the quit button //
      else if ((e.getSource())==quit)
      {
         try  //close the socket//
         {
            clientsocket.Close();
         }
    
        catch (IOException io)  // Connection must have been lost //
        {        
        }

        dispose();
      }
   }

   // This function simply adds an object (registers it) to the Dialog //
   // Further, it sets various parts of the grid bag layout            // 
   private void addObj (Component c, int row, int column, int width, int height)
   {
      gbConstraints.gridx=column;
      gbConstraints.gridy=row;  
      gbConstraints.gridwidth=width;
      gbConstraints.gridheight=height;
      gbLayout.setConstraints (c, gbConstraints);
      add (c);
   }    

   // This function attempts to login to the server using the username and //
   // password provided by the user				           //
   private void LoginHandler ()
   {
     try
     {
        username = new String ();
        username = loginname.getText();   // Get user input //
        userpassword = new String ();
        userpassword = password.getText();  // Get user input //

        // Send request to server //
        clientsocket.Write("login," + username);
        buf=clientsocket.Read();      
        clientsocket.Write("password," + userpassword);
        buf=clientsocket.Read();
             
        // Parse numerical response from server //        
        if (buf.regionMatches(false, 0 , "712", 0,  3))
        {
           msgbox = new MsgBox (this, "  LOGIN ERROR", "Invalid Login! Try Again!", 250, 150);
           msgbox.setVisible(true);
           loginname.setText("");
           password.setText("");    
        }     

        else if (buf.regionMatches(false, 0 , "711", 0,  3))
        {
           msgbox = new MsgBox (this, "  LOGIN ERROR", "User already Logged on!", 250, 150);
           msgbox.setVisible(true);
           loginname.setText("");
           password.setText("");    
        }     
    
        else if (buf.regionMatches(false, 0 , "101", 0,  3))
        {
           if (username.regionMatches(false, 0 , "admin", 0,  5)) // Admin loggin in //
           {
              adminframe = new AdminFrame (userpassword, clientsocket); //need to pass socket
              adminframe.setVisible (true);
           }
 
           else // Normal user logging in //
           {
               calframe = new CalendarFrame(username,clientsocket);
               calframe.setVisible(true);
           }
           
           dispose();      
        }
            
        else
        {	
           msgbox = new MsgBox (this, "  LOGIN FAILED", "Invalid Username/Password!",250, 150);
           msgbox.setVisible(true);
           loginname.setText("");
           password.setText("");    
        }	
     }

     catch (IOException e)  // Connection must have been lost //
     {     
         msgbox = new MsgBox (this, "  NETWORK ERROR", "Connection to Server Lost!",250, 150);
         msgbox.setVisible(true);
         dispose();   
     }
   }

   // This function simply pops up a help dialog box that displays help on using //
   // this dialog screen.                                                        //
   private void helper()
   {
      // Set what the help box should say //
      str = new StringBuffer(); 
      str.append("This screen is used to login to the desktop server.\n");
      str.append("\n");
      str.append("For the login id field, enter your unique username\n");
      str.append("here.  This is set by the system administrator.\n");
      str.append("\n");
      str.append("For the password, enter your secret password.  If\n");
      str.append("you have forgotten your password, then you must\n"); 
      str.append("contact the system administrator!\n");
      str.append("\n");
      str.append("When done, cick on the Login button; otherwise,\n");
      str.append("click Quit to exit.\n");

      // Create and show modal help box //
      helpbox = new AdminHelpBox (this, "  Help Screen", str.toString(), true, 300, 300);
      helpbox.setVisible(true); 
   }
}

