File source

import georegression.metric.UtilAngle;
import gnu.io.CommPort;
import gnu.io.CommPortIdentifier;
import gnu.io.SerialPort;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.EventQueue;

import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.border.EmptyBorder;
import javax.swing.JButton;
import javax.swing.BoxLayout;
import javax.swing.JColorChooser;
import javax.swing.SwingConstants;
import javax.swing.Timer;

import com.github.sarxos.webcam.Webcam;
import com.github.sarxos.webcam.WebcamResolution;

import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import java.awt.image.BufferedImage;
import java.io.IOException;
import javax.swing.JLabel;
import javax.swing.JCheckBox;


public class SorterGUI extends JFrame {

    private JPanel contentPane;
    private SerialPort port;
    private ImagePanel imgPanel;
    private boolean motorRunning = false;
    private JLabel lblColor;
    Color activeColor;
    Color targetColor;
    private JLabel lblTarget;
    private JCheckBox chckbxAutoSort;
    private Timer readTimer = null;
    private ImagePanel imgPanel2;

    /**
     * Launch the application.
     */
    public static void main(String[] args) {
        EventQueue.invokeLater(new Runnable() {
            public void run() {
                try {
                    final SorterGUI frame = new SorterGUI();
                    frame.setVisible(true);

                    /* open serial port */
                    CommPortIdentifier pI = CommPortIdentifier.getPortIdentifier("COM4");
                    CommPort port = pI.open("myApp", 1000);
                    SerialPort serialPort = (SerialPort) port;
                    serialPort.setSerialPortParams(460800,SerialPort.DATABITS_8,SerialPort.STOPBITS_1,SerialPort.PARITY_NONE);
                    serialPort.addEventListener(new SerialReader(port.getInputStream(), frame));
                    serialPort.notifyOnDataAvailable(true);
                    frame.setPort(serialPort);
                    
                    /* open webcam */
                    final Webcam webcam = Webcam.getDefault();
                    webcam.setViewSize(WebcamResolution.VGA.getSize());
                    webcam.open();
                     
                    /* start image capturing thread */
                    new Thread(){
                        public void run(){
                            while(true){
                        final BufferedImage image1 = webcam.getImage();
                        BufferedImage out = new BufferedImage(image1.getWidth(), image1.getHeight(), BufferedImage.TYPE_INT_RGB);
                        frame.setActiveColor(ColorReader.main(image1, out));
                            frame.setWebcamImage(image1);
                            frame.getImgPanel2().setImage(out);
                                
                            try {
                                // let CPU some rest
                                    Thread.sleep(50);
                                } catch (InterruptedException e) {
                                    e.printStackTrace();
                                }
                            }
                        }
                    }.start();                    
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        });        
    }

    /**
     * Create the frame.
     */
    public SorterGUI() {
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setBounds(100, 100, 450, 300);
        contentPane = new JPanel();
        contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
        setContentPane(contentPane);
        contentPane.setLayout(new BorderLayout(0, 0));
        
        JPanel panel = new JPanel();
        contentPane.add(panel, BorderLayout.EAST);
        panel.setLayout(new BoxLayout(panel, BoxLayout.PAGE_AXIS));
        
        JButton btnNext = new JButton("Next");
        btnNext.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent arg0) {
                goToA();
             }
        });
        panel.add(btnNext);
        
