From ae8432ffe5cea8421b04068d0fe62d8e15175505 Mon Sep 17 00:00:00 2001 From: Christopher Baines Date: Wed, 14 Sep 2011 10:42:54 +0100 Subject: New package management, needs more work, not enough is public. Split programs from the gui, these are included as examples. --- PunchingBag/G4.wav | Bin 0 -> 44144 bytes PunchingBag/src/AccelListener.java | 7 - PunchingBag/src/Arduino.java | 242 ------- PunchingBag/src/ButtonArduino.java | 9 - PunchingBag/src/ButtonListener.java | 7 - PunchingBag/src/Contact.java | 19 - PunchingBag/src/Font.java | 374 ---------- PunchingBag/src/LEDListener.java | 7 - PunchingBag/src/PunchingBag.java | 784 -------------------- PunchingBag/src/PunchingBagGUI.java | 643 ----------------- PunchingBag/src/SerialReadListener.java | 7 - PunchingBag/src/SerialWriteListener.java | 9 - .../src/uk/ac/open/punchingbag/AccelListener.java | 8 + .../src/uk/ac/open/punchingbag/Arduino.java | 243 +++++++ .../src/uk/ac/open/punchingbag/ButtonListener.java | 10 + .../src/uk/ac/open/punchingbag/Contact.java | 23 + PunchingBag/src/uk/ac/open/punchingbag/Font.java | 375 ++++++++++ .../src/uk/ac/open/punchingbag/LEDListener.java | 8 + .../src/uk/ac/open/punchingbag/PunchingBag.java | 786 +++++++++++++++++++++ .../src/uk/ac/open/punchingbag/PunchingBagGUI.java | 650 +++++++++++++++++ .../uk/ac/open/punchingbag/SerialReadListener.java | 8 + .../ac/open/punchingbag/SerialWriteListener.java | 10 + .../uk/ac/open/punchingbag/examples/Giggle.java | 74 ++ .../open/punchingbag/examples/SimpleKeyboard.java | 87 +++ 24 files changed, 2282 insertions(+), 2108 deletions(-) create mode 100644 PunchingBag/G4.wav delete mode 100644 PunchingBag/src/AccelListener.java delete mode 100644 PunchingBag/src/Arduino.java delete mode 100644 PunchingBag/src/ButtonArduino.java delete mode 100644 PunchingBag/src/ButtonListener.java delete mode 100644 PunchingBag/src/Contact.java delete mode 100644 PunchingBag/src/Font.java delete mode 100644 PunchingBag/src/LEDListener.java delete mode 100644 PunchingBag/src/PunchingBag.java delete mode 100644 PunchingBag/src/PunchingBagGUI.java delete mode 100644 PunchingBag/src/SerialReadListener.java delete mode 100644 PunchingBag/src/SerialWriteListener.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/AccelListener.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/Arduino.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/ButtonListener.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/Contact.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/Font.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/LEDListener.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/PunchingBag.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/PunchingBagGUI.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/SerialReadListener.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/SerialWriteListener.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/examples/Giggle.java create mode 100644 PunchingBag/src/uk/ac/open/punchingbag/examples/SimpleKeyboard.java diff --git a/PunchingBag/G4.wav b/PunchingBag/G4.wav new file mode 100644 index 0000000..fb50cc5 Binary files /dev/null and b/PunchingBag/G4.wav differ diff --git a/PunchingBag/src/AccelListener.java b/PunchingBag/src/AccelListener.java deleted file mode 100644 index a3ad465..0000000 --- a/PunchingBag/src/AccelListener.java +++ /dev/null @@ -1,7 +0,0 @@ -import java.util.EventListener; - -interface AccelListener extends EventListener { - - void AccelChanged(); - -} diff --git a/PunchingBag/src/Arduino.java b/PunchingBag/src/Arduino.java deleted file mode 100644 index 4fa7cfa..0000000 --- a/PunchingBag/src/Arduino.java +++ /dev/null @@ -1,242 +0,0 @@ -import java.util.Enumeration; -import java.util.HashSet; - -import gnu.io.CommPort; -import gnu.io.CommPortIdentifier; -import gnu.io.SerialPort; - -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; - -import javax.swing.event.EventListenerList; - -import gnu.io.*; - -public class Arduino implements Runnable { - - InputStream in; - OutputStream out; - - private EventListenerList readListenerList = new EventListenerList(); - private EventListenerList writeListenerList = new EventListenerList(); - - public void addSerialWriteListener(SerialWriteListener l) { - writeListenerList.add(SerialWriteListener.class, l); - } - - public void addSerialReadListener(SerialReadListener l) { - readListenerList.add(SerialReadListener.class, l); - } - - static void listPorts() - { - System.out.println("Listing Comm ports:"); - java.util.Enumeration portEnum = CommPortIdentifier.getPortIdentifiers(); - while ( portEnum.hasMoreElements() ) - { - CommPortIdentifier portIdentifier = portEnum.nextElement(); - System.out.println(portIdentifier.getName() + " - " + getPortTypeName(portIdentifier.getPortType()) ); - } - } - - static String getPortTypeName ( int portType ) - { - switch ( portType ) - { - case CommPortIdentifier.PORT_I2C: - return "I2C"; - case CommPortIdentifier.PORT_PARALLEL: - return "Parallel"; - case CommPortIdentifier.PORT_RAW: - return "Raw"; - case CommPortIdentifier.PORT_RS485: - return "RS485"; - case CommPortIdentifier.PORT_SERIAL: - return "Serial"; - default: - return "unknown type"; - } - } - - public String getID() throws IOException { - byte[] idBytes = {0x49, 0x44}; - this.write(idBytes); - try { - Thread.sleep(100); - } catch (InterruptedException e) { - e.printStackTrace(); - } - int id; - while ((id = this.read()) == -1) {} - if (id == 66) { - return "B"; - } else if (id == 76) { - return "L"; - } else { - return "ERROR " + id; - } - } - - /** - * @return A HashSet containing the CommPortIdentifier for all serial ports that are not currently being used. - */ - public static HashSet getAvailableSerialPorts() { - HashSet h = new HashSet(); - Enumeration thePorts = CommPortIdentifier.getPortIdentifiers(); - while (thePorts.hasMoreElements()) { - CommPortIdentifier com = (CommPortIdentifier) thePorts.nextElement(); - switch (com.getPortType()) { - case CommPortIdentifier.PORT_SERIAL: - try { - CommPort thePort = com.open("CommUtil", 50); - thePort.close(); - h.add(com); - //System.out.println("Found a port: " + com.getPortType()); - } catch (PortInUseException e) { - System.out.println("Port, " + com.getName() + ", is in use."); - } catch (Exception e) { - System.err.println("Failed to open port " + com.getName()); - e.printStackTrace(); - } - } - } - return h; - } - - void connect ( String portName ) throws Exception - { - CommPortIdentifier portIdentifier = CommPortIdentifier.getPortIdentifier(portName); - if ( portIdentifier.isCurrentlyOwned() ) - { - System.out.println("Error: Port is currently in use"); - } - else - { - CommPort commPort = portIdentifier.open(this.getClass().getName(),2000); - - if ( commPort instanceof SerialPort ) - { - SerialPort serialPort = (SerialPort) commPort; - serialPort.setSerialPortParams(9600,SerialPort.DATABITS_8,SerialPort.STOPBITS_1,SerialPort.PARITY_NONE); - - in = serialPort.getInputStream(); - out = serialPort.getOutputStream(); - - //(new Thread(this)).start(); - } - else - { - System.out.println("Error: Only serial ports are handled by this example."); - } - } - } - - /** */ - public class SerialReader implements Runnable - { - InputStream in; - - public SerialReader ( InputStream in ) - { - this.in = in; - } - - public void run () - { - byte[] buffer = new byte[1024]; - int len = -1; - try - { - while ( ( len = this.in.read(buffer)) > -1 ) - { - System.out.print(new String(buffer,0,len)); - input(new String(buffer,0,len)); - } - } - catch ( IOException e ) - { - e.printStackTrace(); - } - } - } - - public static void input(String string) { - - } - - /** */ - public class SerialWriter implements Runnable - { - OutputStream out; - - public SerialWriter ( OutputStream out ) - { - this.out = out; - } - - public void run () - { - try - { - int c = 0; - while ( ( c = System.in.read()) > -1 ) - { - this.out.write(c); - } - } - catch ( IOException e ) - { - e.printStackTrace(); - } - } - } - - public void run() { - byte[] buffer = new byte[1024]; - int len = -1; - try - { - while ( ( len = this.in.read(buffer)) > -1 ) - { - System.out.print(new String(buffer,0,len)); - //input(new String(buffer,0,len)); - } - } - catch ( IOException e ) - { - e.printStackTrace(); - } - - } - - - public void write(byte[] bytes) throws IOException { - out.write(bytes); - SerialWriteListener[] sListeners = writeListenerList - .getListeners(SerialWriteListener.class); - for (int i = 0; i < writeListenerList.getListenerCount(); i++) { - sListeners[i].serialWriteEvent(bytes); - } - } - - public void write(byte b) throws IOException { - out.write(b); - SerialWriteListener[] sListeners = writeListenerList - .getListeners(SerialWriteListener.class); - for (int i = 0; i < writeListenerList.getListenerCount(); i++) { - sListeners[i].serialWriteEvent(b); - } - } - - public int read() throws IOException { - int read = in.read(); - SerialReadListener[] sListeners = readListenerList - .getListeners(SerialReadListener.class); - for (int i = 0; i < readListenerList.getListenerCount(); i++) { - sListeners[i].serialReadEvent(read); - } - return read; - } - -} diff --git a/PunchingBag/src/ButtonArduino.java b/PunchingBag/src/ButtonArduino.java deleted file mode 100644 index b56a9ed..0000000 --- a/PunchingBag/src/ButtonArduino.java +++ /dev/null @@ -1,9 +0,0 @@ - -public class ButtonArduino extends Arduino { - - void setButtons(boolean[][] buttons) { - - - } - -} diff --git a/PunchingBag/src/ButtonListener.java b/PunchingBag/src/ButtonListener.java deleted file mode 100644 index 3338a08..0000000 --- a/PunchingBag/src/ButtonListener.java +++ /dev/null @@ -1,7 +0,0 @@ -import java.util.EventListener; - -interface ButtonListener extends EventListener { - - void buttonPressed(int x, int y); - -} diff --git a/PunchingBag/src/Contact.java b/PunchingBag/src/Contact.java deleted file mode 100644 index 8e8970b..0000000 --- a/PunchingBag/src/Contact.java +++ /dev/null @@ -1,19 +0,0 @@ - - - class Contact { - // Height of bag is - - final long time; // Time of the contact with the bag (in millis) - final int x; - final int y; - final int strength; // 0 - 100 - - Contact(long time, int x, int y, int strength) { - this.time = time; - this.x = x; - this.y = y; - this.strength = strength; - } - - - } \ No newline at end of file diff --git a/PunchingBag/src/Font.java b/PunchingBag/src/Font.java deleted file mode 100644 index a8996bf..0000000 --- a/PunchingBag/src/Font.java +++ /dev/null @@ -1,374 +0,0 @@ - -public class Font { - char font[] = { - // -------- Space - 0b00000000, - 0b00000000, - 0b00000000, - 0b00000000, - // -------- A - 0b01111110, - 0b10010000, - 0b10010000, - 0b01111110, - // -------- B - 0b01101100, - 0b10010010, - 0b10010010, - 0b11111110, - // -------- C - 0b10000010, - 0b10000010, - 0b01111100, - // -------- D - 0b00111000, - 0b01000100, - 0b10000010, - 0b11111110, - // -------- E - 0b10000010, - 0b10010010, - 0b11111110, - // -------- F - 0b10000000, - 0b10010000, - 0b11111110, - // -------- G - 0b01011100, - 0b10010010, - 0b10000010, - 0b01111100, - // -------- H - 0b11111110, - 0b00010000, - 0b00010000, - 0b11111110, - // -------- I - 0b10000010, - 0b11111110, - 0b10000010, - // -------- J - 0b11111100, - 0b00000010, - 0b00001100, - // -------- K - 0b10000110, - 0b01001000, - 0b00110000, - 0b11111110, - // -------- L - 0b00000010, - 0b00000010, - 0b11111110, - // -------- M - 0b11111110, - 0b01100000, - 0b00111100, - 0b01100000, - 0b11111110, - // -------- N - 0b11111110, - 0b00011000, - 0b01100000, - 0b11111110, - // -------- O - 0b01111100, - 0b10000010, - 0b10000010, - 0b01111100, - // -------- P - 0b01100000, - 0b10010000, - 0b10010000, - 0b11111110, - // -------- Q - 0b01111010, - 0b10000100, - 0b10001010, - 0b01111100, - // -------- R - 0b01100110, - 0b10011000, - 0b10010000, - 0b11111110, - // -------- S - 0b10001100, - 0b10010010, - 0b01100010, - // -------- T - 0b10000000, - 0b11111110, - 0b10000000, - // -------- U - 0b11111100, - 0b00000010, - 0b00000010, - 0b11111100, - // -------- V - 0b11000000, - 0b00111000, - 0b00000110, - 0b00111000, - 0b11000000, - // -------- W - 0b11111110, - 0b00001100, - 0b00111000, - 0b00001100, - 0b11111110, - // -------- X - 0b11000110, - 0b00111000, - 0b00111000, - 0b11000110, - // -------- Y - 0b11100000, - 0b00011110, - 0b11100000, - // -------- Z - 0b11000010, - 0b10110010, - 0b10001110, - // -------- Unknown character - 0b00111000, - 0b00111000, - 0b00111000, - // -------- 0 - 0b01111100, - 0b10100010, - 0b10010010, - 0b01111100, - // -------- 1 - 0b11111110, - 0b01000000, - // -------- 2 - 0b01100010, - 0b10010010, - 0b10001110, - // -------- 3 - 0b01101100, - 0b10010010, - 0b10000010, - // -------- 4 - 0b11111110, - 0b00010000, - 0b11110000, - // -------- 5 - 0b10001100, - 0b10010010, - 0b11110010, - // -------- 6 - 0b01001100, - 0b10010010, - 0b10010010, - 0b01111100, - // -------- 7 - 0b11100000, - 0b10011110, - 0b10000000, - // -------- 8 - 0b01101100, - 0b10010010, - 0b10010010, - 0b01101100, - // -------- 9 - 0b01111100, - 0b10010010, - 0b10010010, - 0b01100100, - // -------- : - 0b00100100, - // -------- ; - 0b00100110, - 0b00000001, - // -------- ! - 0b01100000, - 0b11111010, - 0b01100000, - // -------- Heart - 0b01111000, - 0b11111100, - 0b11111110, - 0b01111111, - 0b11111110, - 0b11111100, - 0b01111000, - // -------- < - 0b01000100, - 0b00101000, - 0b00010000, - // -------- = - 0b00101000, - 0b00101000, - 0b00101000, - 0b00101000, - // -------- > - 0b00010000, - 0b00101000, - 0b01000100, - // -------- ? - 0b01100000, - 0b10011010, - 0b10000000, - // -------- @ - 0b01111100, - 0b10000010, - 0b10111010, - 0b10100010, - 0b01011100, - // -------- ( - 0b10000010, - 0b01111100, - // -------- ) - 0b01111100, - 0b10000010, - // -------- * - 0b00101000, - 0b00010000, - 0b00101000, - // -------- + - 0b00010000, - 0b00010000, - 0b01111100, - 0b00010000, - 0b00010000, - // -------- , - 0b00000110, - 0b00000001, - // -------- - - 0b00010000, - 0b00010000, - 0b00010000, - 0b00010000, - // -------- . - 0b00000010, - // -------- / - 0b11000000, - 0b00111000, - 0b00000110, - // -------- a - 0b00111110, - 0b00100010, - 0b00100010, - 0b00011100, - // -------- b - 0b00011100, - 0b00100010, - 0b00100010, - 0b11111110, - // -------- c - 0b00100010, - 0b00100010, - 0b00011100, - // -------- d - 0b11111110, - 0b00100010, - 0b00100010, - 0b00011100, - // -------- e - 0b00011000, - 0b00101010, - 0b00101010, - 0b00011100, - // -------- f - 0b10010000, - 0b01111110, - 0b00010000, - // -------- g - 0b00111110, - 0b00100101, - 0b00100101, - 0b00011000, - // -------- h - 0b00011110, - 0b00100000, - 0b00100000, - 0b11111110, - // -------- i - 0b00000010, - 0b01011110, - 0b00010010, - // -------- j - 0b01011110, - 0b00000001, - 0b00000001, - // -------- k - 0b00100010, - 0b00010100, - 0b00001000, - 0b11111110, - // -------- l - 0b00000010, - 0b11111100, - // -------- m - 0b00011110, - 0b00100000, - 0b00111110, - 0b00100000, - 0b00111110, - // -------- n - 0b00011110, - 0b00100000, - 0b00100000, - 0b00111110, - // -------- o - 0b00011100, - 0b00100010, - 0b00100010, - 0b00011100, - // -------- p - 0b00011100, - 0b00100010, - 0b00100010, - 0b00111111, - // -------- q - 0b00111111, - 0b00100010, - 0b00100010, - 0b00011100, - // -------- r - 0b00010000, - 0b00100000, - 0b00111110, - // -------- s - 0b00100100, - 0b00101010, - 0b00101010, - 0b00010010, - // -------- t - 0b00100010, - 0b11111100, - 0b00100000, - // -------- u - 0b00111110, - 0b00000010, - 0b00000010, - 0b00111100, - // -------- v - 0b00111000, - 0b00000110, - 0b00111000, - // -------- w - 0b00111110, - 0b00000010, - 0b00011110, - 0b00000010, - 0b00111100, - // -------- x - 0b00110110, - 0b00001000, - 0b00110110, - // -------- y - 0b00111110, - 0b00000101, - 0b00000101, - 0b00111001, - // -------- z - 0b00110010, - 0b00101010, - 0b00100110, - 0b00100010, - 0b11000001 - }; - -} diff --git a/PunchingBag/src/LEDListener.java b/PunchingBag/src/LEDListener.java deleted file mode 100644 index 3031f58..0000000 --- a/PunchingBag/src/LEDListener.java +++ /dev/null @@ -1,7 +0,0 @@ -import java.util.EventListener; - -interface LEDListener extends EventListener { - - void LEDchanged(); - -} diff --git a/PunchingBag/src/PunchingBag.java b/PunchingBag/src/PunchingBag.java deleted file mode 100644 index 941e4d7..0000000 --- a/PunchingBag/src/PunchingBag.java +++ /dev/null @@ -1,784 +0,0 @@ -import gnu.io.CommPortIdentifier; - -import javax.swing.event.EventListenerList; - -import java.awt.Rectangle; -import java.awt.geom.Area; - -import java.io.IOException; -import java.math.BigInteger; - -import java.util.ArrayList; -import java.util.Arrays; -import java.util.HashSet; -import java.util.Iterator; - -// TODO: Loads of threads in this class, make sure everything is thread safe. - -public class PunchingBag implements Runnable { - boolean ledsChanged = false; - final public int ledHeight = 20; - final public int ledWidth = 9; - private byte[] rawLeds = new byte[6 * 8]; - private Colour[][] leds = new Colour[ledWidth][ledHeight]; // NEVER ACCESS - // DIRECTLY (Use - // SetLedInternal) - private byte[] ledGridIntensities = new byte[6]; - final public int buttonHeight = 19; - final public int buttonWidth = 8; - private boolean[][] buttons = new boolean[buttonWidth][buttonHeight]; - boolean buttonsChanged = false; - - int bottomAccelX = 0; - int bottomAccelY = 0; - int topAccelX = 0; - int topAccelY = 0; - boolean acccelChanged = false; - - private long lastRefresh = 0; - - private ArrayList runningEffects = new ArrayList(); - - Arduino buttonArduino = new Arduino(); - Arduino ledArduino = new Arduino(); - - public enum Colour { - None, Red, Yellow, Green - }; - - public enum Direction { - Right, Left, Up, Down - }; - - // Is there a better class for this? One that it is not a swing class. - private EventListenerList buttonListenerList = new EventListenerList(); - private EventListenerList ledListenerList = new EventListenerList(); - private EventListenerList accelListenerList = new EventListenerList(); - - public PunchingBag() { - Thread bagControlThread = new Thread(this); - bagControlThread.setPriority(Thread.MAX_PRIORITY); - bagControlThread.start(); - } - - /** - * Adds an ActionListener to the button. - * - * @param l - * the ActionListener to be added - */ - public void addButtonListener(ButtonListener l) { - buttonListenerList.add(ButtonListener.class, l); - } - - public void addLEDChangeListener(LEDListener l) { - ledListenerList.add(LEDListener.class, l); - } - - public void addAccelChangeListener(AccelListener l) { - accelListenerList.add(AccelListener.class, l); - } - - public Colour getLED(int x, int y) { - return leds[x][y]; - } - - private boolean setLEDInternal(int x, int y, Colour colour) { - if (x >= 0 && x < ledWidth && y >= 0 && y < ledHeight) { - if (leds[x][y] != colour) { - leds[x][y] = colour; - ledsChanged = true; - - } - return true; - } else { - return false; - } - } - - public void setLED(int x, int y, Colour colour) { - runningEffects.add(new Point(x, y, colour)); - } - - void circleExpand(int x, int y, int intensity) { - runningEffects.add(new CircleExpand(x, y, 100)); - } - - void squareExpand(int x, int y, int intensity, Colour colour) { - runningEffects.add(new SquareExpand(x, y, intensity, colour)); - } - - void fillRect(int x, int y, int width, int height, Colour colour, long time) { - runningEffects.add(new FillRect(x, y, width, height, colour, time)); - } - - void rect(int x, int y, int width, int height, Colour colour) { - runningEffects.add(new Rect(x, y, width, height, colour)); - } - - void noise(Rectangle rect, long time) { - runningEffects.add(new Noise(rect, System.currentTimeMillis() + time)); - } - - abstract class Effect { - long lastRefresh = 0; - boolean stop = false; - - // int refreshRate = 60; // Times per second to refresh - - public void stop() { - stop = true; - } - - abstract public void draw(); - } - - class Point extends Effect { - final int x; - final int y; - final Colour colour; - - public Point(int x, int y, Colour colour) { - this.x = x; - this.y = y; - this.colour = colour; - } - - public void draw() { - setLEDInternal(x, y, colour); - } - } - - class FillRect extends Effect { - final int x; - final int y; - final int width; - final int height; - final Colour colour; - final long time; - - public FillRect(int x, int y, int width, int height, Colour colour, long time) { - this.x = x; - this.y = y; - this.width = width; - this.height = height; - this.colour = colour; - this.time = System.currentTimeMillis() + time; - } - - public void draw() { - fillRectInternal(x, y, width, height, colour); - if (System.currentTimeMillis() >= time) { - stop(); - } - } - } - - class Rect extends Effect { - final int x; - final int y; - final int width; - final int height; - final Colour colour; - - public Rect(int x, int y, int width, int height, Colour colour) { - this.x = x; - this.y = y; - this.width = width; - this.height = height; - this.colour = colour; - } - - public void draw() { - drawRectInternal(x, y, width, height, colour); - } - } - - class Text extends Effect { - final String string; - final Area area; - final Direction direction; - final int speed; - - public Text(String string, Area area, Direction direction, int speed) { - this.string = string; - this.area = area; - this.direction = direction; - this.speed = speed; - - } - - public void draw() { - byte[] stringBytes = string.getBytes(); - - } - } - - class CircleExpand extends Effect { - final double x; - final double y; - int intensity; - boolean drawnSomething = true; - - double currentRadius = 0.5; - - public CircleExpand(int x, int y, int intensity) { - this.x = x + 0.5; - this.y = y + 0.5; - this.intensity = intensity; - } - - public void draw() { - Colour colour; - - if (intensity >= 10) { - colour = Colour.Red; - } else if (intensity >= 5) { - colour = Colour.Yellow; - } else { - colour = Colour.Green; - } - - intensity -= 5; - - currentRadius += 0.4 + (currentRadius / 20); - // currentRadius += 0.01; - // longhand: currentRadius = currentRadius + 0.1 + (currentRadius / - // 10); - - if (!drawCircle(x, y, currentRadius, colour)) - stop = true; - } - - } - - class SquareExpand extends Effect { - final int x; - final int y; - final Colour colour; - int intensity; - boolean drawnSomething = true; - - int heightWidth = 2; - - public SquareExpand(int x, int y, int intensity, Colour colour) { - this.x = x; - this.y = y; - this.intensity = intensity; - this.colour = colour; - - } - - public void draw() { - heightWidth += 0.1 + 0.1 + (heightWidth / 20); - if (!drawRectCenter(x, y, heightWidth, heightWidth, colour)) - stop = true; - - } - - } - - class Noise extends Effect { - final Rectangle area; - final long endTime; - - public Noise(Rectangle area, long endTime) { - this.area = area; - this.endTime = endTime; - } - - @Override - public void draw() { - if (endTime >= System.currentTimeMillis()) { - for (int y = area.y; y < (area.y + area.height); y++) { - for (int x = area.x; x < (area.x + area.width); x++) { - double random = Math.random(); - if (random < 0.25) { - setLEDInternal(x, y, Colour.Red); - } else if (random < 0.5) { - setLEDInternal(x, y, Colour.Yellow); - } else if (random < 0.75) { - setLEDInternal(x, y, Colour.Green); - } else { - setLEDInternal(x, y, Colour.None); - } - } - } - } else { - stop(); - } - } - } - - public boolean drawRectCenter(int x, int y, int height, int width, - Colour colour) { - if (height < 0) { - height = 0; - } - if (width < 0) { - width = 0; - } - if (height == 0 && width == 0) { - return setLEDInternal(x, y, colour); - } - - boolean doneSomething = false; - int widthEx = 0; - int heightEx = 0; - - do { - if (setLEDInternal((x - (height / 2)) + widthEx, y - (height / 2), - colour)) { - doneSomething = true; - } - if (setLEDInternal(x - (height / 2), (y - (height / 2)) + heightEx, - colour)) { - doneSomething = true; - } - if (setLEDInternal((x - (height / 2)) + widthEx, y + (height / 2), - colour)) { - doneSomething = true; - } - if (setLEDInternal(x + (height / 2), (y - (height / 2)) + heightEx, - colour)) { - doneSomething = true; - } - if (heightEx < height) { - heightEx++; - } - if (widthEx < width) { - widthEx++; - } - - } while (height >= 0 && width >= 0); - - return doneSomething; - } - - public boolean drawRectInternal(int x, int y, int width, int height, - Colour colour) { - if (height < 0) { - height = 0; - } - if (width < 0) { - width = 0; - } - if (height == 0 && width == 0) { - return setLEDInternal(x, y, colour); - } - - boolean doneSomething = false; - int heightEx = 0; - int widthEx = 0; - boolean finished = true; - do { - if (setLEDInternal(x + widthEx, y, colour)) { - doneSomething = true; - } - if (setLEDInternal(x, y + heightEx, colour)) { - doneSomething = true; - } - if (setLEDInternal(x + widthEx, y + height, colour)) { - doneSomething = true; - } - if (setLEDInternal(x + width, y + heightEx, colour)) { - doneSomething = true; - } - if (heightEx < height) { - finished = false; - heightEx++; - } - if (widthEx < width) { - finished = false; - widthEx++; - } - } while (!finished); - - return doneSomething; - } - - public boolean drawEllipse(int x, int y, int radx, int rady, Colour colour) { - if (radx == 0 && rady == 0) { - return setLEDInternal(x, y, colour); - } - - boolean doneSomething = false; - - int dx = 0, dy = rady; /* first quadrant from top left to bottom right */ - int a2 = radx * radx, b2 = rady * rady; - int err = b2 - (2 * rady - 1) * a2, e2; /* error value in the first step */ - - do { - if (setLEDInternal(x + dx, y + dy, colour)) {/* I. Quadrant */ - doneSomething = true; - } - if (setLEDInternal(x - dx, y + dy, colour)) {/* II. Quadrant */ - doneSomething = true; - } - if (setLEDInternal(x - dx, y - dy, colour)) {/* III. Quadrant */ - doneSomething = true; - } - if (setLEDInternal(x + dx, y - dy, colour)) {/* IV. Quadrant */ - doneSomething = true; - } - - e2 = 2 * err; - if (e2 < (2 * dx + 1) * b2) { - dx++; - err += (2 * dx + 1) * b2; - } - if (e2 > -(2 * dy - 1) * a2) { - dy--; - err -= (2 * dy - 1) * a2; - } - } while (dy >= 0); - - while (dx++ < radx) { /* correction for flat ellipses (b=1) */ - if (setLEDInternal(x + dx, y, colour)) { - doneSomething = true; - } - if (setLEDInternal(x - dx, y, colour)) { - doneSomething = true; - } - } - return doneSomething; - } - - public boolean drawCircle(double x, double y, double radius, Colour colour) { - boolean drawnSomething = false; - int px; - int py; - for (double i = 0; i < 360; i++) { - px = (int) Math.round(x + (radius * Math.cos(i))); - py = (int) Math.round(y + (radius * Math.sin(i))); - - if (x >= 0 && x <= 8 && y >= 0 && y <= 19) { - if (setLEDInternal(px, py, colour)) { - drawnSomething = true; - } - } - } - return drawnSomething; - } - - public boolean fillRectInternal(int x, int y, int height, int width, - Colour colour) { - boolean doneSomething = false; - for (int px = x; px < (x + height); px++) { - - for (int py = y; py < (y + width); py++) { - if (setLEDInternal(px, py, colour)) { - doneSomething = true; - } - } - } - - return doneSomething; - - } - - private void calculateRawLeds() { - // First clear everything - Arrays.fill(rawLeds, (byte) 0); - // First loop through the 5 easy arrays - for (int grid = 0; grid < 5; grid++) { - for (int x = 0; x < 8; x++) { - for (int y = 0; y < 8; y++) { - if ((y % 2) == 0) { - if (leds[1 + x][(grid * 4) + (y / 2)] == Colour.Green - || leds[1 + x][(grid * 4) + (y / 2)] == Colour.Yellow) { - rawLeds[(grid * 8) + x] = (byte) (rawLeds[(grid * 8) - + x] | (1 << (7 - y))); - } - } else { - if (leds[1 + x][(grid * 4) + (y / 2)] == Colour.Red - || leds[1 + x][(grid * 4) + (y / 2)] == Colour.Yellow) { - rawLeds[(grid * 8) + x] = (byte) (rawLeds[(grid * 8) - + x] | (1 << (7 - y))); - } - } - } - } - } - - /* - * for (int y = 0; y <= 18; y++) { for (int x = 0; x <= 6; x++) { if ((y - * % 2) == 0) { if (leds[x][y] == Colour.Green || leds[x][y] == - * Colour.Yellow) { rawLeds[(int) Math.floor(y / 4)] = (byte) - * (rawLeds[(int) Math .floor(y / 4)] | (1 << (7 - x))); } } else { if - * (leds[x][y] == Colour.Red || leds[x][y] == Colour.Yellow) { - * rawLeds[(int) Math.floor(y / 4)] = (byte) (rawLeds[(int) Math - * .floor(y / 4)] | (1 << (7 - x))); } } } } - */ - /* - * int x = 7; // TODO: Complete and test, or rethink the following? for - * (int startY = 0; startY <= 4; startY++) { for (int y = 0; y <= 3; - * y++) { if (leds[x][startY + (y * 4)] == Colour.Red || leds[x][startY - * + (y * 4)] == Colour.Yellow) { rawLeds[(5 * 8) + startY] = (byte) - * (rawLeds[(int) Math .floor(y / 4)] | (1 << (7 - x))); } if - * (leds[x][y] == Colour.Green || leds[x][y] == Colour.Yellow) { - * rawLeds[(int) Math.floor(y / 4)] = (byte) (rawLeds[(int) Math - * .floor(y / 4)] | (1 << (7 - x))); } } } - */ - } - - /* Clears the led grid */ - private void clearLEDGrid() { - for (int x = 0; x < ledWidth; x++) { - for (int y = 0; y < ledHeight; y++) { - leds[x][y] = Colour.None; - } - } - } - - private void clearButtonGrid() { - for (int x = 0; x < buttonWidth; x++) { - for (int y = 0; y < buttonHeight; y++) { - buttons[x][y] = false; - } - } - } - - private void clearEffects() { - for (Iterator iter = runningEffects.iterator(); iter.hasNext();) { - ((Effect) iter.next()).stop(); - } - } - - public void clearLEDs() { - clearLEDGrid(); - clearEffects(); - } - - public void setLEDGridIntensity(byte grid, byte intensity) { - ledGridIntensities[grid] = intensity; - } - - public void setLEDIntensities(byte intensity) { - Arrays.fill(ledGridIntensities, intensity); - } - - public void buttonPressed(int x, int y) { - buttons[x][y] = true; - buttonsChanged = true; - } - - public boolean connectToArduinos() { - try { - ledArduino.connect("COM6"); - buttonArduino.connect("COM7"); - } catch (Exception e1) { - // TODO Auto-generated catch block - e1.printStackTrace(); - } - HashSet serialPorts = Arduino - .getAvailableSerialPorts(); - for (Iterator iter = serialPorts.iterator(); iter.hasNext();) { - CommPortIdentifier comPort = (CommPortIdentifier) iter.next(); - // HACK FOR WINDOWS TO IDENIFY PORTS LIKELY TO CONTAIN ARDUINO - // (COM10 for instance). TODO: FIX - if (comPort.getName().length() == 5) { - System.out.println(comPort.getName()); - } - try { - - System.out.println(comPort.getName()); - } catch (Exception e) { - e.printStackTrace(); - } - } - return true; - } - - private void readAccelData(String data) { - String[] nums = data.split(" "); - for (int x = 1; x < 5; x++) { - // Regex expression to strip newline at end (normally just 4th) - int num = Integer.valueOf(nums[x].replaceAll("[^0-9]", "")); - if (x == 1 && num != topAccelX) { - topAccelX = num; - acccelChanged = true; - } else if (x == 2 && num != topAccelY) { - topAccelY = num; - acccelChanged = true; - } else if (x == 3 && num != bottomAccelX) { - bottomAccelX = num; - acccelChanged = true; - } else if (x == 4 && num != bottomAccelY) { - bottomAccelY = num; - acccelChanged = true; - } - } - } - - private void readButtonData(String data) { - if (data.replaceAll("[^0-9]", "").length() > 0) { - System.out.print(data); - int num = Integer.valueOf(data.replaceAll("[^0-9]", "")); - int x = ((num-1) % 8); - int y = (num-1) / 8; - System.out.println("X: " + x + " Y: " + y); - if (!(x < 0)) { - buttons[x][y] = true; - buttonsChanged = true; - } - } - } - - private void printByte(byte b) { - // System.out.println("Byte: " + b); - String str; - for (int j = 0; j < 8; j++) { - byte val = (byte) (b & (1 << (7 - j))); - // System.out.println("Val: " + val + " " + (1 << (7-j))); - if (val > 0) { - str = "1"; - } else { - str = "0"; - } - System.out.print(str); - } - } - - private void printlnByte(byte b) { - printByte(b); - System.out.println(""); - } - - public void run() { - long timeToSleep = 10; - - while (true) { - //System.out.println("Time since last refresh: " - // + (System.currentTimeMillis() - lastRefresh)); - - if ((System.currentTimeMillis() - lastRefresh) > (1000 / 60)) { - if (timeToSleep > 0) { - timeToSleep--; - } - } else { - timeToSleep++; - } - - //System.out.println("Sleeping: " + timeToSleep); - lastRefresh = System.currentTimeMillis(); - - // System.out.println("R"); - synchronized (leds) { - clearLEDGrid(); - // clearButtonGrid(); - long beginTimeForEffects = System.currentTimeMillis(); - synchronized (runningEffects) { // Should prevent - // ConcurrentModificationException's - // (havent managed to produce one - // though - for (Iterator iter = runningEffects.iterator(); iter - .hasNext();) { - Effect ef = (Effect) iter.next(); - if (ef.stop) { - iter.remove(); - } else {// if ((ef.lastRefresh + (1000 / - // ef.refreshRate)) <= - // Systems.currentTimeMillis()) { - ef.draw(); - ef.lastRefresh = System.currentTimeMillis(); - } - } - } - //System.out.println("Effects: " - // + (System.currentTimeMillis() - beginTimeForEffects)); - } - - long beginTimeButtonIn = System.currentTimeMillis(); - if (buttonArduino.in != null) { - try { - int read; - while ((read = buttonArduino.read()) != -1) { - // System.out.print((char) read); - if ((char) read == 'A') { - String str = ""; - // StringBuilder sb = new StringBuilder(20); - while ((read = buttonArduino.read()) != '\n') { - str = str + String.valueOf((char) read); - // sb.append((char) read); - } - // System.out.println(""); - // readAccelData(str); - // String[] nums = sbString.trim().split(" "); - // System.out.println(nums); - // for (int x=0; x<4; x++) { - // System.out.println(nums[x]); - // } - - } else if ((char) read == 'B') { - String str = ""; - // StringBuilder sb = new StringBuilder(20); - while ((read = buttonArduino.read()) != '\n') { - str = str + String.valueOf((char) read); - // sb.append((char) read); - } - // System.out.println(""); - readButtonData(str); - - } else { - // System.out.println((char) read); - } - // System.out.print("|"); - } - } catch (IOException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } - } - //System.out.println("Button: " - // + (System.currentTimeMillis() - beginTimeButtonIn)); - - calculateRawLeds(); - String str; - for (int i = 0; i < (6 * 8); i++) { - // printByte(rawLeds[i]); - } - // System.out.println(""); - - // Arrays.fill(rawLeds, (byte) -42); - if (ledArduino.out != null) { - // calculateRawLeds(); - try { - ledArduino.write(((byte) 108)); - ledArduino.write(rawLeds); - } catch (IOException e1) { - e1.printStackTrace(); - } - } - - if (ledsChanged) { - LEDListener[] LEDListeners = ledListenerList - .getListeners(LEDListener.class); - for (int i = 0; i < ledListenerList.getListenerCount(); i++) { - LEDListeners[i].LEDchanged(); - } - } - - if (buttonsChanged) { - ButtonListener[] buttonListeners = buttonListenerList - .getListeners(ButtonListener.class); - for (int i = 0; i < buttonListenerList.getListenerCount(); i++) { - for (int x = 0; x < buttonWidth; x++) { - for (int y = 0; y < buttonHeight; y++) { - if (buttons[x][y]) - buttonListeners[i].buttonPressed(x, y); - } - } - } - } - - clearButtonGrid(); - - try { - Thread.sleep(timeToSleep); - } catch (InterruptedException e) { - e.printStackTrace(); - } - } - } -} diff --git a/PunchingBag/src/PunchingBagGUI.java b/PunchingBag/src/PunchingBagGUI.java deleted file mode 100644 index 5db11ef..0000000 --- a/PunchingBag/src/PunchingBagGUI.java +++ /dev/null @@ -1,643 +0,0 @@ -import java.awt.BorderLayout; -import java.awt.Color; -import java.awt.Component; -import java.awt.Dimension; -import java.awt.Graphics; -import java.awt.GridBagConstraints; -import java.awt.GridBagLayout; -import java.awt.Insets; -import java.awt.Rectangle; -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.IOException; - -import javax.swing.BorderFactory; -import javax.swing.JButton; -import javax.swing.JComboBox; -import javax.swing.JComponent; -import javax.swing.JFrame; -import javax.swing.JLabel; -import javax.swing.JList; -import javax.swing.JPanel; -import javax.swing.JScrollPane; -import javax.swing.JSplitPane; -import javax.swing.JTabbedPane; -import javax.swing.JTextArea; -import javax.swing.ListCellRenderer; - -import javax.sound.sampled.AudioFormat; -import javax.sound.sampled.AudioInputStream; -import javax.sound.sampled.AudioSystem; -import javax.sound.sampled.Clip; -import javax.sound.sampled.DataLine; -import javax.sound.sampled.Line; -import javax.sound.sampled.LineUnavailableException; -import javax.sound.sampled.Mixer; -import javax.sound.sampled.TargetDataLine; -import javax.sound.sampled.UnsupportedAudioFileException; -import javax.sound.sampled.AudioFormat.Encoding; -import javax.sound.sampled.Mixer.Info; - -public class PunchingBagGUI implements MouseListener, MouseMotionListener, - ButtonListener, LEDListener { - - public static enum Mode { - Menu, Interactive, Game - }; - - Mode currentMode = Mode.Interactive; - - static JFrame frame; - - // Contact - public enum Direction { - None, Up, Down, Left, Right - }; - - String soundDir = System.getProperty("user.dir") - + System.getProperty("file.separator"); - - File[] keys = { new File(soundDir + "G4.wav"), - new File(soundDir + "C5.wav"), new File(soundDir + "D5.wav"), - new File(soundDir + "E5.wav"), new File(soundDir + "F5.wav"), - new File(soundDir + "G5.wav") }; - - static PunchingBag bag = new PunchingBag(); - - final boolean useDebugScreen = true; - - public static void main(String[] args) throws InterruptedException { - new PunchingBagGUI(); - - } - - PunchingBagGUI() throws InterruptedException { - - // System.out.println(AudioSystem.getMixerInfo()[0].getName()); - // System.out.println(AudioSystem.getMixerInfo()[0].getDescription()); - // Mixer mix = AudioSystem.getMixer(AudioSystem.getMixerInfo()[0]); - - bag.connectToArduinos(); - - frame = new JFrame("Punching Bag GUI"); - frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); - - // frame.setSize(600, 600); - frame.setVisible(true); - - frame.addMouseListener(this); - frame.addMouseMotionListener(this); - - bag.addButtonListener(this); - bag.addLEDChangeListener(this); - - JSplitPane bottomTopSplitPane = new JSplitPane( - JSplitPane.VERTICAL_SPLIT); - - JSplitPane centerTopSplitPane = new JSplitPane( - JSplitPane.HORIZONTAL_SPLIT); - - JTabbedPane tabbedPane = new JTabbedPane(); - tabbedPane.addTab("LED Control Panel", null, new LEDControlPanel(), - "Allows control of individual LED's"); - - centerTopSplitPane.setLeftComponent(new PunchingBagSim()); - centerTopSplitPane.setRightComponent(tabbedPane); - - bottomTopSplitPane.setTopComponent(centerTopSplitPane); - bottomTopSplitPane.setBottomComponent(new SerialPanel()); - - frame.add(bottomTopSplitPane, BorderLayout.CENTER); - - // frame.pack(); - } - - void playKey(int key) { - try { - AudioInputStream sound = AudioSystem.getAudioInputStream(keys[key]); - DataLine.Info dataLine = new DataLine.Info(Clip.class, - sound.getFormat()); - Clip clip = (Clip) AudioSystem.getLine(dataLine); - clip.open(sound); - clip.start(); - } catch (LineUnavailableException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } catch (IOException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } catch (UnsupportedAudioFileException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } - } - - class SerialPanel extends JPanel implements ActionListener, - SerialReadListener, SerialWriteListener { - JTextArea buttonIn = new JTextArea(); - JTextArea buttonOut = new JTextArea(); - JTextArea ledIn = new JTextArea(); - JTextArea ledOut = new JTextArea(); - - public SerialPanel() { - JSplitPane splitPane = new JSplitPane(JSplitPane.HORIZONTAL_SPLIT); - JSplitPane buttonSplitPane = new JSplitPane( - JSplitPane.HORIZONTAL_SPLIT); - JSplitPane ledSplitPane = new JSplitPane( - JSplitPane.HORIZONTAL_SPLIT); - /* - * splitPane.setOneTouchExpandable(true); - * buttonSplitPane.setOneTouchExpandable(true); - * ledSplitPane.setOneTouchExpandable(true); - */ - - splitPane.setMinimumSize(new Dimension(200, 50)); - buttonSplitPane.setMinimumSize(new Dimension(100, 50)); - ledSplitPane.setMinimumSize(new Dimension(100, 50)); - - JButton clear = new JButton("Clear"); - clear.addActionListener(this); - - JPanel buttonInPanel = new JPanel(); - JScrollPane areaScrollPane = new JScrollPane(buttonIn); - areaScrollPane - .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS); - areaScrollPane.setPreferredSize(new Dimension(250, 100)); - buttonInPanel.add(areaScrollPane, BorderLayout.CENTER); - clear.setActionCommand("BI"); - buttonInPanel.add(clear, BorderLayout.SOUTH); - buttonInPanel.setBorder(BorderFactory - .createTitledBorder("Serial In - Button Arduino")); - buttonSplitPane.setLeftComponent(buttonInPanel); - - JPanel buttonOutPanel = new JPanel(); - areaScrollPane = new JScrollPane(buttonOut); - areaScrollPane - .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS); - areaScrollPane.setPreferredSize(new Dimension(250, 100)); - buttonOutPanel.add(areaScrollPane, BorderLayout.CENTER); - clear = new JButton("Clear"); - clear.setActionCommand("BO"); - buttonOutPanel.add(clear, BorderLayout.SOUTH); - buttonOutPanel.setBorder(BorderFactory - .createTitledBorder("Serial Out - Button Arduino")); - buttonSplitPane.setRightComponent(buttonOutPanel); - - JPanel ledInPanel = new JPanel(); - areaScrollPane = new JScrollPane(ledIn); - areaScrollPane - .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS); - areaScrollPane.setPreferredSize(new Dimension(250, 100)); - ledInPanel.add(areaScrollPane, BorderLayout.CENTER); - clear = new JButton("Clear"); - clear.setActionCommand("LI"); - ledInPanel.add(clear, BorderLayout.SOUTH); - ledInPanel.setBorder(BorderFactory - .createTitledBorder("Serial In - LED Arduino")); - ledSplitPane.setLeftComponent(ledInPanel); - - JPanel ledOutPanel = new JPanel(); - areaScrollPane = new JScrollPane(ledOut); - areaScrollPane - .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS); - areaScrollPane.setPreferredSize(new Dimension(250, 100)); - ledOutPanel.add(areaScrollPane, BorderLayout.CENTER); - clear = new JButton("Clear"); - clear.setActionCommand("LO"); - ledOutPanel.add(clear, BorderLayout.SOUTH); - ledOutPanel.setBorder(BorderFactory - .createTitledBorder("Serial Out - LED Arduino")); - ledSplitPane.setRightComponent(ledOutPanel); - - splitPane.setLeftComponent(buttonSplitPane); - splitPane.setRightComponent(ledSplitPane); - - this.add(splitPane); - - bag.buttonArduino.addSerialReadListener(this); - bag.buttonArduino.addSerialWriteListener(this); - - } - - @Override - public void actionPerformed(ActionEvent arg0) { - // TODO Auto-generated method stub - - } - - @Override - public void serialWriteEvent(byte b) { - buttonOut.append(String.valueOf((char) b)); - } - - @Override - public void serialWriteEvent(byte[] b) { - buttonOut.append(String.valueOf(b)); - } - - @Override - public void serialReadEvent(int b) { - if (b != -1) - buttonIn.append(String.valueOf((char) b)); - } - } - - class LEDControlPanel extends JPanel implements ActionListener { - String[] colours = { " ", "R", "Y", "G" }; - - public LEDControlPanel() { - this.setLayout(new GridBagLayout()); - - GridBagConstraints c = new GridBagConstraints(); - c.fill = GridBagConstraints.BOTH; - c.anchor = GridBagConstraints.CENTER; - // c.weightx = 0.2; - // c.weighty = 0.2; - - for (int y = 0; y < bag.ledHeight; y++) { - for (int x = 0; x < bag.ledWidth; x++) { - c.gridx = x; - c.gridy = y; - - RYGComboBoxRenderer renderer = new RYGComboBoxRenderer(); - JComboBox rygCombo = new JComboBox(colours); - rygCombo.setSelectedIndex(0); - rygCombo.addActionListener(this); - rygCombo.setActionCommand(String.valueOf(x) + "," - + String.valueOf(y)); - // rygCombo.setRenderer(renderer); - - this.add(rygCombo, c); - } - } - - c.gridx = 0; - c.gridy = 20; - c.fill = GridBagConstraints.HORIZONTAL; - c.anchor = GridBagConstraints.CENTER; - c.gridwidth = 9; - JButton clear = new JButton("Clear"); - clear.setActionCommand("C"); - clear.addActionListener(this); - this.add(clear, c); - } - - public void actionPerformed(ActionEvent a) { - if (a.getActionCommand() == "C") { - bag.clearLEDs(); - } else { - PunchingBag.Colour colour = PunchingBag.Colour.None; - if (((JComboBox) a.getSource()).getSelectedIndex() == 1) { - colour = PunchingBag.Colour.Red; - } else if (((JComboBox) a.getSource()).getSelectedIndex() == 2) { - colour = PunchingBag.Colour.Yellow; - } else if (((JComboBox) a.getSource()).getSelectedIndex() == 3) { - colour = PunchingBag.Colour.Green; - } - System.out.println("Setting " - + a.getActionCommand().split(",")[0] + " " - + a.getActionCommand().split(",")[1]); - bag.setLED(Integer.valueOf(a.getActionCommand().split(",")[0]), - Integer.valueOf(a.getActionCommand().split(",")[1]), - colour); - } - } - - class RYGComboBoxRenderer extends JLabel implements ListCellRenderer { - public RYGComboBoxRenderer() { - super(); - } - - public Component getListCellRendererComponent(JList list, - Object value, int index, boolean isSelected, - boolean cellHasFocus) { - - // Get the selected index. (The index param isn't - // always valid, so just use the value.) - - if (isSelected) { - setBackground(list.getSelectionBackground()); - setForeground(list.getSelectionForeground()); - } else { - setBackground(list.getBackground()); - setForeground(list.getForeground()); - } - - if (index != -1) - setText(colours[index]); - - return this; - } - } - } - - class PunchingBagSim extends JPanel implements ButtonListener, LEDListener, - MouseListener { - int buttonMinSize = 10; - int buttonMaxSize = 50; - - int ledMinSize = 10; - int ledMaxSize = 50; - - int buttonSize = 40; - int ledSize = 8; - - public PunchingBagSim() { - /* - * this.setMinimumSize(new Dimension((bag.buttonWidth * - * buttonMinSize) + (bag.ledWidth * ledMinSize), (bag.buttonHeight * - * buttonMinSize) + (bag.ledHeight * ledMaxSize))); - * this.setMaximumSize(new Dimension((bag.buttonWidth * - * buttonMaxSize) + (bag.ledWidth * ledMaxSize), (bag.buttonHeight * - * buttonMaxSize) + (bag.ledHeight * ledMaxSize))); - */ - bag.addButtonListener(this); - bag.addLEDChangeListener(this); - - this.addMouseListener(this); - - GridBagLayout gbl = new GridBagLayout(); - this.setLayout(gbl); - GridBagConstraints c = new GridBagConstraints(); - - // c.insets = new Insets(1, 1, 1, 1); - c.fill = GridBagConstraints.BOTH; - c.anchor = GridBagConstraints.CENTER; - // c.weightx = 0.2; - // c.weighty = 0.2; - for (int y = 0; y < bag.ledHeight; y++) { - for (int x = 0; x < bag.ledWidth; x++) { - c.gridx = x * 2; - c.gridy = y * 2; - - this.add(new LED(x, y), c); - } - } - - // c.weightx = 0.8; - // c.weighty = 0.8; - for (int y = 0; y < bag.buttonHeight; y++) { - for (int x = 0; x < bag.buttonWidth; x++) { - c.gridx = (x * 2) + 1; - c.gridy = (y * 2) + 1; - - this.add(new Button(x, y), c); - } - } - - // this.setMinimumSize(new Dimension(500,500)); - // this.setPreferredSize(new Dimension(500,500)); - - // this.setBackground(Color.BLUE); - - frame.pack(); - frame.setSize(500, 500); - - this.setBorder(BorderFactory.createLineBorder(Color.black)); - } - - /* - * public Dimension getPreferredSize() { if () return new - * Dimension(super.,10); } - */ - - class LED extends JComponent implements LEDListener { - final int x; - final int y; - - public LED(int x, int y) { - this.x = x; - this.y = y; - /* - * this.setMinimumSize(new Dimension(50,50)); this.setSize(50, - * 50); this.setPreferredSize(new Dimension(50,50)); - */ - bag.addLEDChangeListener(this); - - } - - public Dimension getPreferredSize() { - return new Dimension(5, 5); - } - - public void paintComponent(Graphics g) { - if (bag.getLED(x, y) == PunchingBag.Colour.Red) { - g.setColor(Color.red); - } else if (bag.getLED(x, y) == PunchingBag.Colour.Green) { - g.setColor(Color.green); - } else if (bag.getLED(x, y) == PunchingBag.Colour.Yellow) { - g.setColor(Color.yellow); - } else { - g.setColor(Color.white); - } - - g.fillOval(0, 0, this.getWidth(), this.getHeight()); - } - - @Override - public void LEDchanged() { - this.repaint(); - } - - } - - class Button extends JComponent implements MouseListener { - final int x; - final int y; - - public Button(int x, int y) { - this.x = x; - this.y = y; - setBorder(BorderFactory.createLineBorder(Color.black)); - this.addMouseListener(this); - } - - public Dimension getPreferredSize() { - return new Dimension(20, 20); - } - - public void paintComponent(Graphics g) { - super.paintComponent(g); - - g.setColor(Color.black); - g.fillRect(0, 0, this.getWidth(), this.getHeight()); - g.setColor(new Color(220, 220, 220)); - g.fillRect(4, 4, this.getWidth() - 8, this.getHeight() - 8); - - } - - public void mouseClicked(MouseEvent arg0) { - } - - public void mouseEntered(MouseEvent arg0) { - } - - public void mouseExited(MouseEvent arg0) { - } - - public void mousePressed(MouseEvent arg0) { - System.out.println("Button Pressed"); - bag.buttonPressed(x, y); - } - - public void mouseReleased(MouseEvent arg0) { - } - - } - - public void buttonPressed(int x, int y) { - this.repaint(); - } - - public void LEDchanged() { - this.repaint(); - - } - - @Override - public void mouseClicked(MouseEvent arg0) { - // TODO Auto-generated method stub - - } - - @Override - public void mouseEntered(MouseEvent arg0) { - // TODO Auto-generated method stub - - } - - @Override - public void mouseExited(MouseEvent arg0) { - // TODO Auto-generated method stub - - } - - @Override - public void mousePressed(MouseEvent me) { - if (currentMode == Mode.Interactive) { - // bag.buttonPressed(me.getX()/(buttonSize+ledSize), - // me.getY()/(buttonSize+ledSize)); - } - } - - @Override - public void mouseReleased(MouseEvent arg0) { - // TODO Auto-generated method stub - - } - } - - public void runInteractively(Contact contact) { - System.out.println("Contact"); - bag.buttonPressed(contact.x, contact.y); - } - - 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 arg0) { - /* - * if (currentMode == Mode.Interactive) { runInteractively(new - * Contact(System.currentTimeMillis(), (arg0 .getX() - 4) / 40, - * (arg0.getY() - 30) / 40, 0)); } - */ - } - - public void mouseReleased(MouseEvent arg0) { - // TODO Auto-generated method stub - - } - - public void mouseDragged(MouseEvent arg0) { - // TODO Auto-generated method stub - - } - - public void mouseMoved(MouseEvent arg0) { - // TODO Auto-generated method stub - - } - - public void contact(Contact c) { - // TODO Auto-generated method stub - - } - - @Override - public void buttonPressed(int x, int y) { - System.out.println("Button Pressed: " + x + " " + y); - // bag.circleExpand(x, y, 16); - // bag.setLED(x, y, PunchingBag.Colour.Red); - // bag.noise(new Rectangle(0, 0, 9, 20), 5000); - /* - * for (int bx=0; bx portEnum = CommPortIdentifier.getPortIdentifiers(); + while ( portEnum.hasMoreElements() ) + { + CommPortIdentifier portIdentifier = portEnum.nextElement(); + System.out.println(portIdentifier.getName() + " - " + getPortTypeName(portIdentifier.getPortType()) ); + } + } + + static String getPortTypeName ( int portType ) + { + switch ( portType ) + { + case CommPortIdentifier.PORT_I2C: + return "I2C"; + case CommPortIdentifier.PORT_PARALLEL: + return "Parallel"; + case CommPortIdentifier.PORT_RAW: + return "Raw"; + case CommPortIdentifier.PORT_RS485: + return "RS485"; + case CommPortIdentifier.PORT_SERIAL: + return "Serial"; + default: + return "unknown type"; + } + } + + public String getID() throws IOException { + byte[] idBytes = {0x49, 0x44}; + this.write(idBytes); + try { + Thread.sleep(100); + } catch (InterruptedException e) { + e.printStackTrace(); + } + int id; + while ((id = this.read()) == -1) {} + if (id == 66) { + return "B"; + } else if (id == 76) { + return "L"; + } else { + return "ERROR " + id; + } + } + + /** + * @return A HashSet containing the CommPortIdentifier for all serial ports that are not currently being used. + */ + public static HashSet getAvailableSerialPorts() { + HashSet h = new HashSet(); + Enumeration thePorts = CommPortIdentifier.getPortIdentifiers(); + while (thePorts.hasMoreElements()) { + CommPortIdentifier com = (CommPortIdentifier) thePorts.nextElement(); + switch (com.getPortType()) { + case CommPortIdentifier.PORT_SERIAL: + try { + CommPort thePort = com.open("CommUtil", 50); + thePort.close(); + h.add(com); + //System.out.println("Found a port: " + com.getPortType()); + } catch (PortInUseException e) { + System.out.println("Port, " + com.getName() + ", is in use."); + } catch (Exception e) { + System.err.println("Failed to open port " + com.getName()); + e.printStackTrace(); + } + } + } + return h; + } + + void connect ( String portName ) throws Exception + { + CommPortIdentifier portIdentifier = CommPortIdentifier.getPortIdentifier(portName); + if ( portIdentifier.isCurrentlyOwned() ) + { + System.out.println("Error: Port is currently in use"); + } + else + { + CommPort commPort = portIdentifier.open(this.getClass().getName(),2000); + + if ( commPort instanceof SerialPort ) + { + SerialPort serialPort = (SerialPort) commPort; + serialPort.setSerialPortParams(9600,SerialPort.DATABITS_8,SerialPort.STOPBITS_1,SerialPort.PARITY_NONE); + + in = serialPort.getInputStream(); + out = serialPort.getOutputStream(); + + //(new Thread(this)).start(); + } + else + { + System.out.println("Error: Only serial ports are handled by this example."); + } + } + } + + /** */ + public class SerialReader implements Runnable + { + InputStream in; + + public SerialReader ( InputStream in ) + { + this.in = in; + } + + public void run () + { + byte[] buffer = new byte[1024]; + int len = -1; + try + { + while ( ( len = this.in.read(buffer)) > -1 ) + { + System.out.print(new String(buffer,0,len)); + input(new String(buffer,0,len)); + } + } + catch ( IOException e ) + { + e.printStackTrace(); + } + } + } + + public static void input(String string) { + + } + + /** */ + public class SerialWriter implements Runnable + { + OutputStream out; + + public SerialWriter ( OutputStream out ) + { + this.out = out; + } + + public void run () + { + try + { + int c = 0; + while ( ( c = System.in.read()) > -1 ) + { + this.out.write(c); + } + } + catch ( IOException e ) + { + e.printStackTrace(); + } + } + } + + public void run() { + byte[] buffer = new byte[1024]; + int len = -1; + try + { + while ( ( len = this.in.read(buffer)) > -1 ) + { + System.out.print(new String(buffer,0,len)); + //input(new String(buffer,0,len)); + } + } + catch ( IOException e ) + { + e.printStackTrace(); + } + + } + + + public void write(byte[] bytes) throws IOException { + out.write(bytes); + SerialWriteListener[] sListeners = writeListenerList + .getListeners(SerialWriteListener.class); + for (int i = 0; i < writeListenerList.getListenerCount(); i++) { + sListeners[i].serialWriteEvent(bytes); + } + } + + public void write(byte b) throws IOException { + out.write(b); + SerialWriteListener[] sListeners = writeListenerList + .getListeners(SerialWriteListener.class); + for (int i = 0; i < writeListenerList.getListenerCount(); i++) { + sListeners[i].serialWriteEvent(b); + } + } + + public int read() throws IOException { + int read = in.read(); + SerialReadListener[] sListeners = readListenerList + .getListeners(SerialReadListener.class); + for (int i = 0; i < readListenerList.getListenerCount(); i++) { + sListeners[i].serialReadEvent(read); + } + return read; + } + +} diff --git a/PunchingBag/src/uk/ac/open/punchingbag/ButtonListener.java b/PunchingBag/src/uk/ac/open/punchingbag/ButtonListener.java new file mode 100644 index 0000000..abea103 --- /dev/null +++ b/PunchingBag/src/uk/ac/open/punchingbag/ButtonListener.java @@ -0,0 +1,10 @@ +package uk.ac.open.punchingbag; +import java.util.EventListener; + +public interface ButtonListener extends EventListener { + + void buttonPressed(int x, int y); + + void contact(Contact c); + +} diff --git a/PunchingBag/src/uk/ac/open/punchingbag/Contact.java b/PunchingBag/src/uk/ac/open/punchingbag/Contact.java new file mode 100644 index 0000000..b33ef53 --- /dev/null +++ b/PunchingBag/src/uk/ac/open/punchingbag/Contact.java @@ -0,0 +1,23 @@ +package uk.ac.open.punchingbag; + + + public class Contact { + // Height of bag is + + public final long time; // Time of the contact with the bag (in millis) + public final int x; + public final int y; + public final int force; // 0 - 100 + + Contact(long time, int x, int y, int force) { + this.time = time; + this.x = x; + this.y = y; + this.force = force; + } + + public String toString() { + return "X: " + x + " Y: " + y + " Force: " + force; + } + + } \ No newline at end of file diff --git a/PunchingBag/src/uk/ac/open/punchingbag/Font.java b/PunchingBag/src/uk/ac/open/punchingbag/Font.java new file mode 100644 index 0000000..aec6550 --- /dev/null +++ b/PunchingBag/src/uk/ac/open/punchingbag/Font.java @@ -0,0 +1,375 @@ +package uk.ac.open.punchingbag; + +public class Font { + char font[] = { + // -------- Space + 0b00000000, + 0b00000000, + 0b00000000, + 0b00000000, + // -------- A + 0b01111110, + 0b10010000, + 0b10010000, + 0b01111110, + // -------- B + 0b01101100, + 0b10010010, + 0b10010010, + 0b11111110, + // -------- C + 0b10000010, + 0b10000010, + 0b01111100, + // -------- D + 0b00111000, + 0b01000100, + 0b10000010, + 0b11111110, + // -------- E + 0b10000010, + 0b10010010, + 0b11111110, + // -------- F + 0b10000000, + 0b10010000, + 0b11111110, + // -------- G + 0b01011100, + 0b10010010, + 0b10000010, + 0b01111100, + // -------- H + 0b11111110, + 0b00010000, + 0b00010000, + 0b11111110, + // -------- I + 0b10000010, + 0b11111110, + 0b10000010, + // -------- J + 0b11111100, + 0b00000010, + 0b00001100, + // -------- K + 0b10000110, + 0b01001000, + 0b00110000, + 0b11111110, + // -------- L + 0b00000010, + 0b00000010, + 0b11111110, + // -------- M + 0b11111110, + 0b01100000, + 0b00111100, + 0b01100000, + 0b11111110, + // -------- N + 0b11111110, + 0b00011000, + 0b01100000, + 0b11111110, + // -------- O + 0b01111100, + 0b10000010, + 0b10000010, + 0b01111100, + // -------- P + 0b01100000, + 0b10010000, + 0b10010000, + 0b11111110, + // -------- Q + 0b01111010, + 0b10000100, + 0b10001010, + 0b01111100, + // -------- R + 0b01100110, + 0b10011000, + 0b10010000, + 0b11111110, + // -------- S + 0b10001100, + 0b10010010, + 0b01100010, + // -------- T + 0b10000000, + 0b11111110, + 0b10000000, + // -------- U + 0b11111100, + 0b00000010, + 0b00000010, + 0b11111100, + // -------- V + 0b11000000, + 0b00111000, + 0b00000110, + 0b00111000, + 0b11000000, + // -------- W + 0b11111110, + 0b00001100, + 0b00111000, + 0b00001100, + 0b11111110, + // -------- X + 0b11000110, + 0b00111000, + 0b00111000, + 0b11000110, + // -------- Y + 0b11100000, + 0b00011110, + 0b11100000, + // -------- Z + 0b11000010, + 0b10110010, + 0b10001110, + // -------- Unknown character + 0b00111000, + 0b00111000, + 0b00111000, + // -------- 0 + 0b01111100, + 0b10100010, + 0b10010010, + 0b01111100, + // -------- 1 + 0b11111110, + 0b01000000, + // -------- 2 + 0b01100010, + 0b10010010, + 0b10001110, + // -------- 3 + 0b01101100, + 0b10010010, + 0b10000010, + // -------- 4 + 0b11111110, + 0b00010000, + 0b11110000, + // -------- 5 + 0b10001100, + 0b10010010, + 0b11110010, + // -------- 6 + 0b01001100, + 0b10010010, + 0b10010010, + 0b01111100, + // -------- 7 + 0b11100000, + 0b10011110, + 0b10000000, + // -------- 8 + 0b01101100, + 0b10010010, + 0b10010010, + 0b01101100, + // -------- 9 + 0b01111100, + 0b10010010, + 0b10010010, + 0b01100100, + // -------- : + 0b00100100, + // -------- ; + 0b00100110, + 0b00000001, + // -------- ! + 0b01100000, + 0b11111010, + 0b01100000, + // -------- Heart + 0b01111000, + 0b11111100, + 0b11111110, + 0b01111111, + 0b11111110, + 0b11111100, + 0b01111000, + // -------- < + 0b01000100, + 0b00101000, + 0b00010000, + // -------- = + 0b00101000, + 0b00101000, + 0b00101000, + 0b00101000, + // -------- > + 0b00010000, + 0b00101000, + 0b01000100, + // -------- ? + 0b01100000, + 0b10011010, + 0b10000000, + // -------- @ + 0b01111100, + 0b10000010, + 0b10111010, + 0b10100010, + 0b01011100, + // -------- ( + 0b10000010, + 0b01111100, + // -------- ) + 0b01111100, + 0b10000010, + // -------- * + 0b00101000, + 0b00010000, + 0b00101000, + // -------- + + 0b00010000, + 0b00010000, + 0b01111100, + 0b00010000, + 0b00010000, + // -------- , + 0b00000110, + 0b00000001, + // -------- - + 0b00010000, + 0b00010000, + 0b00010000, + 0b00010000, + // -------- . + 0b00000010, + // -------- / + 0b11000000, + 0b00111000, + 0b00000110, + // -------- a + 0b00111110, + 0b00100010, + 0b00100010, + 0b00011100, + // -------- b + 0b00011100, + 0b00100010, + 0b00100010, + 0b11111110, + // -------- c + 0b00100010, + 0b00100010, + 0b00011100, + // -------- d + 0b11111110, + 0b00100010, + 0b00100010, + 0b00011100, + // -------- e + 0b00011000, + 0b00101010, + 0b00101010, + 0b00011100, + // -------- f + 0b10010000, + 0b01111110, + 0b00010000, + // -------- g + 0b00111110, + 0b00100101, + 0b00100101, + 0b00011000, + // -------- h + 0b00011110, + 0b00100000, + 0b00100000, + 0b11111110, + // -------- i + 0b00000010, + 0b01011110, + 0b00010010, + // -------- j + 0b01011110, + 0b00000001, + 0b00000001, + // -------- k + 0b00100010, + 0b00010100, + 0b00001000, + 0b11111110, + // -------- l + 0b00000010, + 0b11111100, + // -------- m + 0b00011110, + 0b00100000, + 0b00111110, + 0b00100000, + 0b00111110, + // -------- n + 0b00011110, + 0b00100000, + 0b00100000, + 0b00111110, + // -------- o + 0b00011100, + 0b00100010, + 0b00100010, + 0b00011100, + // -------- p + 0b00011100, + 0b00100010, + 0b00100010, + 0b00111111, + // -------- q + 0b00111111, + 0b00100010, + 0b00100010, + 0b00011100, + // -------- r + 0b00010000, + 0b00100000, + 0b00111110, + // -------- s + 0b00100100, + 0b00101010, + 0b00101010, + 0b00010010, + // -------- t + 0b00100010, + 0b11111100, + 0b00100000, + // -------- u + 0b00111110, + 0b00000010, + 0b00000010, + 0b00111100, + // -------- v + 0b00111000, + 0b00000110, + 0b00111000, + // -------- w + 0b00111110, + 0b00000010, + 0b00011110, + 0b00000010, + 0b00111100, + // -------- x + 0b00110110, + 0b00001000, + 0b00110110, + // -------- y + 0b00111110, + 0b00000101, + 0b00000101, + 0b00111001, + // -------- z + 0b00110010, + 0b00101010, + 0b00100110, + 0b00100010, + 0b11000001 + }; + +} diff --git a/PunchingBag/src/uk/ac/open/punchingbag/LEDListener.java b/PunchingBag/src/uk/ac/open/punchingbag/LEDListener.java new file mode 100644 index 0000000..a8b9c61 --- /dev/null +++ b/PunchingBag/src/uk/ac/open/punchingbag/LEDListener.java @@ -0,0 +1,8 @@ +package uk.ac.open.punchingbag; +import java.util.EventListener; + +interface LEDListener extends EventListener { + + void LEDchanged(); + +} diff --git a/PunchingBag/src/uk/ac/open/punchingbag/PunchingBag.java b/PunchingBag/src/uk/ac/open/punchingbag/PunchingBag.java new file mode 100644 index 0000000..31b0575 --- /dev/null +++ b/PunchingBag/src/uk/ac/open/punchingbag/PunchingBag.java @@ -0,0 +1,786 @@ +package uk.ac.open.punchingbag; + +import gnu.io.CommPortIdentifier; + +import javax.swing.event.EventListenerList; + +import java.awt.Rectangle; +import java.awt.geom.Area; + +import java.io.IOException; +import java.math.BigInteger; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.HashSet; +import java.util.Iterator; + +// TODO: Loads of threads in this class, make sure everything is thread safe. + +public class PunchingBag implements Runnable { + boolean ledsChanged = false; + final public int ledHeight = 20; + final public int ledWidth = 9; + private byte[] rawLeds = new byte[6 * 8]; + private Colour[][] leds = new Colour[ledWidth][ledHeight]; // NEVER ACCESS + // DIRECTLY (Use + // SetLedInternal) + private byte[] ledGridIntensities = new byte[6]; + final public int buttonHeight = 19; + final public int buttonWidth = 8; + private boolean[][] buttons = new boolean[buttonWidth][buttonHeight]; + boolean buttonsChanged = false; + + int bottomAccelX = 0; + int bottomAccelY = 0; + int topAccelX = 0; + int topAccelY = 0; + boolean acccelChanged = false; + + private long lastRefresh = 0; + + private ArrayList runningEffects = new ArrayList(); + + Arduino buttonArduino = new Arduino(); + Arduino ledArduino = new Arduino(); + + boolean debugTimings = false; + boolean debugSerial = false; + + static private PunchingBag bag = new PunchingBag(); + + public static PunchingBag getBag() { + return bag; + } + + public enum Colour { + None, Red, Yellow, Green + }; + + public enum Direction { + Right, Left, Up, Down + }; + + // Is there a better class for this? One that it is not a swing class. + private EventListenerList buttonListenerList = new EventListenerList(); + private EventListenerList ledListenerList = new EventListenerList(); + private EventListenerList accelListenerList = new EventListenerList(); + + private PunchingBag() { + Thread bagControlThread = new Thread(this); + bagControlThread.setPriority(Thread.MAX_PRIORITY); + bagControlThread.start(); + } + + /** + * Adds an ActionListener to the button. + * + * @param l + * the ActionListener to be added + */ + public void addButtonListener(ButtonListener l) { + buttonListenerList.add(ButtonListener.class, l); + } + + public void addLEDChangeListener(LEDListener l) { + ledListenerList.add(LEDListener.class, l); + } + + public void addAccelChangeListener(AccelListener l) { + accelListenerList.add(AccelListener.class, l); + } + + public Colour getLED(int x, int y) { + return leds[x][y]; + } + + private boolean setLEDInternal(int x, int y, Colour colour) { + if (x >= 0 && x < ledWidth && y >= 0 && y < ledHeight) { + if (leds[x][y] != colour) { + leds[x][y] = colour; + ledsChanged = true; + + } + return true; + } else { + return false; + } + } + + public void setLED(int x, int y, Colour colour) { + runningEffects.add(new Point(x, y, colour)); + } + + public void circleExpand(int x, int y, int intensity) { + runningEffects.add(new CircleExpand(x, y, 100)); + } + + void squareExpand(int x, int y, int intensity, Colour colour) { + runningEffects.add(new SquareExpand(x, y, intensity, colour)); + } + + public void fillRect(int x, int y, int width, int height, Colour colour, long time) { + runningEffects.add(new FillRect(x, y, width, height, colour, time)); + } + + void rect(int x, int y, int width, int height, Colour colour) { + runningEffects.add(new Rect(x, y, width, height, colour)); + } + + void noise(Rectangle rect, long time) { + runningEffects.add(new Noise(rect, System.currentTimeMillis() + time)); + } + + abstract class Effect { + long lastRefresh = 0; + boolean stop = false; + + // int refreshRate = 60; // Times per second to refresh + + public void stop() { + stop = true; + } + + abstract public void draw(); + } + + class Point extends Effect { + final int x; + final int y; + final Colour colour; + + public Point(int x, int y, Colour colour) { + this.x = x; + this.y = y; + this.colour = colour; + } + + public void draw() { + setLEDInternal(x, y, colour); + } + } + + class FillRect extends Effect { + final int x; + final int y; + final int width; + final int height; + final Colour colour; + final long time; + + public FillRect(int x, int y, int width, int height, Colour colour, long time) { + this.x = x; + this.y = y; + this.width = width; + this.height = height; + this.colour = colour; + this.time = System.currentTimeMillis() + time; + } + + public void draw() { + fillRectInternal(x, y, width, height, colour); + if (System.currentTimeMillis() >= time) { + stop(); + } + } + } + + class Rect extends Effect { + final int x; + final int y; + final int width; + final int height; + final Colour colour; + + public Rect(int x, int y, int width, int height, Colour colour) { + this.x = x; + this.y = y; + this.width = width; + this.height = height; + this.colour = colour; + } + + public void draw() { + drawRectInternal(x, y, width, height, colour); + } + } + + class Text extends Effect { + final String string; + final Area area; + final Direction direction; + final int speed; + + public Text(String string, Area area, Direction direction, int speed) { + this.string = string; + this.area = area; + this.direction = direction; + this.speed = speed; + + } + + public void draw() { + byte[] stringBytes = string.getBytes(); + + } + } + + class CircleExpand extends Effect { + final double x; + final double y; + int intensity; + boolean drawnSomething = true; + + double currentRadius = 0.5; + + public CircleExpand(int x, int y, int intensity) { + this.x = x + 0.5; + this.y = y + 0.5; + this.intensity = intensity; + } + + public void draw() { + Colour colour; + + if (intensity >= 10) { + colour = Colour.Red; + } else if (intensity >= 5) { + colour = Colour.Yellow; + } else { + colour = Colour.Green; + } + + intensity -= 5; + + currentRadius += 0.4 + (currentRadius / 20); + // currentRadius += 0.01; + // longhand: currentRadius = currentRadius + 0.1 + (currentRadius / + // 10); + + if (!drawCircle(x, y, currentRadius, colour)) + stop = true; + } + + } + + class SquareExpand extends Effect { + final int x; + final int y; + final Colour colour; + int intensity; + boolean drawnSomething = true; + + int heightWidth = 2; + + public SquareExpand(int x, int y, int intensity, Colour colour) { + this.x = x; + this.y = y; + this.intensity = intensity; + this.colour = colour; + + } + + public void draw() { + heightWidth += 0.1 + 0.1 + (heightWidth / 20); + if (!drawRectCenter(x, y, heightWidth, heightWidth, colour)) + stop = true; + + } + + } + + class Noise extends Effect { + final Rectangle area; + final long endTime; + + public Noise(Rectangle area, long endTime) { + this.area = area; + this.endTime = endTime; + } + + @Override + public void draw() { + if (endTime >= System.currentTimeMillis()) { + for (int y = area.y; y < (area.y + area.height); y++) { + for (int x = area.x; x < (area.x + area.width); x++) { + double random = Math.random(); + if (random < 0.25) { + setLEDInternal(x, y, Colour.Red); + } else if (random < 0.5) { + setLEDInternal(x, y, Colour.Yellow); + } else if (random < 0.75) { + setLEDInternal(x, y, Colour.Green); + } else { + setLEDInternal(x, y, Colour.None); + } + } + } + } else { + stop(); + } + } + } + + public boolean drawRectCenter(int x, int y, int height, int width, Colour colour) { + if (height < 0) { + height = 0; + } + if (width < 0) { + width = 0; + } + if (height == 0 && width == 0) { + return setLEDInternal(x, y, colour); + } + + boolean doneSomething = false; + int widthEx = 0; + int heightEx = 0; + + do { + if (setLEDInternal((x - (height / 2)) + widthEx, y - (height / 2), colour)) { + doneSomething = true; + } + if (setLEDInternal(x - (height / 2), (y - (height / 2)) + heightEx, colour)) { + doneSomething = true; + } + if (setLEDInternal((x - (height / 2)) + widthEx, y + (height / 2), colour)) { + doneSomething = true; + } + if (setLEDInternal(x + (height / 2), (y - (height / 2)) + heightEx, colour)) { + doneSomething = true; + } + if (heightEx < height) { + heightEx++; + } + if (widthEx < width) { + widthEx++; + } + + } while (height >= 0 && width >= 0); + + return doneSomething; + } + + public boolean drawRectInternal(int x, int y, int width, int height, Colour colour) { + if (height < 0) { + height = 0; + } + if (width < 0) { + width = 0; + } + if (height == 0 && width == 0) { + return setLEDInternal(x, y, colour); + } + + boolean doneSomething = false; + int heightEx = 0; + int widthEx = 0; + boolean finished = true; + do { + if (setLEDInternal(x + widthEx, y, colour)) { + doneSomething = true; + } + if (setLEDInternal(x, y + heightEx, colour)) { + doneSomething = true; + } + if (setLEDInternal(x + widthEx, y + height, colour)) { + doneSomething = true; + } + if (setLEDInternal(x + width, y + heightEx, colour)) { + doneSomething = true; + } + if (heightEx < height) { + finished = false; + heightEx++; + } + if (widthEx < width) { + finished = false; + widthEx++; + } + } while (!finished); + + return doneSomething; + } + + public boolean drawEllipse(int x, int y, int radx, int rady, Colour colour) { + if (radx == 0 && rady == 0) { + return setLEDInternal(x, y, colour); + } + + boolean doneSomething = false; + + int dx = 0, dy = rady; /* first quadrant from top left to bottom right */ + int a2 = radx * radx, b2 = rady * rady; + int err = b2 - (2 * rady - 1) * a2, e2; /* error value in the first step */ + + do { + if (setLEDInternal(x + dx, y + dy, colour)) {/* I. Quadrant */ + doneSomething = true; + } + if (setLEDInternal(x - dx, y + dy, colour)) {/* II. Quadrant */ + doneSomething = true; + } + if (setLEDInternal(x - dx, y - dy, colour)) {/* III. Quadrant */ + doneSomething = true; + } + if (setLEDInternal(x + dx, y - dy, colour)) {/* IV. Quadrant */ + doneSomething = true; + } + + e2 = 2 * err; + if (e2 < (2 * dx + 1) * b2) { + dx++; + err += (2 * dx + 1) * b2; + } + if (e2 > -(2 * dy - 1) * a2) { + dy--; + err -= (2 * dy - 1) * a2; + } + } while (dy >= 0); + + while (dx++ < radx) { /* correction for flat ellipses (b=1) */ + if (setLEDInternal(x + dx, y, colour)) { + doneSomething = true; + } + if (setLEDInternal(x - dx, y, colour)) { + doneSomething = true; + } + } + return doneSomething; + } + + public boolean drawCircle(double x, double y, double radius, Colour colour) { + boolean drawnSomething = false; + int px; + int py; + for (double i = 0; i < 360; i++) { + px = (int) Math.round(x + (radius * Math.cos(i))); + py = (int) Math.round(y + (radius * Math.sin(i))); + + if (x >= 0 && x <= 8 && y >= 0 && y <= 19) { + if (setLEDInternal(px, py, colour)) { + drawnSomething = true; + } + } + } + return drawnSomething; + } + + public boolean fillRectInternal(int x, int y, int height, int width, Colour colour) { + boolean doneSomething = false; + for (int px = x; px < (x + height); px++) { + + for (int py = y; py < (y + width); py++) { + if (setLEDInternal(px, py, colour)) { + doneSomething = true; + } + } + } + + return doneSomething; + + } + + private void calculateRawLeds() { + // First clear everything + Arrays.fill(rawLeds, (byte) 0); + // First loop through the 5 easy arrays + for (int grid = 0; grid < 5; grid++) { + for (int x = 0; x < 8; x++) { + for (int y = 0; y < 8; y++) { + if ((y % 2) == 0) { + if (leds[1 + x][(grid * 4) + (y / 2)] == Colour.Green || leds[1 + x][(grid * 4) + (y / 2)] == Colour.Yellow) { + rawLeds[(grid * 8) + x] = (byte) (rawLeds[(grid * 8) + x] | (1 << (7 - y))); + } + } else { + if (leds[1 + x][(grid * 4) + (y / 2)] == Colour.Red || leds[1 + x][(grid * 4) + (y / 2)] == Colour.Yellow) { + rawLeds[(grid * 8) + x] = (byte) (rawLeds[(grid * 8) + x] | (1 << (7 - y))); + } + } + } + } + } + + /* + * for (int y = 0; y <= 18; y++) { for (int x = 0; x <= 6; x++) { if ((y + * % 2) == 0) { if (leds[x][y] == Colour.Green || leds[x][y] == + * Colour.Yellow) { rawLeds[(int) Math.floor(y / 4)] = (byte) + * (rawLeds[(int) Math .floor(y / 4)] | (1 << (7 - x))); } } else { if + * (leds[x][y] == Colour.Red || leds[x][y] == Colour.Yellow) { + * rawLeds[(int) Math.floor(y / 4)] = (byte) (rawLeds[(int) Math + * .floor(y / 4)] | (1 << (7 - x))); } } } } + */ + /* + * int x = 7; // TODO: Complete and test, or rethink the following? for + * (int startY = 0; startY <= 4; startY++) { for (int y = 0; y <= 3; + * y++) { if (leds[x][startY + (y * 4)] == Colour.Red || leds[x][startY + * + (y * 4)] == Colour.Yellow) { rawLeds[(5 * 8) + startY] = (byte) + * (rawLeds[(int) Math .floor(y / 4)] | (1 << (7 - x))); } if + * (leds[x][y] == Colour.Green || leds[x][y] == Colour.Yellow) { + * rawLeds[(int) Math.floor(y / 4)] = (byte) (rawLeds[(int) Math + * .floor(y / 4)] | (1 << (7 - x))); } } } + */ + } + + /* Clears the led grid */ + private void clearLEDGrid() { + for (int x = 0; x < ledWidth; x++) { + for (int y = 0; y < ledHeight; y++) { + leds[x][y] = Colour.None; + } + } + } + + private void clearButtonGrid() { + for (int x = 0; x < buttonWidth; x++) { + for (int y = 0; y < buttonHeight; y++) { + buttons[x][y] = false; + } + } + } + + private void clearEffects() { + for (Iterator iter = runningEffects.iterator(); iter.hasNext();) { + ((Effect) iter.next()).stop(); + } + } + + public void clearLEDs() { + clearLEDGrid(); + clearEffects(); + } + + public void setLEDGridIntensity(byte grid, byte intensity) { + ledGridIntensities[grid] = intensity; + } + + public void setLEDIntensities(byte intensity) { + Arrays.fill(ledGridIntensities, intensity); + } + + public void buttonPressed(int x, int y) { + buttons[x][y] = true; + buttonsChanged = true; + } + + public boolean connectToArduinos() { + try { + ledArduino.connect("COM6"); + buttonArduino.connect("COM7"); + } catch (Exception e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } + HashSet serialPorts = Arduino.getAvailableSerialPorts(); + for (Iterator iter = serialPorts.iterator(); iter.hasNext();) { + CommPortIdentifier comPort = (CommPortIdentifier) iter.next(); + // HACK FOR WINDOWS TO IDENIFY PORTS LIKELY TO CONTAIN ARDUINO + // (COM10 for instance). TODO: FIX + if (comPort.getName().length() == 5) { + System.out.println(comPort.getName()); + } + try { + + System.out.println(comPort.getName()); + } catch (Exception e) { + e.printStackTrace(); + } + } + return true; + } + + private void readAccelData(String data) { + //System.out.println("Data: " + data); + String[] nums = data.split(" "); + for (int x = 1; x < 5; x++) { + // Regex expression to strip newline at end (normally just 4th) + int num = Integer.valueOf(nums[x].replaceAll("[^0-9]", "")); + if (x == 1 && num != topAccelX) { + topAccelX = num; + acccelChanged = true; + } else if (x == 2 && num != topAccelY) { + topAccelY = num; + acccelChanged = true; + } else if (x == 3 && num != bottomAccelX) { + bottomAccelX = num; + acccelChanged = true; + } else if (x == 4 && num != bottomAccelY) { + bottomAccelY = num; + acccelChanged = true; + } + } + } + + private void readButtonData(String data) { + if (data.replaceAll("[^0-9]", "").length() > 0) { + //System.out.print(data); + int num = Integer.valueOf(data.replaceAll("[^0-9]", "")); + int x = ((num - 1) % 8); + int y = (num - 1) / 8; + //System.out.println("X: " + x + " Y: " + y); + if (!(x < 0)) { + buttons[x][y] = true; + buttonsChanged = true; + } + } + } + + private void printByte(byte b) { + // System.out.println("Byte: " + b); + String str; + for (int j = 0; j < 8; j++) { + byte val = (byte) (b & (1 << (7 - j))); + // System.out.println("Val: " + val + " " + (1 << (7-j))); + if (val > 0) { + str = "1"; + } else { + str = "0"; + } + System.out.print(str); + } + } + + private void printlnByte(byte b) { + printByte(b); + System.out.println(""); + } + + public void run() { + long timeToSleep = 10; + + while (true) { + if (debugTimings) { + System.out.println("Time since last refresh: " + (System.currentTimeMillis() - lastRefresh)); + if ((System.currentTimeMillis() - lastRefresh) != 0) + System.out.println("FPS: " + (1000 / (System.currentTimeMillis() - lastRefresh))); + } + + if ((System.currentTimeMillis() - lastRefresh) > (1000 / 60)) { + if (timeToSleep > 0) { + timeToSleep--; + } + } else { + timeToSleep++; + } + if (debugTimings) + System.out.println("Sleeping: " + timeToSleep); + lastRefresh = System.currentTimeMillis(); + + // System.out.println("R"); + synchronized (leds) { + clearLEDGrid(); + // clearButtonGrid(); + long beginTimeForEffects = System.currentTimeMillis(); + synchronized (runningEffects) { // Should prevent + // ConcurrentModificationException's + // (havent managed to produce one + // though + for (Iterator iter = runningEffects.iterator(); iter.hasNext();) { + Effect ef = (Effect) iter.next(); + if (ef.stop) { + iter.remove(); + } else {// if ((ef.lastRefresh + (1000 / + // ef.refreshRate)) <= + // Systems.currentTimeMillis()) { + ef.draw(); + ef.lastRefresh = System.currentTimeMillis(); + } + } + } + // System.out.println("Effects: " + // + (System.currentTimeMillis() - beginTimeForEffects)); + } + + long beginTimeButtonIn = System.currentTimeMillis(); + if (buttonArduino.in != null) { + try { + int read; + while ((read = buttonArduino.read()) != -1) { + // System.out.print((char) read); + if ((char) read == 'A') { + String str = ""; + // StringBuilder sb = new StringBuilder(20); + while ((read = buttonArduino.read()) != '\n') { + str = str + String.valueOf((char) read); + // sb.append((char) read); + } + // System.out.println(""); + readAccelData(str); + // String[] nums = sbString.trim().split(" "); + // System.out.println(nums); + // for (int x=0; x<4; x++) { + // System.out.println(nums[x]); + // } + + } else if ((char) read == 'B') { + String str = ""; + // StringBuilder sb = new StringBuilder(20); + while ((read = buttonArduino.read()) != '\n') { + str = str + String.valueOf((char) read); + // sb.append((char) read); + } + // System.out.println(""); + readButtonData(str); + + } else { + // System.out.println((char) read); + } + // System.out.print("|"); + } + } catch (IOException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + if (debugTimings) + System.out.println("Button: " + (System.currentTimeMillis() - beginTimeButtonIn)); + + calculateRawLeds(); + String str; + for (int i = 0; i < (6 * 8); i++) { + // printByte(rawLeds[i]); + } + // System.out.println(""); + + // Arrays.fill(rawLeds, (byte) -42); + if (ledArduino.out != null) { + // calculateRawLeds(); + try { + ledArduino.write(((byte) 108)); + ledArduino.write(rawLeds); + } catch (IOException e1) { + e1.printStackTrace(); + } + } + + if (ledsChanged) { + LEDListener[] LEDListeners = ledListenerList.getListeners(LEDListener.class); + for (int i = 0; i < ledListenerList.getListenerCount(); i++) { + LEDListeners[i].LEDchanged(); + } + } + + if (buttonsChanged) { + ButtonListener[] buttonListeners = buttonListenerList.getListeners(ButtonListener.class); + for (int i = 0; i < buttonListenerList.getListenerCount(); i++) { + for (int x = 0; x < buttonWidth; x++) { + for (int y = 0; y < buttonHeight; y++) { + if (buttons[x][y]) { + buttonListeners[i].buttonPressed(x, y); + buttonListeners[i].contact(new Contact(System.currentTimeMillis(), x, y, bottomAccelX)); + } + } + } + } + } + + clearButtonGrid(); + + try { + Thread.sleep(timeToSleep); + } catch (InterruptedException e) { + e.printStackTrace(); + } + } + } +} diff --git a/PunchingBag/src/uk/ac/open/punchingbag/PunchingBagGUI.java b/PunchingBag/src/uk/ac/open/punchingbag/PunchingBagGUI.java new file mode 100644 index 0000000..e790abb --- /dev/null +++ b/PunchingBag/src/uk/ac/open/punchingbag/PunchingBagGUI.java @@ -0,0 +1,650 @@ +package uk.ac.open.punchingbag; +import java.awt.BorderLayout; +import java.awt.Color; +import java.awt.Component; +import java.awt.Dimension; +import java.awt.Graphics; +import java.awt.GridBagConstraints; +import java.awt.GridBagLayout; +import java.awt.Insets; +import java.awt.Rectangle; +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.IOException; + +import javax.swing.BorderFactory; +import javax.swing.JButton; +import javax.swing.JComboBox; +import javax.swing.JComponent; +import javax.swing.JFrame; +import javax.swing.JLabel; +import javax.swing.JList; +import javax.swing.JPanel; +import javax.swing.JScrollPane; +import javax.swing.JSplitPane; +import javax.swing.JTabbedPane; +import javax.swing.JTextArea; +import javax.swing.ListCellRenderer; + +import javax.sound.sampled.AudioFormat; +import javax.sound.sampled.AudioInputStream; +import javax.sound.sampled.AudioSystem; +import javax.sound.sampled.Clip; +import javax.sound.sampled.DataLine; +import javax.sound.sampled.Line; +import javax.sound.sampled.LineUnavailableException; +import javax.sound.sampled.Mixer; +import javax.sound.sampled.TargetDataLine; +import javax.sound.sampled.UnsupportedAudioFileException; +import javax.sound.sampled.AudioFormat.Encoding; +import javax.sound.sampled.Mixer.Info; + +public class PunchingBagGUI implements MouseListener, MouseMotionListener, + ButtonListener, LEDListener { + + public static enum Mode { + Menu, Interactive, Game + }; + + Mode currentMode = Mode.Interactive; + + static JFrame frame; + + // Contact + public enum Direction { + None, Up, Down, Left, Right + }; + + String soundDir = System.getProperty("user.dir") + + System.getProperty("file.separator"); + + File[] keys = { new File(soundDir + "G4.wav"), + new File(soundDir + "C5.wav"), new File(soundDir + "D5.wav"), + new File(soundDir + "E5.wav"), new File(soundDir + "F5.wav"), + new File(soundDir + "G5.wav") }; + + static PunchingBag bag = PunchingBag.getBag(); + + final boolean useDebugScreen = true; + + public static void main(String[] args) throws InterruptedException { + new PunchingBagGUI(); + + } + + PunchingBagGUI() throws InterruptedException { + + // System.out.println(AudioSystem.getMixerInfo()[0].getName()); + // System.out.println(AudioSystem.getMixerInfo()[0].getDescription()); + // Mixer mix = AudioSystem.getMixer(AudioSystem.getMixerInfo()[0]); + + bag.connectToArduinos(); + + frame = new JFrame("Punching Bag GUI"); + frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); + + // frame.setSize(600, 600); + frame.setVisible(true); + + frame.addMouseListener(this); + frame.addMouseMotionListener(this); + + bag.addButtonListener(this); + bag.addLEDChangeListener(this); + + JSplitPane bottomTopSplitPane = new JSplitPane( + JSplitPane.VERTICAL_SPLIT); + + JSplitPane centerTopSplitPane = new JSplitPane( + JSplitPane.HORIZONTAL_SPLIT); + + JTabbedPane tabbedPane = new JTabbedPane(); + tabbedPane.addTab("LED Control Panel", null, new LEDControlPanel(), + "Allows control of individual LED's"); + + centerTopSplitPane.setLeftComponent(new PunchingBagSim()); + centerTopSplitPane.setRightComponent(tabbedPane); + + bottomTopSplitPane.setTopComponent(centerTopSplitPane); + bottomTopSplitPane.setBottomComponent(new SerialPanel()); + + frame.add(bottomTopSplitPane, BorderLayout.CENTER); + + // frame.pack(); + } + + void playKey(int key) { + try { + AudioInputStream sound = AudioSystem.getAudioInputStream(keys[key]); + DataLine.Info dataLine = new DataLine.Info(Clip.class, + sound.getFormat()); + Clip clip = (Clip) AudioSystem.getLine(dataLine); + clip.open(sound); + clip.start(); + } catch (LineUnavailableException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (IOException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (UnsupportedAudioFileException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + + class SerialPanel extends JPanel implements ActionListener, + SerialReadListener, SerialWriteListener { + JTextArea buttonIn = new JTextArea(); + JTextArea buttonOut = new JTextArea(); + JTextArea ledIn = new JTextArea(); + JTextArea ledOut = new JTextArea(); + + public SerialPanel() { + JSplitPane splitPane = new JSplitPane(JSplitPane.HORIZONTAL_SPLIT); + JSplitPane buttonSplitPane = new JSplitPane( + JSplitPane.HORIZONTAL_SPLIT); + JSplitPane ledSplitPane = new JSplitPane( + JSplitPane.HORIZONTAL_SPLIT); + /* + * splitPane.setOneTouchExpandable(true); + * buttonSplitPane.setOneTouchExpandable(true); + * ledSplitPane.setOneTouchExpandable(true); + */ + + splitPane.setMinimumSize(new Dimension(200, 50)); + buttonSplitPane.setMinimumSize(new Dimension(100, 50)); + ledSplitPane.setMinimumSize(new Dimension(100, 50)); + + JButton clear = new JButton("Clear"); + clear.addActionListener(this); + + JPanel buttonInPanel = new JPanel(); + JScrollPane areaScrollPane = new JScrollPane(buttonIn); + areaScrollPane + .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS); + areaScrollPane.setPreferredSize(new Dimension(250, 100)); + buttonInPanel.add(areaScrollPane, BorderLayout.CENTER); + clear.setActionCommand("BI"); + buttonInPanel.add(clear, BorderLayout.SOUTH); + buttonInPanel.setBorder(BorderFactory + .createTitledBorder("Serial In - Button Arduino")); + buttonSplitPane.setLeftComponent(buttonInPanel); + + JPanel buttonOutPanel = new JPanel(); + areaScrollPane = new JScrollPane(buttonOut); + areaScrollPane + .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS); + areaScrollPane.setPreferredSize(new Dimension(250, 100)); + buttonOutPanel.add(areaScrollPane, BorderLayout.CENTER); + clear = new JButton("Clear"); + clear.setActionCommand("BO"); + buttonOutPanel.add(clear, BorderLayout.SOUTH); + buttonOutPanel.setBorder(BorderFactory + .createTitledBorder("Serial Out - Button Arduino")); + buttonSplitPane.setRightComponent(buttonOutPanel); + + JPanel ledInPanel = new JPanel(); + areaScrollPane = new JScrollPane(ledIn); + areaScrollPane + .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS); + areaScrollPane.setPreferredSize(new Dimension(250, 100)); + ledInPanel.add(areaScrollPane, BorderLayout.CENTER); + clear = new JButton("Clear"); + clear.setActionCommand("LI"); + ledInPanel.add(clear, BorderLayout.SOUTH); + ledInPanel.setBorder(BorderFactory + .createTitledBorder("Serial In - LED Arduino")); + ledSplitPane.setLeftComponent(ledInPanel); + + JPanel ledOutPanel = new JPanel(); + areaScrollPane = new JScrollPane(ledOut); + areaScrollPane + .setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_ALWAYS); + areaScrollPane.setPreferredSize(new Dimension(250, 100)); + ledOutPanel.add(areaScrollPane, BorderLayout.CENTER); + clear = new JButton("Clear"); + clear.setActionCommand("LO"); + ledOutPanel.add(clear, BorderLayout.SOUTH); + ledOutPanel.setBorder(BorderFactory + .createTitledBorder("Serial Out - LED Arduino")); + ledSplitPane.setRightComponent(ledOutPanel); + + splitPane.setLeftComponent(buttonSplitPane); + splitPane.setRightComponent(ledSplitPane); + + this.add(splitPane); + + bag.buttonArduino.addSerialReadListener(this); + bag.buttonArduino.addSerialWriteListener(this); + + } + + @Override + public void actionPerformed(ActionEvent arg0) { + // TODO Auto-generated method stub + + } + + @Override + public void serialWriteEvent(byte b) { + buttonOut.append(String.valueOf((char) b)); + } + + @Override + public void serialWriteEvent(byte[] b) { + buttonOut.append(String.valueOf(b)); + } + + @Override + public void serialReadEvent(int b) { + if (b != -1) + buttonIn.append(String.valueOf((char) b)); + } + } + + class LEDControlPanel extends JPanel implements ActionListener { + String[] colours = { " ", "R", "Y", "G" }; + + public LEDControlPanel() { + this.setLayout(new GridBagLayout()); + + GridBagConstraints c = new GridBagConstraints(); + c.fill = GridBagConstraints.BOTH; + c.anchor = GridBagConstraints.CENTER; + // c.weightx = 0.2; + // c.weighty = 0.2; + + for (int y = 0; y < bag.ledHeight; y++) { + for (int x = 0; x < bag.ledWidth; x++) { + c.gridx = x; + c.gridy = y; + + RYGComboBoxRenderer renderer = new RYGComboBoxRenderer(); + JComboBox rygCombo = new JComboBox(colours); + rygCombo.setSelectedIndex(0); + rygCombo.addActionListener(this); + rygCombo.setActionCommand(String.valueOf(x) + "," + + String.valueOf(y)); + // rygCombo.setRenderer(renderer); + + this.add(rygCombo, c); + } + } + + c.gridx = 0; + c.gridy = 20; + c.fill = GridBagConstraints.HORIZONTAL; + c.anchor = GridBagConstraints.CENTER; + c.gridwidth = 9; + JButton clear = new JButton("Clear"); + clear.setActionCommand("C"); + clear.addActionListener(this); + this.add(clear, c); + } + + public void actionPerformed(ActionEvent a) { + if (a.getActionCommand() == "C") { + bag.clearLEDs(); + } else { + PunchingBag.Colour colour = PunchingBag.Colour.None; + if (((JComboBox) a.getSource()).getSelectedIndex() == 1) { + colour = PunchingBag.Colour.Red; + } else if (((JComboBox) a.getSource()).getSelectedIndex() == 2) { + colour = PunchingBag.Colour.Yellow; + } else if (((JComboBox) a.getSource()).getSelectedIndex() == 3) { + colour = PunchingBag.Colour.Green; + } + System.out.println("Setting " + + a.getActionCommand().split(",")[0] + " " + + a.getActionCommand().split(",")[1]); + bag.setLED(Integer.valueOf(a.getActionCommand().split(",")[0]), + Integer.valueOf(a.getActionCommand().split(",")[1]), + colour); + } + } + + class RYGComboBoxRenderer extends JLabel implements ListCellRenderer { + public RYGComboBoxRenderer() { + super(); + } + + public Component getListCellRendererComponent(JList list, + Object value, int index, boolean isSelected, + boolean cellHasFocus) { + + // Get the selected index. (The index param isn't + // always valid, so just use the value.) + + if (isSelected) { + setBackground(list.getSelectionBackground()); + setForeground(list.getSelectionForeground()); + } else { + setBackground(list.getBackground()); + setForeground(list.getForeground()); + } + + if (index != -1) + setText(colours[index]); + + return this; + } + } + } + + class PunchingBagSim extends JPanel implements ButtonListener, LEDListener, + MouseListener { + int buttonMinSize = 10; + int buttonMaxSize = 50; + + int ledMinSize = 10; + int ledMaxSize = 50; + + int buttonSize = 40; + int ledSize = 8; + + public PunchingBagSim() { + /* + * this.setMinimumSize(new Dimension((bag.buttonWidth * + * buttonMinSize) + (bag.ledWidth * ledMinSize), (bag.buttonHeight * + * buttonMinSize) + (bag.ledHeight * ledMaxSize))); + * this.setMaximumSize(new Dimension((bag.buttonWidth * + * buttonMaxSize) + (bag.ledWidth * ledMaxSize), (bag.buttonHeight * + * buttonMaxSize) + (bag.ledHeight * ledMaxSize))); + */ + bag.addButtonListener(this); + bag.addLEDChangeListener(this); + + this.addMouseListener(this); + + GridBagLayout gbl = new GridBagLayout(); + this.setLayout(gbl); + GridBagConstraints c = new GridBagConstraints(); + + // c.insets = new Insets(1, 1, 1, 1); + c.fill = GridBagConstraints.BOTH; + c.anchor = GridBagConstraints.CENTER; + // c.weightx = 0.2; + // c.weighty = 0.2; + for (int y = 0; y < bag.ledHeight; y++) { + for (int x = 0; x < bag.ledWidth; x++) { + c.gridx = x * 2; + c.gridy = y * 2; + + this.add(new LED(x, y), c); + } + } + + // c.weightx = 0.8; + // c.weighty = 0.8; + for (int y = 0; y < bag.buttonHeight; y++) { + for (int x = 0; x < bag.buttonWidth; x++) { + c.gridx = (x * 2) + 1; + c.gridy = (y * 2) + 1; + + this.add(new Button(x, y), c); + } + } + + // this.setMinimumSize(new Dimension(500,500)); + // this.setPreferredSize(new Dimension(500,500)); + + // this.setBackground(Color.BLUE); + + frame.pack(); + frame.setSize(500, 500); + + this.setBorder(BorderFactory.createLineBorder(Color.black)); + } + + /* + * public Dimension getPreferredSize() { if () return new + * Dimension(super.,10); } + */ + + class LED extends JComponent implements LEDListener { + final int x; + final int y; + + public LED(int x, int y) { + this.x = x; + this.y = y; + /* + * this.setMinimumSize(new Dimension(50,50)); this.setSize(50, + * 50); this.setPreferredSize(new Dimension(50,50)); + */ + bag.addLEDChangeListener(this); + + } + + public Dimension getPreferredSize() { + return new Dimension(5, 5); + } + + public void paintComponent(Graphics g) { + if (bag.getLED(x, y) == PunchingBag.Colour.Red) { + g.setColor(Color.red); + } else if (bag.getLED(x, y) == PunchingBag.Colour.Green) { + g.setColor(Color.green); + } else if (bag.getLED(x, y) == PunchingBag.Colour.Yellow) { + g.setColor(Color.yellow); + } else { + g.setColor(Color.white); + } + + g.fillOval(0, 0, this.getWidth(), this.getHeight()); + } + + @Override + public void LEDchanged() { + this.repaint(); + } + + } + + class Button extends JComponent implements MouseListener { + final int x; + final int y; + + public Button(int x, int y) { + this.x = x; + this.y = y; + setBorder(BorderFactory.createLineBorder(Color.black)); + this.addMouseListener(this); + } + + public Dimension getPreferredSize() { + return new Dimension(20, 20); + } + + public void paintComponent(Graphics g) { + super.paintComponent(g); + + g.setColor(Color.black); + g.fillRect(0, 0, this.getWidth(), this.getHeight()); + g.setColor(new Color(220, 220, 220)); + g.fillRect(4, 4, this.getWidth() - 8, this.getHeight() - 8); + + } + + public void mouseClicked(MouseEvent arg0) { + } + + public void mouseEntered(MouseEvent arg0) { + } + + public void mouseExited(MouseEvent arg0) { + } + + public void mousePressed(MouseEvent arg0) { + System.out.println("Button Pressed"); + bag.buttonPressed(x, y); + } + + public void mouseReleased(MouseEvent arg0) { + } + + } + + public void buttonPressed(int x, int y) { + this.repaint(); + } + + public void LEDchanged() { + this.repaint(); + + } + + @Override + public void mouseClicked(MouseEvent arg0) { + // TODO Auto-generated method stub + + } + + @Override + public void mouseEntered(MouseEvent arg0) { + // TODO Auto-generated method stub + + } + + @Override + public void mouseExited(MouseEvent arg0) { + // TODO Auto-generated method stub + + } + + @Override + public void mousePressed(MouseEvent me) { + if (currentMode == Mode.Interactive) { + // bag.buttonPressed(me.getX()/(buttonSize+ledSize), + // me.getY()/(buttonSize+ledSize)); + } + } + + @Override + public void mouseReleased(MouseEvent arg0) { + // TODO Auto-generated method stub + + } + + @Override + public void contact(Contact c) { + // TODO Auto-generated method stub + + } + } + + public void runInteractively(Contact contact) { + System.out.println("Contact"); + bag.buttonPressed(contact.x, contact.y); + } + + 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 arg0) { + /* + * if (currentMode == Mode.Interactive) { runInteractively(new + * Contact(System.currentTimeMillis(), (arg0 .getX() - 4) / 40, + * (arg0.getY() - 30) / 40, 0)); } + */ + } + + public void mouseReleased(MouseEvent arg0) { + // TODO Auto-generated method stub + + } + + public void mouseDragged(MouseEvent arg0) { + // TODO Auto-generated method stub + + } + + public void mouseMoved(MouseEvent arg0) { + // TODO Auto-generated method stub + + } + + public void contact(Contact c) { + // TODO Auto-generated method stub + + } + + @Override + public void buttonPressed(int x, int y) { + System.out.println("Button Pressed: " + x + " " + y); + // bag.circleExpand(x, y, 16); + // bag.setLED(x, y, PunchingBag.Colour.Red); + // bag.noise(new Rectangle(0, 0, 9, 20), 5000); + /* + * for (int bx=0; bx 520) { + //int laugh = c.force + } + } + + void laugh(int laugh) { + try { + AudioInputStream sound = AudioSystem.getAudioInputStream(laughs[laugh]); + DataLine.Info dataLine = new DataLine.Info(Clip.class, + sound.getFormat()); + Clip clip = (Clip) AudioSystem.getLine(dataLine); + clip.open(sound); + clip.start(); + } catch (LineUnavailableException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (IOException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (UnsupportedAudioFileException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + +} diff --git a/PunchingBag/src/uk/ac/open/punchingbag/examples/SimpleKeyboard.java b/PunchingBag/src/uk/ac/open/punchingbag/examples/SimpleKeyboard.java new file mode 100644 index 0000000..188b262 --- /dev/null +++ b/PunchingBag/src/uk/ac/open/punchingbag/examples/SimpleKeyboard.java @@ -0,0 +1,87 @@ +package uk.ac.open.punchingbag.examples; + +import java.io.File; +import java.io.IOException; + +import javax.sound.sampled.AudioInputStream; +import javax.sound.sampled.AudioSystem; +import javax.sound.sampled.Clip; +import javax.sound.sampled.DataLine; +import javax.sound.sampled.LineUnavailableException; +import javax.sound.sampled.UnsupportedAudioFileException; + +import uk.ac.open.punchingbag.ButtonListener; +import uk.ac.open.punchingbag.Contact; +import uk.ac.open.punchingbag.PunchingBag; + +public class SimpleKeyboard implements ButtonListener { + + String soundDir = System.getProperty("user.dir") + + System.getProperty("file.separator"); + + File[] keys = { new File(soundDir + "G4.wav"), + new File(soundDir + "C5.wav"), new File(soundDir + "D5.wav"), + new File(soundDir + "E5.wav"), new File(soundDir + "F5.wav"), + new File(soundDir + "G5.wav") }; + + static PunchingBag bag = PunchingBag.getBag(); + + public static void main(String[] args) { + new SimpleKeyboard(); + } + + SimpleKeyboard() { + bag.addButtonListener(this); + bag.connectToArduinos(); + } + + public void buttonPressed(int x, int y) { + if (y < 3) { + bag.fillRect(0, 0, 9, 4, PunchingBag.Colour.Red, 500); + playKey(5); + } else if (y < 6) { + bag.fillRect(0, 3, 9, 4, PunchingBag.Colour.Red, 500); + playKey(4); + } else if (y < 9) { + bag.fillRect(0, 6, 9, 4, PunchingBag.Colour.Red, 500); + playKey(3); + } else if (y < 12) { + bag.fillRect(0, 9, 9, 4, PunchingBag.Colour.Red, 500); + playKey(2); + } else if (y < 15) { + bag.fillRect(0, 12, 9, 4, PunchingBag.Colour.Red, 500); + playKey(1); + } else { + bag.fillRect(0, 15, 9, 4, PunchingBag.Colour.Red, 500); + playKey(0); + } + } + + void playKey(int key) { + try { + AudioInputStream sound = AudioSystem.getAudioInputStream(keys[key]); + DataLine.Info dataLine = new DataLine.Info(Clip.class, + sound.getFormat()); + Clip clip = (Clip) AudioSystem.getLine(dataLine); + clip.open(sound); + clip.start(); + } catch (LineUnavailableException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (IOException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (UnsupportedAudioFileException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + + @Override + public void contact(Contact c) { + // TODO Auto-generated method stub + + } + + +} -- cgit v1.2.3