import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Point;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.PrintWriter;
import java.util.Scanner;

import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JMenu;
import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.JPanel;
import javax.swing.border.BevelBorder;

public class BasicLinePix extends JFrame {

	/**
	 * @param args
	 */
	private JPanel drawingPanel; // user draws here
	private JPanel controlPanel; // drawing related controls located here

	private JButton exitButton;

	private Container cp;
	private JPanel statusBar;
	private JLabel statusLabel;// used to show informational messages

	private Line[] lines;
	private int lineCount;
	private JMenuBar menuBar;
	private JMenu fileMenu;
	private ActionEventHandler aeh;

	public static void main(String[] args) {
		// TODO Auto-generated method stub

		BasicLinePix lp = new BasicLinePix();
		lp.setVisible(true);

	}

	public BasicLinePix() {
		setTitle("Basic Line Pix 1.0");
		setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
		cp = getContentPane();
		cp.setLayout(new BorderLayout());

		drawingPanel = makeDrawingPanel();

		controlPanel = makeControlPanel();
		statusBar = createStatusBar();

		cp.add(drawingPanel, BorderLayout.CENTER);
		// cp.add(controlPanel, BorderLayout.EAST);
		cp.add(statusBar, BorderLayout.SOUTH);

		lines = new Line[100];

		buildMenu();

		pack();
	}

	public void buildMenu() {
		menuBar = new JMenuBar();
		fileMenu = new JMenu("File");

		JMenuItem menuItem = new JMenuItem("Open");
		menuItem.addActionListener(aeh);
		fileMenu.add(menuItem);

		menuItem = new JMenuItem("Save");
		menuItem.addActionListener(aeh);
		fileMenu.add(menuItem);

		menuItem = new JMenuItem("Exit");
		menuItem.addActionListener(aeh);
		fileMenu.add(menuItem);

		menuBar.add(fileMenu);
		setJMenuBar(menuBar);

	}

	private JPanel makeControlPanel() {
		// TODO Auto-generated method stub
		JPanel p = new JPanel();
		p.setPreferredSize(new Dimension(100, 400));
		p.setBackground(Color.WHITE);

		exitButton = new JButton("Exit");
		aeh = new ActionEventHandler();

		exitButton.addActionListener(aeh);

		p.add(exitButton);

		return p;
	}

	private JPanel makeDrawingPanel() {
		// TODO Auto-generated method stub
		JPanel p = new JPanel();
		p.setPreferredSize(new Dimension(500, 400));
		p.setBackground(Color.YELLOW);

		MouseEventHandler meh = new MouseEventHandler();
		p.addMouseListener(meh);
		p.addMouseMotionListener(meh);

		return p;
	}

	public void paint(Graphics g) {
		super.paint(g);

		for (int i = 0; i < lineCount; i++)
			lines[i].draw(drawingPanel.getGraphics());

	}

	private JPanel createStatusBar() {
		JPanel panel = new JPanel();
		panel.setLayout(new BorderLayout());
		statusLabel = new JLabel("None");
		panel.add(statusLabel, BorderLayout.CENTER);

		panel.setBorder(new BevelBorder(BevelBorder.LOWERED));

		return panel;
	}

	private void loadDrawing() {
		// TODO Auto-generated method stub
		File inFile = new File("picture.txt");
		Scanner s = null;
		try {
			s = new Scanner(inFile);

			lineCount = s.nextInt();
			lines = new Line[100];

			for (int i = 0; i < lineCount; i++) {
				int x1 = s.nextInt();
				int y1 = s.nextInt();
				int x2 = s.nextInt();
				int y2 = s.nextInt();

				lines[i] = new Line(x1, y1, x2, y2);
			}
			repaint();

		} catch (FileNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} finally {
			if (s != null)
				s.close();
			repaint();
		}
	}

	private void saveDrawing() {
		// TODO Auto-generated method stub
		File outFile = new File("picture.txt");
		FileOutputStream outStream;
		PrintWriter textStream = null;
		try {
			outStream = new FileOutputStream(outFile);
			textStream = new PrintWriter(outStream);

			textStream.println(lineCount);
			for (int i = 0; i < lineCount; i++) {
				Line l = lines[i];
//				textStream.println(l.getStartX() + " " + l.getStartY() + " "
//						+ l.getEndX() + " " + l.getEndY());
				textStream.println(l);
			}
		} catch (FileNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} finally {
			if (textStream != null)
				textStream.close();
		}

	}

	// Inner class - instances of this class handle action events
	private class ActionEventHandler implements ActionListener {

		public void actionPerformed(ActionEvent arg0) {
			if (arg0.getActionCommand().equals("Exit")) {
				statusLabel.setText("Exiting program...");
				System.exit(0);
			} else if (arg0.getActionCommand().equals("Open")) {
				statusLabel.setText("Loading drawing from file...");
				loadDrawing();
			}
			if (arg0.getActionCommand().equals("Save")) {
				statusLabel.setText("Saving drawing to file...");
				saveDrawing();
			}

			repaint();

		}

	}

	private class MouseEventHandler implements MouseListener,
			MouseMotionListener {
		private int startX, startY; // line start coordinates
		private int lastX, lastY; // line most recent end point

		public void mouseClicked(MouseEvent arg0) {
			// TODO Auto-generated method stub

		}

		public void mouseEntered(MouseEvent arg0) {
			// TODO Auto-generated method stub

		}

		public void mouseExited(MouseEvent arg0) {
			// TODO Auto-generated method stub

		}

		public void mousePressed(MouseEvent e) {
			// TODO Auto-generated method stub
			startX = e.getX();
			startY = e.getY();

			// initialize lastX, lastY
			lastX = startX;
			lastY = startY;

		}

		public void mouseReleased(MouseEvent e) {
			// TODO Auto-generated method stub;
			lines[lineCount] = new Line(startX, startY, lastX, lastY);
			lineCount++;

		}

		public void mouseDragged(MouseEvent e) {
			// TODO Auto-generated method stub

			// Implement rubber-band cursor
			Graphics g = drawingPanel.getGraphics();
			g.setColor(Color.black);

			g.setXORMode(drawingPanel.getBackground());

			// REDRAW the line that was last drawn (using the next line of code)
			// in the previous drag event
			// yellow pixels turn black. This includes background pixels as well
			// as yellow breaks in existing lines caused by the last draw.
			g.drawLine(startX, startY, lastX, lastY);

			// draw line to current mouse position
			// XOR mode: yellow pixels become black
			// black pixels, like those from existing lines, temporarily become
			// yellow
			g.drawLine(startX, startY, e.getX(), e.getY());
			lastX = e.getX();
			lastY = e.getY();
		}

		public void mouseMoved(MouseEvent arg0) {
			// TODO Auto-generated method stub

		}

	}

}