        JButton btnRead = new JButton("Read color");
        btnRead.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent arg0) {
                doSort(false);
            }
        });
        btnRead.setHorizontalAlignment(SwingConstants.RIGHT);
        panel.add(btnRead);
        
        JButton btnSetTargetColor = new JButton("Set target color");
        btnSetTargetColor.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                setTargetColor(activeColor);
                getLblTarget().setBackground(targetColor);
            }
        });
        panel.add(btnSetTargetColor);
        
        JButton btnSort = new JButton("Sort");
        btnSort.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
              doSort(true);
            }
        });
        panel.add(btnSort);
        
        JButton btnGoA = new JButton("Go to A");
        btnGoA.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                goToA();
            }
        });
        panel.add(btnGoA);
        
        JButton btnGoB = new JButton("Go to B");
        btnGoB.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                goToB();
            }
        });
        panel.add(btnGoB);
        
        JButton btnSelectColors = new JButton("Select color");
        btnSelectColors.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent arg0) {
                setTargetColor(JColorChooser.showDialog(contentPane, "Color", activeColor));    
                getLblTarget().setBackground(targetColor);
            }
        });
        panel.add(btnSelectColors);
        
        chckbxAutoSort = new JCheckBox("Auto sort");
        panel.add(chckbxAutoSort);
        
        lblTarget = new JLabel("TARGET");
        lblTarget.setOpaque(true);
        panel.add(lblTarget);
        
        lblColor = new JLabel("COLOR");
        lblColor.setOpaque(true);
        panel.add(lblColor);
        
        JPanel panel_1 = new JPanel();
        contentPane.add(panel_1, BorderLayout.CENTER);
        panel_1.setLayout(new BoxLayout(panel_1, BoxLayout.X_AXIS));
        
        imgPanel = new ImagePanel(640,480);
        panel_1.add(imgPanel);
        
        imgPanel2 = new ImagePanel(640, 480);
        panel_1.add(imgPanel2);
    }
    
    public void setPort(SerialPort port){
        this.port = port;
    }
    
    public void setWebcamImage(BufferedImage image){
        imgPanel.setImage(image);
    }
    
    public void motorStop(){
        System.out.println("motor stopped");
        motorRunning = false;

        /* if AutoSort checked, wait 1,5sec and run doSort() */
        if(chckbxAutoSort.isSelected()){
            if(readTimer != null){
                readTimer.stop();
            }
            readTimer = new Timer(9999, new ActionListener() {
                
                @Override
                public void actionPerformed(ActionEvent arg0) {
                    if(!motorRunning){
                        doSort(true);
                    }
                }
            });
            readTimer.setInitialDelay(1500);
            readTimer.setRepeats(false);
            readTimer.start();
        }
    }
    protected JLabel getLblColor() {
        return lblColor;
    }
    
    public void setActiveColor(Color color){
        activeColor = color;
    }
    
    public void setTargetColor(Color color){
        targetColor = color;
    }
    protected JLabel getLblTarget() {
        return lblTarget;
    }
    
    protected void goToA(){
        try {
            port.getOutputStream().write("BACK\n".getBytes());
            motorRunning = true;
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
    
    protected void goToB(){
        try {
            port.getOutputStream().write("NEXT\n".getBytes());
            motorRunning = false;
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
    
    /** Determine output bucket,
        move bead toward it,
        take new bead and return under the camera */
    protected void doSort(boolean go){
        getLblColor().setBackground(activeColor);
        float[] hsb = new float[3];
        Color.RGBtoHSB(activeColor.getRed(), activeColor.getGreen(), activeColor.getBlue(), hsb);
        float[] hsbTarget = new float[3];
        Color.RGBtoHSB(targetColor.getRed(), targetColor.getGreen(), targetColor.getBlue(), hsbTarget);
        double diff = UtilAngle.dist(hsb[0]*2*Math.PI,hsbTarget[0]*2*Math.PI);
        System.out.println("now "+hsb[0]+" target "+hsbTarget[0]+" diff "+diff);

        // hard-coded hue threshold here (PI/12)
        if(diff < Math.PI/12.0 && ! activeColor.equals(Color.black)){
            System.out.println("Color match -> A");
            if(go) goToA();
        }else{
            System.out.println("Color no match -> B");
            if(go) goToB();
        }
    }

    
    protected JCheckBox getChckbxAutoSort() {
        return chckbxAutoSort;
    }
    public ImagePanel getImgPanel2() {
        return imgPanel2;
    }
}