import edu.neu.ccs.*;
import edu.neu.ccs.gui.*;
import edu.neu.ccs.codec.*;
import edu.neu.ccs.console.*;
import edu.neu.ccs.filter.*;
import edu.neu.ccs.jpf.*;
import edu.neu.ccs.parser.*;
import edu.neu.ccs.pedagogy.*;
import edu.neu.ccs.quick.*;
import edu.neu.ccs.util.*;

import java.awt.*;
import java.awt.event.*;
import java.awt.geom.*;
import java.awt.font.*;
import java.awt.image.*;
import javax.swing.*;
import javax.swing.border.*;
import java.io.*;
import java.util.*;
import java.math.*;
import java.beans.*;
import java.lang.reflect.*;
import java.net.URL;
import java.util.regex.*;
import java.text.ParseException;

public class KeyPlay
    extends DisplayPanel
    implements ConsoleAware
{
    public static int SIZE = 400;
    
    BufferedPanel window = new BufferedPanel(SIZE, SIZE);
    
    PaintableSequence sequence = window.getPaintableSequence();
    
    XRect shape = new XRect(100, 100, 50, 50);
    
    Paintable paintable = new ShapePaintable
        (shape, PaintMode.FILL, Colors.red);
    
    
    // JPT attaches the mouse and key adapters to an inner panel
    // that is obtained by the method call below
    //
    // The inner panel is needed to initialize and reset the key
    // listener
    DisplayPanel inner = window.getInnerPanel();
    
    
    // To activate listening for keys
    // one needs both the key adapter
    // which implements the KeyListener interface
    // and some additional initialization and reset code
    //
    // See the methods initializeKeys() and resetKeyFocus()
    KeyActionAdapter keyadapter = window.getKeyActionAdapter();
    
    
    // The key action object for key pressed events
    KeyAction keyAction = new KeyAction() {
        public void keyActionPerformed(KeyEvent kevt) {
            handleKey(kevt);
        }
    };
    
    
    public KeyPlay() {
        // initializations
        initializeWindow();
        initializeKeys();
        
        // instantiate GUI
        add(window);
        frame("Key Play");
        
        // set focus on the inner panel
        // after the GUI has been instantiated in its frame
        resetKeyFocus();
    }
    
    
    // The key action method for key pressed events
    void handleKey(KeyEvent kevt) {
        // set delta to 10 if the shift key is down
        // otherwise set delta to 1
        int small = 1;
        int large = 10;
        
        int delta = (kevt.isShiftDown()) ? large : small;
        
        // compute x, y shift if the key code is for
        // one of the four keyboard cursor keys
        //
        // this does not work for keypad cursor keys
        int x;
        int y;
        
        switch(kevt.getKeyCode()) {
            case KeyEvent.VK_DOWN:
                x = 0;
                y = delta;
                break;
            
            case KeyEvent.VK_UP:
                x = 0;
                y = -delta;
                break;
                
            case KeyEvent.VK_RIGHT:
                x = delta;
                y = 0;
                break;
                
            case KeyEvent.VK_LEFT:
                x = -delta;
                y = 0;
                break;
                
            default:
                // if not a cursor key
                // do nothing
                return;
        }
        
        // move the paintable and repaint the window
        paintable.move(x, y);
        window.repaint();
    }
    
    
    void initializeWindow() {
        window.drawGrid(50);
        sequence.addPaintable(paintable);
        
        window.repaint();
    }
    
    
    // The method to initialize key listening in the inner panel
    void initializeKeys() {
        // enable the inner panel to gain the focus of attention
        inner.setFocusable(true);
        
        // attach the pressed action object to the key adapter
        keyadapter.addKeyPressedAction(keyAction);
    }
    
    
    // The method to set or reset key listening to the inner panel
    void resetKeyFocus() {
        // reset the focus of attention to the inner panel
        // in case it has been set to some other component
        inner.requestFocusInWindow();
    }
    
    
    public static void main(String[] args) {
        new KeyPlay();
    }
    
}
