Tile Grid Applet

<< Stone Game | FinalProjectsTrailIndex | SpaceInvadersApplet >>

Library

You can make subclasses and override if you add this external library and use

import sfhs.cct.tilegrid.*;

http://www.stfrank.com/tilegrid.jar

Tile.java

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.geom.AffineTransform;
import java.awt.image.BufferedImage;
/**
 * Tile Class for TileGrid, TileGridApplet 
 * @author Chris Thiel
 * @version 25 May 2010 3pm
 *
 */



public class Tile {

	protected int row;
	protected int col;
	protected TileGrid grid;
	protected Color color;
	protected BufferedImage img;
	protected double angle;


	public Tile(int row,int col){
		this.row=row;
		this.col=col;
		this.grid=null;
		this.color=Color.RED;
		img=null;
		angle=0.0;
	}
	public Tile(){
		this(-1, -1);
	}
	public BufferedImage getImg(){
		return img;
	}
	public void setImg(BufferedImage img){
		this.img=img;
	}
	public double getAngle(){
		return angle;
	}
	public void setAngle(double angle){
		this.angle=angle;
	}
	public void turnUp(){
		this.angle=0;
	}
	public void turnDown(){
		this.angle=Math.PI;
	}
	public void turnLeft(){
		this.angle=Math.PI/-2.0;
	}
	public void turnRight(){
		this.angle=Math.PI/2.0;
	}
	public Tile(int row, int col, Color color){
		this(row,col);
		this.color=color;
	}
	public Tile(Color color){
		this(-1,-1);
		this.color=color;
	}
	public Tile(BufferedImage img){
		this(-1,-1);
		this.img=img;
	}
	public int getRow() {
		return row;
	}
	public void setRow(int row){
		this.row=row;
	}
	public int getCol() {
		return col;
	}
	public void setCol(int col) {
		this.col= col;
	}
	public Color getColor(){
		return color;
	}
	public void setColor(Color color){
		this.color=color;
	}
	public void act(){

	}

	public void draw(Graphics g, int x, int y, int size) {
		if(img==null){
			g.setColor(color);
			g.fillOval(x+3, y+3, size-6, size-6);
		}else{
			Graphics2D g2=(Graphics2D)g;
			AffineTransform at=new AffineTransform();
			at.setToIdentity();
			double anchorx=(x+size/2.0);
			double anchory=(y+size/2.0);
			at.rotate(angle, anchorx, anchory);
			double xFactor=(double)size/img.getWidth();
			double yFactor=(double)size/img.getHeight();
			at.scale(xFactor, yFactor);
			at.translate(x/xFactor, y/yFactor);

			g2.drawImage(img, at,null);

		}
	}

	public void setGrid(TileGrid tileGrid) {
		this.grid=tileGrid;

	}
	public TileGrid getGrid(){
		return this.grid;
	}
	public void removeSelfFromGrid(){
		grid.remove(this);
		grid=null;

	}

}

TileGrid.java

import java.awt.Color;
import java.awt.Graphics;
import java.awt.Point;
import java.util.ArrayList;
/**
 * TileGrid for TileGridApplet
 * @author Chris Thiel
 * @version 25 May 2010 3pm
 *
 */

public class TileGrid {
	private int rows;
	private int cols;
	private int x;
	private int y;
	private int size;
	private boolean showLines;
	private ArrayList<Tile> tiles;
	private Tile[][] map;
	private Color bgColor;
	private Color lineColor;

