import java.util.*;
import java.awt.*;
import java.awt.image.*;
import java.awt.event.*;
import java.awt.geom.*;
import javax.swing.*;
import java.io.*;
import java.net.*;
import java.io.*;
import java.util.*;

public class ADCColors extends JApplet {

	ADCColorsFrame frame;
	
	public void init() {
		try {
			// For native Look and Feel, uncomment the following code.
		        /*
		        try {
		                UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
		        }
		        catch (Exception e) {
		        }
		        */
			frame = new ADCColorsFrame();
			frame.initComponents();
			frame.setVisible(true);
		}
		catch (Exception e) {
			e.printStackTrace();
		}
	}

	// Main entry point
	static public void main(String[] args) {
		ADCColors colors = new ADCColors();
		colors.init();
		
		try {
			
		        int myPort = 10181;
		        ServerSocket listener = new ServerSocket(myPort);
		
		        while (true){
		            System.out.println("Waiting for Connection from CoBox");
		            Socket client = listener.accept();
		            ClientThread myClientThread = new ClientThread(client, colors.frame);
		            myClientThread.start();
		        }
		}
		catch (Exception e)
		{
			e.printStackTrace();
		}		
	}
}


class ADCColorsFrame extends javax.swing.JFrame {
	// Constants
	int frameHeight = 480;
	int frameWidth = 640;

	// Graphics Objects
	private BufferedImage bImage = new BufferedImage(frameWidth, frameHeight, java.awt.image.BufferedImage.TYPE_INT_ARGB);

	// UI Objects
	DrawingPanel drawingPanel = new DrawingPanel();
	javax.swing.JMenuBar menuBar = new javax.swing.JMenuBar();

	// Default Constructor
	public ADCColorsFrame() {
	}

	public void initComponents() throws Exception
	{

		// Frame initialization
		setSize(new java.awt.Dimension(frameWidth,frameHeight));
		drawingPanel.setVisible(true);
		drawingPanel.setLayout(null);
		setLocation(new java.awt.Point(0,0));
		setResizable(false);
		setTitle("ADC Colors");

		// Component initialzation
		menuBar.setVisible(true);

		setJMenuBar(menuBar);

		getContentPane().add(drawingPanel);
		setDefaultCloseOperation(EXIT_ON_CLOSE);


	}


	public void updateImage(int colorValue)
	{
		Color newColor = Color.black;
		if (colorValue > 64 && colorValue < 128)
		{
			newColor = Color.blue;
		}
		else if (colorValue < 64 && colorValue > 0)
		{
			newColor = Color.red;
		}
		else if (colorValue < 0 && colorValue > -64)
		{
			newColor = Color.green;
		}
		else if (colorValue < -64)
		{
			newColor = Color.pink;
		}

		Graphics2D bImageGraphics = (Graphics2D) bImage.getGraphics();
		bImageGraphics.setColor(newColor);
    		bImageGraphics.fillRect(0,0,bImage.getWidth(), bImage.getHeight());
    		drawingPanel.repaint();
	}

	private class DrawingPanel extends javax.swing.JPanel {
		// Default Constructor
		public DrawingPanel() {
		}

		// Override Paint Method
		protected void paintComponent(Graphics g)
		{
			super.paintComponent(g);
			g.drawImage(bImage, 0, 0, this);
		}
	}
}

class ClientThread extends Thread   {
    Socket Client;              // contains the socket
    PrintWriter pout;           // an object to print text to the client
    OutputStream outStream;     // an output stream to talk to the client
    ADCColorsFrame theAppFrame;

	byte responseByte = 66;
	byte connectionByte = 65;

    ClientThread (Socket _client, ADCColorsFrame _appFrame) {
        Client = _client;
        theAppFrame = _appFrame;
     }

    public void run(){
        try{
            System.out.println("CoBox Connected");
            InputStream in = Client.getInputStream();

            outStream = Client.getOutputStream();
            pout = new PrintWriter(outStream,true);

            while(true){
		byte inBytes[] = new byte[1]; // Should change to integer not byte array...
		in.read(inBytes);
		
		System.out.println("Received: " + inBytes[0]);
		if (inBytes[0] == connectionByte)
		{
			System.out.println("Sending: " + responseByte);
			sendByte(responseByte);		
		}
		else if (inBytes[0] == responseByte)
		{
			System.out.println("Sending: " + responseByte);
			sendByte(responseByte);
		}
		else
		{
			System.out.println("Sending: " + responseByte + " and updating image");
			System.out.println("Sending: " + responseByte);
			theAppFrame.updateImage((int) inBytes[0]);
		}
	    }
        }catch (IOException e){
            System.out.println("Connection Lost");
        }
   }

   public void sendByte(int thisByte) {
          try {
                outStream.write(thisByte);
          } catch (IOException e) {
                System.out.println("Bad Output Stream");
          }
   }
} // End ClientThread.java
