import java.awt.*;
import java.net.*;
import java.awt.Image;
import java.lang.*;
import java.applet.Applet;
import javax.swing.*;
import java.awt.event.*;
import javax.swing.event.*;
import javax.swing.Timer;
import javax.swing.border.BevelBorder;
import javax.swing.border.SoftBevelBorder;
import javax.swing.border.TitledBorder;
import javax.swing.border.EtchedBorder;

/**
 * A basic extension of the javax.swing.JApplet class
 */
public class JApplet1 extends JApplet 
{
    protected GPIOcomm GPIO;
    
    
    String OldStatus;
    Timer ConnectTimer, StatusTimer;
    SymAction lSymAction;
    java.awt.Color EnableColor = new java.awt.Color(102,102,153);
    java.awt.Color ForegColor = new java.awt.Color(102,102,153);
    java.awt.Color BackgColor = new java.awt.Color(204,204,204);
    java.awt.Color DisableColor = java.awt.Color.gray;
    Font fnt = new Font("Dialog", Font.BOLD, 12);
    int p, GPIOS=3;
    int S=100;
    GPIOpanel[] GPIOdisplay = new GPIOpanel[GPIOS];
    
	public void init()
	{
		// Take out this line if you don't use symantec.itools.net.RelativeURL or symantec.itools.awt.util.StatusScroller
//		Context.setApplet(this);
		
		// This line prevents the "Swing: checked access to system event queue" message seen in some browsers.
		getRootPane().putClientProperty("defeatSystemEventQueueCheck", Boolean.TRUE);
		
		// This code is automatically generated by Visual Cafe when you add
		// components to the visual environment. It instantiates and initializes
		// the components. To modify the code, only use code syntax that matches
		// what Visual Cafe can generate, or Visual Cafe may be unable to back
		// parse your Java file into its visual environment.
		//{{INIT_CONTROLS
		setSize(604,386);
		getContentPane().setLayout(null);
		getContentPane().setBackground(BackgColor);
		getContentPane().setForeground(ForegColor);

		//}}
		
		//{{REGISTER_LISTENERS
		lSymAction = new SymAction();
		SymAction lSymAction = new SymAction();
		//}}
//	    try {
//    	    baseIconImage = getImage(symantec.itools.net.RelativeURL.getURL("CP_CTL_rbs.gif"));
    	    baseIconImage = getImage(getCodeBase(), "CP_CTL_rbs.gif");
//		    }
//	    catch (java.net.MalformedURLException error) { }
        
		for (p=0;p<GPIOS;p++)
		{
            GPIOdisplay[p] = new GPIOpanel(baseIconImage, p);
    		GPIOdisplay[p].setLayout(null);
    		getContentPane().add(GPIOdisplay[p]);
            GPIOdisplay[p].setBounds(120+(p*120), 20, 110, 340);
        }
		DirectionLabel.setForeground(ForegColor);
		DirectionLabel.setFont(fnt);
		DirectionLabel.setBounds(20,76,100,24);
		DirectionLabel.setText("Directions:");
		getContentPane().add(DirectionLabel);
		ActivelevelLabel.setForeground(ForegColor);
		ActivelevelLabel.setFont(fnt);
		ActivelevelLabel.setBounds(20,76+S,100,24);
		ActivelevelLabel.setText("Active levels:");
		getContentPane().add(ActivelevelLabel);
		StateLabel.setForeground(ForegColor);
		StateLabel.setFont(fnt);
		StateLabel.setBounds(20,76+2*S,100,24);
		StateLabel.setText("States:");
		getContentPane().add(StateLabel);
		
		UpdateDirectionButton.setForeground(ForegColor);
		UpdateDirectionButton.setFont(fnt);
		UpdateDirectionButton.setBounds(500,70,85,36);
		UpdateDirectionButton.setText("Update");
		UpdateDirectionButton.addActionListener(lSymAction);
        UpdateDirectionButton.setEnabled(false);
		UpdateDirectionButton.setActionCommand("Action");
		UpdateDirectionButton.setRolloverEnabled(true);
//		UpdateDirectionButton.setBorder(bevelBorder2);
		getContentPane().add(UpdateDirectionButton);
		UpdateActivelevelButton.setForeground(ForegColor);
		UpdateActivelevelButton.setFont(fnt);
		UpdateActivelevelButton.setBounds(500,70+S,85,36);
		UpdateActivelevelButton.addActionListener(lSymAction);
        UpdateActivelevelButton.setEnabled(false);
		UpdateActivelevelButton.setText("Update");
		UpdateActivelevelButton.setActionCommand("Action");
		UpdateActivelevelButton.setRolloverEnabled(true);
//		UpdateActivelevelButton.setBorder(bevelBorder2);
		getContentPane().add(UpdateActivelevelButton);
		UpdateStateButton.setForeground(ForegColor);
		UpdateStateButton.setFont(fnt);
		UpdateStateButton.setBounds(500,70+2*S,85,36);
		UpdateStateButton.addActionListener(lSymAction);
        UpdateStateButton.setEnabled(false);
		UpdateStateButton.setText("Update");
		UpdateStateButton.setActionCommand("Action");
		UpdateStateButton.setRolloverEnabled(true);
//		UpdateStateButton.setBorder(bevelBorder2);
		getContentPane().add(UpdateStateButton);
       
	
		StatusBar.setHorizontalTextPosition(javax.swing.SwingConstants.LEFT);
		StatusBar.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);
		StatusBar.setOpaque(true);
		StatusBar.setBorder(bevelBorder1);
		getContentPane().add(StatusBar);
		StatusBar.setForeground(ForegColor);
		StatusBar.setBounds(1,3*S+60,202,24);
		SentLabel.setForeground(ForegColor);
		SentLabel.setFont(new Font("Courier New", Font.BOLD, 12));
		SentLabel.setBounds(203,3*S+60,200,24);
		SentLabel.setText("Sent: 0123456789ABCDEF01");
		SentLabel.setBorder(bevelBorder1);
		SentLabel.setHorizontalAlignment(javax.swing.JLabel.CENTER);
		getContentPane().add(SentLabel);
		ReceivedLabel.setForeground(ForegColor);
		ReceivedLabel.setFont(new Font("Courier New", Font.BOLD, 12));
		ReceivedLabel.setBounds(403,3*S+60,200,24);
		ReceivedLabel.setText("Received: 0123456789");
		ReceivedLabel.setBorder(bevelBorder1);
		ReceivedLabel.setHorizontalAlignment(javax.swing.JLabel.CENTER);
		getContentPane().add(ReceivedLabel);
	
	
	}
	
	
	public void start()
	{
	    ConnectTimer = new Timer(2000, lSymAction);
	    ConnectTimer.setRepeats(false);
	    ConnectTimer.start();
		StatusBar.setText("  Trying to connect.....");
	}
	
	
	public void connect()
	{
		String[] args={};
//		String[] args={"172.19.203.73"};
		InetAddress ip_addr = null;
		if (args.length > 0) {
			try{
				ip_addr = InetAddress.getByName(args[0]);
			}
			catch (UnknownHostException e){}
		}
		else {
			try{
				ip_addr = InetAddress.getByName(getCodeBase().getHost());
			}
			catch (UnknownHostException e){}
		}
        GPIO = new GPIOcomm(ip_addr);
        if (GPIO.gtp1.s != null)
        {
		    GPIO.getFunctions();
		    GPIO.getDirections();
		    GPIO.getActivelevels();
		    GPIO.getStates();
		    GPIO.mask = 0;
		    for (p=0;p<GPIOS;p++)
		    {
		        GPIO.mask |= 1<<p;
		        GPIOdisplay[p].updateGPIOfunction((GPIO.function & (1<<p)) != 0);
		        GPIOdisplay[p].updateGPIOdirection((GPIO.direction & (1<<p)) != 0);
		        GPIOdisplay[p].updateGPIOactivelevel((GPIO.activelevel & (1<<p)) != 0);
		        GPIOdisplay[p].updateGPIOstate((GPIO.state & (1<<p)) != 0);
    		}        
    		SentLabel.setText("Sent: "+toHex(GPIO.cmd,9));
    		ReceivedLabel.setText("Received: "+toHex(GPIO.resp,5));
		    StatusBar.setText("  Connected.");
            UpdateDirectionButton.setEnabled(true);
            UpdateActivelevelButton.setEnabled(true);
            UpdateStateButton.setEnabled(true);
        }
		else
		{
		    StatusBar.setText("  Unable to connect.");
		}
    }

	//{{DECLARE_CONTROLS
	javax.swing.JButton UpdateDirectionButton = new javax.swing.JButton();
	javax.swing.JButton UpdateActivelevelButton = new javax.swing.JButton();
	javax.swing.JButton UpdateStateButton = new javax.swing.JButton();
	javax.swing.JLabel DirectionLabel = new javax.swing.JLabel();
	javax.swing.JLabel ActivelevelLabel = new javax.swing.JLabel();
	javax.swing.JLabel StateLabel = new javax.swing.JLabel();
	javax.swing.JLabel SentLabel = new javax.swing.JLabel();
	javax.swing.JLabel ReceivedLabel = new javax.swing.JLabel();
	javax.swing.border.BevelBorder bevelBorder1 = new javax.swing.border.BevelBorder(javax.swing.border.BevelBorder.LOWERED);
	javax.swing.border.EtchedBorder etchedBorder1 = new javax.swing.border.EtchedBorder();
	javax.swing.border.BevelBorder bevelBorder2 = new javax.swing.border.BevelBorder(javax.swing.border.BevelBorder.RAISED);
	javax.swing.JLabel StatusBar = new javax.swing.JLabel();
    java.awt.Image baseIconImage;
	
	
	//}}
    
	class SymAction implements java.awt.event.ActionListener
	{
		public void actionPerformed(java.awt.event.ActionEvent event)
		{
			Object object = event.getSource();
			if (object == UpdateDirectionButton)
				UpdateDirectionButton_actionPerformed(event);
			else if (object == UpdateActivelevelButton)
				UpdateActivelevelButton_actionPerformed(event);
			else if (object == UpdateStateButton)
				UpdateStateButton_actionPerformed(event);
			else if (object == ConnectTimer)
				connect();
			else if (object == StatusTimer)
				ReturnStatus();
		}
	}


	void UpdateDirectionButton_actionPerformed(java.awt.event.ActionEvent event)
	{
		GPIO.direction = 0;
		for (p=0;p<GPIOS;p++)
		{
		    GPIO.direction += GPIOdisplay[p].getGPIOdirection()<<p;
    	}        
        if (GPIO.setDirections() == -1) DispConErr("Could not update Directions!");
        else
        {
    		DispTempStatus("Directions updated.", 1000, false);
    		SentLabel.setText("Sent: "+toHex(GPIO.cmd,9));
    		ReceivedLabel.setText("Received: "+toHex(GPIO.resp,5));
    	}
		for (p=0;p<GPIOS;p++)
		{
		        GPIOdisplay[p].updateGPIOdirection((GPIO.direction & (1<<p)) != 0);
    	}        
	}
	
	void UpdateActivelevelButton_actionPerformed(java.awt.event.ActionEvent event)
	{
		GPIO.activelevel = 0;
		for (p=0;p<GPIOS;p++)
		{
		    GPIO.activelevel += GPIOdisplay[p].getGPIOactivelevel()<<p;
    	}        
        if (GPIO.setActivelevels() == -1) DispConErr("Could not update Active levels!");
        else
        {
    		DispTempStatus("Active levels updated.", 1000, false);
    		SentLabel.setText("Sent: "+toHex(GPIO.cmd,9));
    		ReceivedLabel.setText("Received: "+toHex(GPIO.resp,5));
    	}
	}
	
	void UpdateStateButton_actionPerformed(java.awt.event.ActionEvent event)
	{
		GPIO.state = 0;
		for (p=0;p<GPIOS;p++)
		{
		    GPIO.state += GPIOdisplay[p].getGPIOstate()<<p;
    	}        
        if (GPIO.setStates() == -1) DispConErr("Could not update States!");
        else
        {
    		DispTempStatus("States updated.", 1000, false);
    		SentLabel.setText("Sent: "+toHex(GPIO.cmd,9));
    		ReceivedLabel.setText("Received: "+toHex(GPIO.resp,5));
    	}
	}
	
    
    
    public void DispConErr(String StatStr)
    {
        StatusBar.setText("  "+StatStr+"  Check connection and try again.");
        getToolkit().beep();
    }
    
    
    public void DispTempStatus(String StatStr, int duration, boolean bp)
    {
//		OldStatus = StatusBar.getText();
        OldStatus = "  Connected.";
	    StatusTimer = new Timer(duration, lSymAction);
	    StatusTimer.setRepeats(false);
	    StatusTimer.start();
		StatusBar.setText("  "+StatStr);
		if (bp) getToolkit().beep();
    }
    
    public void ReturnStatus()
    {
		StatusBar.setText(OldStatus);
    }
    
    private String toHex(byte[] a, int l)
    {
        int c;
        String s="";
        for (c=0;c<l;c++)
        {
            s+=Integer.toString((int)a[c]+(a[c]<0?512:256), 16).substring(1,3);
        }
        return s;
    }
    
    public void destroy()
    {
        GPIO.destroy();
        super.destroy();
    }

}