	public TileGrid(int rows, int cols){
		this.rows=rows;
		this.cols=cols;
		this.x=0;
		this.y=0;
		this.size=50;
		this.showLines=true;
		tiles=new ArrayList<Tile>();
		map = new Tile[rows][cols];
		this.bgColor=new Color(244,223,195);
		this.lineColor=new Color(93,66,58);
	}
	public TileGrid(int rows, int cols, boolean s){
		this(rows, cols);
		this.showLines=s;
	}
	public TileGrid(int rows, int cols, int x, int y, int size){
		this(rows, cols);
		this.x=x;
		this.y=y;
		this.size=size;
		this.showLines=true;
	}
	public TileGrid(int rows, int cols, int x, int y, int size,boolean s){
		this(rows,cols);
		this.x=x;
		this.y=y;
		this.size=size;
		this.showLines=s;
	}
	public boolean getShowLines(){
		return showLines;
	}
	public void setShowLines(boolean value){
		this.showLines=value;
	}
	public int getSize(){
		return size;
	}
	public int getNumTiles(){
		return tiles.size();
	}
	public void setSize(int value){
		this.size=value;
	}
	public int getX(){
		return x;
	}
	public int getY(){
		return y;
	}
	public void setX(int x){
		this.x=x;
	}
	public void setY(int y){
		this.y=y;
	}
	public void setLocation(int x, int y){
		this.x=x;
		this.y=y;
	}
	public void setLocation(Point p){
		this.x=p.x;
		this.y=p.y;
	}
	public Point getLocation(){
		return new Point(x,y);
	}
	public void setBGColor(Color c){
		bgColor=c;
	}
	public Color getBGColor(){
		return bgColor;
	}
	/**
	 * Draws grid on Graphics g with top left corner (x,y)
	 * with each cell being size pixels square. It will
	 * update the grid's location and size.
	 * 
	 * @param g the Graphics Object to draw upon
	 * @param x the horizontal location of top left
	 * @param y the vertical location of top left
	 * @param size the size in pixels of each square
	 */
	public void draw(Graphics g, int x, int y, int size){
		this.x=x;
		this.y=y;
		this.size=size;
		Color currentColor=g.getColor();
		g.setColor(bgColor);
		g.fillRect(x, y, cols*size, rows*size);
		for(Tile t:tiles)
			t.draw(g, col2X(t.getCol()), row2Y(t.getRow()),size);
		if (showLines) drawLines(g);
		g.setColor(currentColor);
	}
	private int row2Y(int r) {
		return y+size*r;
	}
	private int col2X(int c) {
		return x+size*c;
	}
	/**
	 * Adds a tile to the grid, telling the tile its new grid, row and column
	 * @param tile
	 * @param row
	 * @param col
	 * @return true if successful, false if occupied or invalid location
	 */
	public boolean add(Tile tile, int row, int col){
		if (!isEmpty(row,col)) return false;
		map[row][col]=tile;
		tiles.add(tile);
		tile.setGrid(this);
		tile.setRow(row);
		tile.setCol(col);
		return true;
	}
	public boolean move(Tile tile, int row, int col){
		if (!isEmpty(row,col)) return false;
		map[row][col]=map[tile.getRow()][tile.getCol()];
		map[tile.getRow()][tile.getCol()]=null;
		tile.setRow(row);
		tile.setCol(col);
		return true;
	}
	/**
	 * Activate tells all the tiles to act
	 * (Usually called after the passage of time).
	 */
	public void activate(){
		int i=0;
		while(i<tiles.size()){
			Tile t=tiles.get(i);
			if (t.getGrid()!=null){//if still alive
				t.act();
				i++;
			}else{
				tiles.remove(t);
			}

		}
	}
	/**
	 * Removes a tile from the grid, setting the tile to a null grid and an invalid location
	 * @param tile
	 * @return
	 */
	public boolean remove(Tile tile){
		int r=tile.getRow();
		int c=tile.getCol();
		//if (isEmpty(r,c))return false;
		map[r][c]=null;
		tiles.remove(tile);
		tile.setRow(-1);
		tile.setCol(-1);
		tile.setGrid(null);
		return true;
	}
	/**
	 * checks to see if row r and column c is on the grid
	 * @param r the row to check
	 * @param c the column to check
	 * @return
	 */
	public boolean isValid(int r, int c) {

		return r>=0 && r<rows && c>=0 && c<cols;
	}
	/**
	 * checks to see if a tile exists in the
	 * row r and column c
	 * @param r
	 * @param c
	 * @return true if it is an empty cell, false if invalid cell or not empty
	 */
	public boolean isEmpty(int r, int c) {
		if (!isValid(r,c))
			return false;
		return map[r][c]==null;
	}
	/**
	 * Uses the (x,y) location of the screen location
	 * to return a string indicating the (row,col) on the grid
	 * that it corresponds to. 
	 * @param x the horizontal location 
	 * @param y the vertical location
	 * @return a String with the corresponding grid location
	 */
	public String getRowColString(int x, int y){
		String result="(";
		result+=getRow(y)+", ";
		result+=getCol(x);
		return result+")";
	}
	/**
	 * Converts a vertical screen location to a grid row
	 * @param y the vertical location in pixels
	 * @return the row of the click
	 */
	public int getRow(int y){
		if (y<this.y) return -1;
		return (y-this.y)/this.size;
	}
	/**
	 * Converts a horizontal screen location to a grid column
	 * @param x the horizontal location in pixels
	 * @return the column of the click
	 */
	public int getCol(int x){
		if (x<this.x)return -1;
		return (x-this.x)/this.size;
	}
	public Point getRowCol(int x, int y){
		return new Point(getRow(y),getCol(x));
	}
	public int getRowFromPoint(Point p){
		return (p.y-this.y)/this.size;
	}
	public int getColFromPoint(Point p){
		return (p.x-this.x)/this.size;
	}


	public Tile get(int row, int col){
		return map[row][col];
	}

	private void drawLines(Graphics g){
		g.setColor(Color.WHITE);
		for (int r=0; r<=rows;r++)
			g.drawLine(x, y+r*size-2, x+cols*size, y+r*size-2);
		for(int c=0; c<=cols; c++)
			g.drawLine(x+c*size-2, y, x+c*size-2, y+rows*size);
		g.setColor(lineColor);
		for (int r=0; r<=rows;r++)
			g.drawLine(x, y+r*size, x+cols*size, y+r*size);
		for(int c=0; c<=cols; c++)
			g.drawLine(x+c*size, y, x+c*size, y+rows*size);

	}
}

