import java.awt.Image;
import java.awt.Point;
import java.util.Vector;
import java.awt.Color;
import java.awt.FileDialog;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.Stroke;
import java.awt.BasicStroke;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JSlider;
import java.awt.Dimension;
import javax.swing.event.ChangeListener;
import javax.swing.event.ChangeEvent;
import java.awt.Rectangle;
import java.awt.geom.AffineTransform;
import javax.swing.ImageIcon;
import javax.swing.JButton;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import javax.swing.JFrame;

/**
 * @author Milan Ruzicka
 *
 */
public class Stamp extends Tool {
	public final boolean drawable = true;
	private static final long serialVersionUID = 31L; 
	
	public float size = 1.0f;
	public int alpha = 255;
	
	ImageIcon ii;
	
	public Stamp() {
		points = new Vector();
		colors = new Vector();
		
		colors.add(Color.blue);
		colors.add(Color.blue);
		
	}
	
	public Stamp(Image bi){
		this();
		ii = new ImageIcon(bi);
		points.add(new Point(bi.getWidth(null)/2,bi.getHeight(null)/2));
				
	}
	
	public Stamp(JFrame f) {
		this();
	}
	
	public Stamp(MyCanvas mc) {
		this();
		
	}

	
	public Stamp(Color c) {
		points = new Vector();
		colors = new Vector();
		
		Color cc = new Color(c.getRed(),c.getGreen(),c.getBlue(),alpha);
		colors.add(cc);
		colors.add(Color.blue);
	}

	/* (non-Javadoc)
	 * @see Tool#draw(java.awt.Image)
	 */
	@Override
	public void draw(Graphics g1) {
		Graphics2D g = (Graphics2D) g1;
				
		g.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
		  Stroke thindashed = new BasicStroke(size, // line width
			      /* cap style */BasicStroke.CAP_SQUARE,
			      /* join style, miter limit */BasicStroke.JOIN_ROUND, 10.0f);//,
			      /* the dash pattern *///new float[] { 8.0f, 3.0f, 2.0f, 3.0f },
			      /* the dash phase *///0.0f); /* on 8, off 3, on 2, off 3 */
		g.setStroke(thindashed);
		g.setColor((Color) colors.get(0));

		AffineTransform at = new AffineTransform();
		double angle = this.angle;

		AffineTransform at2 = new AffineTransform();
		at2.setToRotation(-angle);
	
			
		Point p0 = (Point)points.firstElement();
		Point p1 = (Point)points.lastElement();
		
		int x = at2.createTransformedShape(new Rectangle(p0)).getBounds().x;
		int y = at2.createTransformedShape(new Rectangle(p0)).getBounds().y;
		int x1 = at2.createTransformedShape(new Rectangle(p1)).getBounds().x;
		int y1 = at2.createTransformedShape(new Rectangle(p1)).getBounds().y;
		int w = x1 - x;
		int h = y1 - y;
		if (w < 0) { x += w; w = Math.abs(w); }
		if (h < 0) { y += h; h = Math.abs(h); }
		
	
		int wid = ii.getImage().getWidth(null);
		int hei = ii.getImage().getHeight(null);
		
		at.setToTranslation(p1.x-wid*size/2, p1.y-hei*size/2);
		at.scale(size, size);
		at.rotate(angle);
		g.setTransform(at);
		if (ii != null) g.drawImage(ii.getImage(),0,0,null);
		
	}
	
	public void setColor(Color c){
		Color cc = new Color(c.getRed(),c.getGreen(),c.getBlue(),alpha);
		colors.set(0, cc);
	}
	
