/* * Water - a thread that moves and updates the water * * by Adam Doppelt * http://www.cs.brown.edu/people/amd/ */ import java.awt.*; public class Water extends Thread { final static Color START_COLOR = Color.white; final static int BEHIND_SLEEP = 50; Color color_; int row_, col_; int x1_, y1_, x2_, y2_; boolean lastR_, lastG_, lastB_; int delay_; Board board_; boolean visible_; int slice_, direction_; Piece piece_; public Water(Board board, Piece piece, int row, int col) { board_ = board; row_ = row; col_ = col; piece_ = piece; slice_ = 0; color_ = START_COLOR; visible_ = true; lastR_ = false; lastG_ = false; lastB_ = false; direction_ = Piece.EAST; piece_.WaterEnters(this); delay_ = Score.GetWaterDelay(); start(); } public boolean Advance() { if (slice_ == Piece.SLICES) return MoveToNextPiece(); else { piece_.AdjustWater(this, slice_); board_.DrawWater(this); ++slice_; piece_.AdjustWater(this, slice_); board_.DrawWater(this); ++slice_; piece_.AdjustWater(this, slice_); board_.DrawWater(this); ++slice_; piece_.AdjustWater(this, slice_); board_.DrawWater(this); ++slice_; piece_.AdjustWater(this, slice_); board_.DrawWater(this); ++slice_; piece_.AdjustWater(this, slice_); board_.DrawWater(this); ++slice_; piece_.AdjustWater(this, slice_); board_.DrawWater(this); ++slice_; piece_.AdjustWater(this, slice_); board_.DrawWater(this); ++slice_; piece_.AdjustWater(this, slice_); ++slice_; piece_.AdjustWater(this, slice_); ++slice_; return true; } } public int GetDirection() { return direction_; } public void SetDirection(int direction) { direction_ = direction; } public void SetVisible(boolean visible) { visible_ = visible; } public void SetColor(boolean r, boolean g, boolean b, double percent) { double newR, newG, newB; if (r) newR = lastR_ ? (1.0 - percent) : percent; else newR = lastR_ ? 1.0 : 0.0; if (g) newG = lastG_ ? (1.0 - percent) : percent; else newG = lastG_ ? 1.0 : 0.0; if (b) newB = lastB_ ? (1.0 - percent) : percent; else newB = lastB_ ? 1.0 : 0.0; color_ = new Color((float)newR, (float)newG, (float)newB); } public void SetTileOffset(int x1, int y1, int x2, int y2) { x1_ = col_ * (Piece.SIZE + 1) + x1 + 1; x2_ = col_ * (Piece.SIZE + 1) + x2 + 1; y1_ = row_ * (Piece.SIZE + 1) + y1 + 1; y2_ = row_ * (Piece.SIZE + 1) + y2 + 1; } private boolean MoveToNextPiece() { switch (direction_) { case Piece.NORTH: row_--; break; case Piece.SOUTH: row_++; break; case Piece.EAST: col_++; break; case Piece.WEST: col_--; break; } piece_ = board_.PieceAt(row_, col_); if (piece_ != null) { if (piece_.IsDirectionLegal(direction_)) { slice_ = 0; piece_.WaterEnters(this); lastR_ = color_.getRed() == 255; lastG_ = color_.getGreen() == 255; lastB_ = color_.getBlue() == 255; // HACK! visible_ = false; Score.AnotherPiece(); return true; } else return false; } else return false; } public void Draw(Graphics g) { g.setColor(color_); g.drawLine(x1_, y1_, x2_, y2_); g.setColor(Piece.PIPE_COLOR); g.drawLine(x1_, y1_, x1_, y1_); g.drawLine(x2_, y2_, x2_, y2_); } public synchronized void run() { setPriority(NORM_PRIORITY + 1); long time = System.currentTimeMillis(); while(Advance()) { if (visible_) board_.DrawWater(this); try { time += delay_; long toSleep = time - System.currentTimeMillis(); if (toSleep > 0) sleep(toSleep); else { sleep(BEHIND_SLEEP); time = System.currentTimeMillis(); } } catch (InterruptedException e) { ; } } board_.WaterDied(); } }