TileGridApplet.java

import java.applet.Applet;
import java.awt.Button;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import javax.imageio.ImageIO;
import javax.swing.Timer;
/**
 * TileGridApplet is a simple Applet that 
 * should be reminiscent of GridWorld
 * @author Chris Thiel
 * @version 25 May 2010 9pm
 *
 */


@SuppressWarnings("serial")
public class TileGridApplet extends Applet implements ActionListener, MouseListener, KeyListener 
{
	protected Timer timer;
    protected Image virtualMem;

    protected TileGrid	 grid;

    Button myButton;
    int secs;
	private String message;
	private int keyCode;
	private String key;
    public void init()
    {

        grid= new TileGrid(4, 4 );
        timer=new Timer(1000, this);
        virtualMem = createImage(getWidth(),getHeight());

        myButton= new Button("Start");
        //the class is its own button listener
        myButton.addActionListener (this);
        addMouseListener(this);
        this.addKeyListener(this);
        add(myButton); 
        setMessage("Click Start to begin");
        this.requestFocus();
    }
    public void paint(Graphics g)
    {
        // We draw using the object methods of
        // the graphics buffer, not what is
        // currently on the screen
    	    virtualMem = createImage(getWidth(),getHeight());
        Graphics gBuffer = virtualMem.getGraphics();
        gBuffer.setColor(Color.white);
        gBuffer.fillRect(0,0,getWidth(),getHeight());
        gBuffer.setColor(Color.black);

        grid.draw(gBuffer, getWidth()/6, getHeight()/6, 
        		getWidth()/6);
        gBuffer.drawString("Time: "+getTime(), 20,20);

        gBuffer.drawString(getMessage(), 20, getHeight()-20);

        //Now we send the result to the screen
        g.drawImage(virtualMem,0,0,this);
    }
    public void update(Graphics g)
    {
        paint(g); //get rid of flicker with this method
    }
    public int randInt(int max){
    		return (int)(max*Math.random());
    }
    public boolean isTimerRunning(){
    	     return timer.isRunning();
    }
    public int getTime(){
    		return secs;
    }
    public void setTime(int t){
    		secs=t;
    }
    public void resetTimer(){
    		secs=0;
    		timer.stop();
    }
    public Color randomColor(){
    		int red=randInt(255);
    		int green=randInt(255);
    		int blue=randInt(255);
    		return new Color(red,green,blue);
    }
    public boolean isTimerEvent(ActionEvent e){
    		Object source = e.getSource();
    	    return source == timer;
    }
    //implement the ActionListener
	public void actionPerformed(ActionEvent e) {

        if ( isTimerEvent(e)) {
            setTime(getTime()+1);           
        }else{
            //restart button pressed

              if (isTimerRunning()) {
                  stopTimer();

                  setMessage("Click Start to begin a New Puzzle");
               }else{
                   resetTimer();
                   startTimer();
                   grid= new TileGrid(4, 4 );

                   setMessage("Click Grid to move Tiles");
               }
        }
        this.requestFocus();
        repaint();
	}
	public void startTimer() {
		timer.start();
		myButton.setLabel("Stop");

	}
	public void stopTimer() {
		timer.stop();
		myButton.setLabel("Start");
	}
	public String getMessage(){
		return message;
	}
	public void setMessage(String message){
		this.message=message;
	}
	// implement the MouseListener
	public void mouseClicked(MouseEvent e) {}
	public void mouseEntered(MouseEvent e) {}
	public void mouseExited(MouseEvent e) {}
	public void mousePressed(MouseEvent e) {}
	public void mouseReleased(MouseEvent e) {
		this.requestFocus();
		if (isTimerRunning()){
			int x = e.getX();
			int y = e.getY();
			int r = grid.getRow(y);
			int c = grid.getCol(x);
			setMessage("Clicked "+grid.getRowColString(x, y));
			if (grid.isEmpty(r, c)){
				// img can be any size, place in same folder as class files
				// File f=new File("Ship.gif");
				// BufferedImage img=null;
				// try {
				// 	img = ImageIO.read(f);
				// } catch (IOException err) {
				// 	err.printStackTrace();
				// }
				// Tile t=new Tile(img);
				// or else default is random colored disk
				Tile t=new Tile(randomColor());
				grid.add(t, r, c);
				setMessage(getMessage()+" New Tile Added");
			}else{
				setMessage(getMessage()+" Not a Valid Move");
			}
		}else{
			setMessage("Hummm...Try pressing the Start Button First");
		}
		repaint();
	}
	//KeyListener Methods
	public void keyPressed(KeyEvent e) {
		keyCode=e.getKeyCode();
		key=KeyEvent.getKeyText(keyCode);
		message="You pressed code "+keyCode+" \""+key+"\"";
		repaint();
	}
	public void keyReleased(KeyEvent e) {}
	public void keyTyped(KeyEvent e) {}
}