⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 hanoi11.java

📁 这是我花好长时间找到的
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
/**********************************************************
   Hanoi11.java - Tower of Hanoi puzzle
                  Version 1.1
   by Bob Kirkland
   bob@mazeworks.com

   1.1 - added Timer, Title bar
         removed CC class
**********************************************************/	
import java.applet.* ;
import java.awt.* ;
import java.net.* ;
import java.util.* ;

/******** HANOI11 ********
   main class: initializes applet panel, starts games,
   runs autosolve thread, handles disc moving events
*/	
public class Hanoi11 extends Applet implements Runnable {
   static final Font titleFont=new Font("Helvetica", Font.BOLD, 12),
                     textFont=new Font("Helvetica", Font.PLAIN, 11),
                     monoFont=new Font("Courier", Font.BOLD, 12) ;
   static final int CANVAS_WIDTH=450, CANVAS_HEIGHT=250, TABLE_TOP=225,
                    PEG1=0, PEG2=1, PEG3=2, MIN_DISCS=3, MAX_DISCS=12 ;
   private boolean gameOver ;
   private int sourceDisc, sourcePeg, targetPeg ;
   private String gameStatus ;
   private Panel cpBack, titlePanel ;
   private Label titleLabel ;
   private Board bd ;
   private BoardCanvas bc ;
   private StatusPanel sp ;
   private ControlPanel cp ;
   private Image boardImage ;
   private String boardImageFile = "board.gif" ;
   private Thread solveThread, timer ;

   public void init() {

      // load board image
      MediaTracker tracker = new MediaTracker(this) ;
      URL url = getCodeBase() ;
      boardImage = getImage(url,boardImageFile) ;
      tracker.addImage(boardImage,0) ;
      try { tracker.waitForID(0); }
      catch (InterruptedException e) {}

      // initialize applet layout
      setBackground(Color.black) ;
      Panel mainPanel = new Panel() ;
      mainPanel.setLayout(new BorderLayout(0,0)) ;
      // BoardCanvas
      bc = new BoardCanvas(this) ;
      bc.resize(CANVAS_WIDTH,CANVAS_HEIGHT) ;
      // Title panel
      titlePanel = new Panel() ;
      titlePanel.setLayout(new GridLayout(1,1)) ;
      titlePanel.setBackground(Color.gray) ;
      titlePanel.setFont(titleFont) ;
      titlePanel.add(titleLabel=new Label("   Tower of Hanoi  1.1",Label.LEFT)) ;
      titleLabel.setForeground(Color.white) ;
      // Control Panel
      cpBack = new Panel() ;
      cpBack.setBackground(Color.gray) ;
      cp = new ControlPanel(this) ;
      cpBack.add(cp) ;
      // Status panel
      sp = new StatusPanel(this) ;
      sp.setBackground(Color.gray) ;
      // construct applet panel
      mainPanel.add("Center",bc) ;
      mainPanel.add("North",titlePanel) ;
      mainPanel.add("East",cpBack) ;
      mainPanel.add("South",sp) ;
      add(mainPanel) ;
      validate() ;

      newGame() ;
   }
   // startup
   void newGame() {
      int discs = cp.getDiscs() ;

      System.gc() ;
      gameOver = false ; 
      bd = new Board(discs,this) ;
      bc.drawBoard(bd,boardImage,0,0,0) ;
      sp.setMoveCount(0) ;
      if (cp.isTimerOn()) timer = new Timer(cp) ;
      else cp.setTimer(" ") ;
      if (solveThread == null)
         sp.setStatus("Move all " + discs + " discs to the rightmost peg.") ;
      bc.requestFocus() ;
   }		
   // handle Reset event
   void restartGame() { 
      stop() ; 
      cp.setAutoSolveEnable(true) ;
      newGame() ;
   }
   // kill all threads
   public void stop() {
      if (solveThread!=null) {
         solveThread.stop() ;
         solveThread = null ;
      }
      if (timer!=null) {
         timer.stop() ;
         timer = null ;
      }
   }
   // spawn Autosolve thread
   public void startSolveThread() {
      stop() ;
      solveThread = new Thread(this) ;
      solveThread.start() ;
   }
   // run Autosolve thread
   public void run() {
      newGame() ;
      sp.setStatus("Autosolving ...") ;
      solve(cp.getDiscs(),PEG1,PEG2,PEG3) ;
      sp.setStatus("Finished!") ;
      gameOver = true ;
      solveThread = null ;
      cp.setAutoSolveEnable(true) ;
   }
   // here's the famous algorithm
   void solve(int discs,int source,int aux,int target) {
      if (discs==0) return ;                      // base to end recursion
      solve(discs-1,source,target,aux) ;          // recursive call #1
      bd.moveDisc(source,target) ;                // move disc
      sp.setMoveCount(bd.getMoveCount()) ;        // update display
      bc.drawBoard(bd,boardImage,0,0,0) ;
      try { solveThread.sleep(cp.getDelay()) ; }  // Autosolve delay
      catch (InterruptedException e) {}
      solve(discs-1,aux,source,target) ;          // recursive call #2
   }
   // handle mouse drag event
   void dragDisc(int x,int y) {
      if (!gameOver&&(sourceDisc!=0)) 
         bc.drawBoard(bd,boardImage,sourceDisc,x,y) ;
   }
   // handle mouse down event
   void selectDisc(int x,int y) {
      if (!gameOver&&(solveThread==null)) {
         if ((timer!=null)&&(!timer.isAlive())) timer.start() ;
         sourcePeg = pixelToPeg(x,y) ;
         if (bd.isStartPeg(sourcePeg)) { 
            sourceDisc = bd.getTopDisc(sourcePeg) ;
            bc.drawBoard(bd,boardImage,sourceDisc,x,y) ; 
         }
      }
   }
   // handle mouse up event
   void dropDisc(int x,int y) {
      if (!gameOver&&(sourceDisc!=0)) {
         targetPeg = pixelToPeg(x,y) ;
         if (bd.moveDisc(sourceDisc,sourcePeg,targetPeg)) {
            gameStatus = bd.getBoardStatus() ;
            sp.setMoveCount(bd.getMoveCount()) ;
            if (gameStatus==null) 
               sp.setStatus("The minimum number of moves required is " + 
                             bd.getMinMoves() + ".") ;
            else {
               gameOver = true ; 									
               stop() ;
               sp.setStatus(gameStatus) ;
            }
         }
         bc.drawBoard(bd,boardImage,0,0,0) ;
         sourceDisc = 0 ;
      }
   }
   // conversion for mouse down/up events
   int pixelToPeg(int x,int y) {
      int peg = -1 ;
      if ((y>40)&&(y<TABLE_TOP)) {
         if ((x>50)&&(x<100)) peg = PEG1 ;
         else if ((x>200)&&(x<250)) peg = PEG2 ;
         else if ((x>350)&&(x<400)) peg = PEG3 ;
      }
      return peg ;
   }
}
/******** TIMER ********
	controls Timer thread
*/	
final class Timer extends Thread {
   static final int ONE_SECOND=1000 ;
   private long startTime, rem ;
   private int hours, min, sec ;
   private String sMin, sSec, sTime ;
   private ControlPanel cp ;