	public void drawPreview(Graphics g1) {
		if (points.isEmpty()) return;
		Graphics2D g = (Graphics2D) g1;
		
		AffineTransform at = new AffineTransform();
		double angle = this.angle;
		at.setToRotation(angle);
	
		AffineTransform at2 = new AffineTransform();
		at2.setToRotation(-angle);
	
		g.setColor(Color.GRAY);
		
		Point p0 = (Point)points.firstElement();
		Point p1 = (Point)points.lastElement();
		
		int x = at2.createTransformedShape(new Rectangle(p0)).getBounds().x;
		int y = at2.createTransformedShape(new Rectangle(p0)).getBounds().y;
		int x1 = at2.createTransformedShape(new Rectangle(p1)).getBounds().x;
		int y1 = at2.createTransformedShape(new Rectangle(p1)).getBounds().y;
		int w = x1 - x;
		int h = y1 - y;
		if (w < 0) { x += w; w = Math.abs(w); }
		if (h < 0) { y += h; h = Math.abs(h); }
		
		
		int wid = ii.getImage().getWidth(null);
		int hei = ii.getImage().getHeight(null);
		
		at.setToTranslation(p1.x-wid*size/2, p1.y-hei*size/2);
		at.scale(size, size);
		at.rotate(angle);
		g.setTransform(at);
		if (ii != null) g.drawImage(ii.getImage(),0,0,null);
		
	}
	
	public JPanel settingPanel(){
		JPanel panel = new JPanel();
		
		panel.add(new JLabel("Set scale:"));
		
		JSlider widthSlider = new JSlider(JSlider.HORIZONTAL,1,100,Math.round(size*10f));
		widthSlider.addChangeListener(new ChangeListener(){
			public void stateChanged(ChangeEvent e){
				size = (float)((JSlider)e.getSource()).getValue()/10f;
			}
		});
		widthSlider.setPreferredSize(new Dimension(50,20));
        panel.add(widthSlider);
        
        
        
        panel.add(new JLabel("Orientation"));
        
        AngleChooser angleChooser = new AngleChooser(this,angle); 
        panel.add(angleChooser);
        
        JButton previewPanel = new JButton(){
        	private ImageIcon iii = ii;
        	{
        		setSize(80,80);
        		setPreferredSize(new Dimension(80,80));
        	}
        	public void paint(Graphics g1){
        		if (ii == null){
        			g1.setColor(Color.WHITE);
        			g1.fillRect(0, 0, getWidth(), getHeight());
        			String msg1 = "Click";
        			String msg2 = "to load";
        			String msg3 = "image ...";
        			g1.setColor(Color.BLACK);
        			g1.drawRect(0, 0, getWidth()-1, getHeight()-1);
        			g1.drawBytes(msg1.getBytes(), 0, msg1.length(), getWidth()/2-20,getHeight()/2-15 );
        			g1.drawBytes(msg2.getBytes(), 0, msg2.length(), getWidth()/2-23,getHeight()/2 );
        			g1.drawBytes(msg3.getBytes(), 0, msg3.length(), getWidth()/2-25,getHeight()/2+15 );

        		}
        		else {
        			Graphics2D g2 = (Graphics2D)g1;
        			g2.setColor(Color.white);
        			g2.fillRect(0, 0, getWidth(), getHeight());
        			AffineTransform at = new AffineTransform();
        			at.setToScale(((double)getWidth())/((double)ii.getIconWidth()), ((double)getHeight())/((double)ii.getIconHeight()));
        			g2.drawImage(ii.getImage(), at, null);
        		}
        	}
        };
 

        panel.add(new JLabel("Preview"));
        
        previewPanel.addActionListener(new ActionListener(){
        	FileDialog loadDialog = new FileDialog(new JFrame(),"Load stamp from file ..",FileDialog.LOAD);
        	public void actionPerformed(ActionEvent e){
        		loadDialog.show();
        		if (loadDialog.getFile() != null){
        			ii = new ImageIcon(loadDialog.getDirectory()+loadDialog.getFile());
        			if (ii.getImage().getWidth(null)==-1){

        				ii = null;
        				
        			}
        		}
        	}
        });
        
        panel.add(previewPanel);
        
		return panel;
	}
	
	public boolean isDrawable(){
		return true;
	}

}