   // constructor
   Timer(ControlPanel cp) {
      this.cp = cp ;
      cp.setTimer(setTime(0)) ;
   }
   // run thread
   public void run() {
      startTime = System.currentTimeMillis() ;
      while (true) {
         try { Thread.sleep(ONE_SECOND) ; } 
         catch (InterruptedException e) {}
         cp.setTimer(setTime(System.currentTimeMillis() - startTime)) ;
      }
   }
   // return h:mm:ss string from milliseconds
   String setTime(long millisec) { 
      hours = (int)(millisec/3600000) ;
      rem = millisec - (hours*3600000) ;
      min = (int)(rem/60000) ;
      rem = rem - (min*60000) ;
      sec = (int)(rem/1000) ;      

      sMin = Integer.toString(min) ;
      if (sMin.length()==1) sMin = "0" + sMin ;
      sSec = Integer.toString(sec) ;
      if (sSec.length()==1) sSec = "0" + sSec ;
      sTime = "  " + Integer.toString(hours) + ":" + sMin + ":" + sSec ;
      return sTime ;
   }
}			
/******** BOARD ********
   controls disc positions, rules for moving discs
*/   
final class Board {
   static final int PEGS=3, 
                    DISC_SIZES[][]={ {68,18},{76,16},{84,14},{92,13},{100,12},
                                     {108,12},{112,11},{116,10},{120,9},{124,9} } ;
   private int peg[][], pegTop[]=new int[PEGS], discWidth[] ;
   private int discs, moveCount, minMoves ;
   private Hanoi11 main ;

   // constructor
   Board(int discs,Hanoi11 main) {
      this.discs = discs ;
      this.main = main ;
      peg = new int[discs][PEGS] ;
      // put all the disks on the first peg
      for (int i=0; i<discs; i++) peg[i][main.PEG1] = discs-i ;
      pegTop[main.PEG1] = discs-1 ;
      for (int i=1; i<PEGS; i++) pegTop[i] = -1 ;
      // calculate disc widths
      discWidth = new int[discs] ;
      for (int i=discs-1; i>=0; i--) 
         discWidth[i] = DISC_SIZES[discs-main.MIN_DISCS][0] - 
                        (DISC_SIZES[discs-main.MIN_DISCS][1] * 
                        (discs-1-i)) ;
      moveCount = 0 ;
      // minimum moves is (2**discs)-1
      minMoves = ((int)Math.pow(2.0,discs)) - 1 ;
   }

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -