This puzzle game is to help students do, or is very good, the implementation of features include: automatic selection of pictures, automatic arbitrary cutting pictures, and ensure that the generation of a certain solution, there is a countdown function.
Also wrote that Dijkstra demonstration, after two days to send up, after all to test (preview ...) )
First of all, how to ensure that there are solutions, two methods: 1, first cut and then their own background let the space to move randomly.
2, generate a full array, and then determine if there is a solution:
Whether a n*m digital solution exists The following conclusions: 1. If M is an odd number, then move up or down, move left and right will not change the sequence of the reverse value of the parity, so if begin to end two states of the reverse value of the parity of the same solution! 2. If M is even, moving left and right does not change the parity of the sequence's inverse value, moving up and down one time to change the parity once, so if the begin space of the number of lines I and the end of the space of the number of lines J of the difference between the absolute value of the inverse of begin and end is the same as the parity. 3. No solution for other situations!
This actually do POJ that 8 digital problem should be mentioned, so I first think of is the second way of thinking, the first is to listen to classmates do, feel more convenient.
Automatic selection of the picture is simple, set a jfilechooser can, progress bar with JProgressBar The difficulty is that this progress bar of the thread to be associated with the game, I am by the value of its static member variable implementation.
Automatically cut the picture is Google to a string of code (seemingly the second is, but it is saved into a photo, I this directly saved as Imagecon can, slightly modified under.
Puzzle class
public class Puzzle extends JFrame implements Actionlistener{game g;private JButton jb,jb2,jb3;//start the game in turn, show the correct picture private JTextField jt,jt2;//the number of rows and columns read into the cut JProgressBar progressbar;//progress bar Progress p; String file;public Puzzle () {settitle ("my Jigsaw");//Application title setlayout (null); SetBounds (0,0,900,700);//The range of the puzzle program g= new Game (); /If you choose a picture later from the main interface to choose a good URL to pass the URL (game has multiple constructors) g.setbounds (0,0,600,600); Container Container=getcontentpane (); JB = new JButton ("Start Game"); Jb.setbounds (650,50,200,100); Jb.addactionlistener (this); JB2 = new JButton ("show correct picture"); Jb2.setbounds (650,175,200,100); Jb2.addactionlistener (this); Jb3=new JButton ("select Picture"); Jb3.setbounds (650,300,200,100); Jb3.addactionlistener (this); JLabel jl= New JLabel ("Horizontal cut quantity"); Jl.setbounds (650,400,200,50); Container.add (JL); Jt=new JTextField (""); Jt.setbounds (650,450,200,50); JLabel jl2=new JLabel ("Longitudinal cut quantity"); Jl2.setbounds (650,500,200,50); Container.add (JL2); Jt2=new JTextField (""); Jt2.setbounds (650,550,200,50); ProgressBar =new JProgressBar (); Progressbar.setbounds (0,600,800,75); Progressbar.setminimum (0); Progressbar.setmaximum (100); Progressbar.setvalue (0); Progressbar.setbackground (Color.Blue); Progressbar.setborderpainted (TRUE); Container.add (ProgressBar); Container.add (JT); Container.add (JT2); Container.add (JB); Container.add (JB2); Container.add (JB3); Container.add (g); Container.setbackground (Color.White); SetVisible (TRUE); Setdefaultcloseoperation (Jframe.exit_on_close); } public void actionperformed (ActionEvent e) {int n,m; if (E.getsource () ==JB) {//If it is the start game (get n rows, m column) String S1=jt.gettext (); String S2=jt2.gettext (), if (S1.matches ("\\d+") &&s2.matches ("\\d+"))//If it is an integer {n=integer.parseint (S1); m= Integer.parseint (S2);//system.out.println (s1+ "" +s2);//new picturecut (N,m); if (file==null) new Alert4 (); else{ G.start (n,m,file);//incoming n rows, m column if (p==null)//Only once {p=new Progress (ProgressBar);p. Start ();} else//If the front-line has been opened {if ((progress.value>=100) | | | (ProGRESS.VALUE<0)//If the previous thread ran out {progressbar.setvalue (0); progress.value=0; }else//system.out.println ("new P");//close the thread before opening a new thread, do not open a new thread, use the previous one directly, but modify the value inside. {progressbar.setvalue (0); progress.value=0;}}}} Elsenew Alert3 (); } if (E.getsource () ==jb2) {//If the picture is displayed G. Display (file); } if (E.getsource () ==jb3) {JFileChooser filechooser; {filechooser =new jfilechooser (); FileFilter Filter =new filenameextensionfilter ("Image file (only PNG or jpg)", "JPG", "PNG"); Filechooser.setfilefilter (filter); } int I=filechooser.showopendialog (Getcontentpane ()); if (i==jfilechooser.approve_option) {File selectedfile=filechooser.getselectedfile (); file= Selectedfile.getabsolutepath (); System.out.println (file); G.redraw (file); Progressbar.setvalue (0); progress.value=-10000; }}}public static void Main (String []args) {new Firstapplet (); new puzzle ();}} Class Progress extends thread{static int value=0;private jprogressbar progressbar;public Progress (jprogressbar ProgressBar) {This.progressbar=progressbar;} PuBlic void Run () {while (value<=100) {try{thread.sleep (1000);} catch (Interruptedexception e) {e.printstacktrace ();} Value++;if (value==100) {new Alert2 ();} Progressbar.setindeterminate (False);p Rogressbar.setvalue (value);}}
Game class
Package Puzzle;import Java.awt.button;import java.awt.color;import java.awt.container;import java.awt.Graphics; Import Java.awt.image;import Java.awt.toolkit;import Java.awt.event.actionevent;import Java.awt.event.actionlistener;import Java.awt.event.mouseevent;import Java.awt.event.mouselistener;import Java.awt.image.bufferedimage;import Java.awt.image.cropimagefilter;import Java.awt.image.FilteredImageSource; Import Java.awt.image.imagefilter;import java.io.file;import javax.imageio.imageio;import Javax.swing.ImageIcon; Import Javax.swing.jdialog;import Javax.swing.jlabel;import Javax.swing.jpanel;public class Game extends JPanel Implements mouselistener{//create start to put a picture, and upset, click to start the game time and display pictures, when running to the final result when the exit path private ImageIcon imagecon;private ImageIcon [] Oid The Thread Runner;boolean ok=false;int time;//judgment is the number of calls to the repaint function int []a;//array that stores the first-I position with the first few cut pictures if 9 is an empty picture. int CurrentX ,///current empty ordinate int currenty;//is currently empty, the coordinate int number;//is currently the first position of the empty int n;//n row int m;//m column public Game () {imagecon=new ImageIcon (". /picture/bG2.png ");//record full picture time=1; Repaint ();} public void init (int n,int m) {//Initialize picture Position information (12 of 9 pictures in 1~9 location), to ensure that the reverse pair is even (note that the computer N rows m column is upside down) int Flag,c;boolean f=true;pi= New Imageicon[n*m+1];while (f)//if M is odd, then the reverse pair is even feasible, if even, the difference between the number of spaces and the inverse of the difference parity is the same as {System.out.println ("n is" +n+ "M" +m); for ( int i=1;i<=n*m;i++) {a[i]= (int) (1+math.random () * (n*m-1+1));//random a 1 to n*m number flag=1;for (int j=1;j<i;j++) if (a[i]= =A[J])//Flag=0;if (flag==0)//If not in line with i--;} int sum=0;//calculates the reverse order of number=0;for (int i=1;i<=n*m;i++) {if (a[i]==n*m) {number=i;//record is the number of empty continue;} for (int j=1;j <i;j++) {if (j==number) continue; if (a[j]>a[i]) sum++;}} System.out.println (sum), if ((sum%2==0) && (m%2==1))//If it is an odd-numbered solution F=false;else if ((m%2==0) && (N-(number-1 )/m-1)%2==sum%2)//If it is an even f=false; for (c=1;c<=n;c++)//cannot be the same if (a[c]!=c) break; if (c==n+1) f=true;} for (int i=1;i<=n*m;i++) System.out.println (A[i]);} @Override public void Paint (Graphics g) {if (time==1) {Image r=imagecon.getimage (); G.drawimage (r,0,0,600,600,this);//Draw the original full pattern} else if (!isfinish ()) {g.clearrect (0,0,600,600); for (int i=1;i<=n*m;i++) {if (a[i]!=n*m) {int temp=a[i];//I-position is the first a[i] block picture image R=pi[temp].getimag E (); G.drawimage (R, (i-1)%m* (600/m), (i-1)/m* (600/n), 600/m,600/n,this);} else {currentx= (i-1)%m* (600/m); Currenty= (i-1)/m* (600/n);//The vertical upper-left coordinate of the space G.clearrect ((i-1)%m* (600/m), (i-1)/m* (600/n), 600/m,600/n);//Set 9th space}}} El se{G.clearrect (0,0,600,600); for (int i=1;i<=n*m;i++)//All output {Image r=pi[i].getimage (); G.drawimage (R, (i-1)%m* (600 /m), (i-1)/m* (600/n), 600/m,600/n,this); } progress.value=-10000;//game end to set the progress bar to negative new alert (); }} public void start (int n,int m,string file)//incoming m row n column, starting to cut graph {this.n=n; This.m=m; A=new int[n*m+1];//n row M-column init (N,M); String Srcimagefile=file; int cols,rows; Cols=m; Rows=n; progress.value=0; if (time==1) time=2; try{//Read source image bufferedimage bi = imageio.read (new File (Srcimagefile)); Source Graph width int srcwidth = Bi.getwidth (); SOURCE graph height int srcheight = bi.getheight (); if (cols >= 1 && rows >=1) {image image = Bi.getscaledinstance (Srcwidth, Srcheight, Image.sca Le_default); Slice landscape quantity//slice longitudinal quantity//calculate the horizontal and vertical number of slices double destwidth = srcwidth/cols; Double destheight = srcheight/rows; Image img; ImageFilter Cropfilter; Loop builds a slice for (int i = 0; i < rows; i++) {for (int j = 0; J < cols; J + +) { The four parameters are the image start coordinate and the width height cropfilter = new CropImageFilter ((int) (J * destwidth), (int) (I * Destheight), (int) ((j+1) * destwidth), (int) ((i+1) * destheight)); img = Toolkit.getdefaulttoolkit (). CreateImage (New FilteredImageSource (Image.getsou RcE (), cropfilter)); BufferedImage tag = new BufferedImage ((int) destwidth, (int) destheight, bufferedimage.type_i NT_RGB); Graphics g = tag.getgraphics (); G.drawimage (IMG, 0, 0, NULL); Draw the reduced figure g.dispose (); int c=j+1+i*cols; Pi[c]=new ImageIcon (tag); }}}}catch (Exception e) {e.printstacktrace (); } this.addmouselistener (this); Repaint ();} public Boolean isfinish () {//description has completed for (int i=1;i<=n*m;i++) {if (a[i]!=i) return false;} return true;} @Override public void mousepressed (MouseEvent e) {int tempx,tempy; System.out.println ("mouse Touch"); Tempx=e.getx ();//Current Location tempy=e.gety ();//System.out.println (TEMPX); System.out.println (Tempy); System.out.println ("The original length is:" +currentx+ "original height:" +currenty); if (TEMpx-currentx>=0) && (tempx-currentx<=600/m) && (currenty-tempy<=600/n) && ( currenty-tempy>=0) {//If you click the button at the top of the current int temp=a[number];//to swap your own picture a[number]=a[number-m];a[number-m]=temp; number=number-m;//Update current Location currentx=tempx/(600/m) * (600/m);//The first few lines currenty=tempy/(600/n) * (600/n);// The first few columns of System.out.println ("+currentx+" to the Top "+currenty"); } else if ((currentx-tempx>=0) && (currentx-tempx<=600/m) && (tempy-currenty>=0) && ( tempy-currenty<=600/n) {//If the button is clicked at the current left int temp=a[number]; a[number]=a[number-1]; a[number-1]=temp; number= Number-1; currentx=tempx/(600/m) * (600/m); currenty=tempy/(600/n) * (600/n); System.out.println ("To the Left" +currentx+ "" +currenty);} else if ((tempx-currentx<=2* (600/m)) && (tempx-currentx>=600/m) && (tempy-currenty>=0) & & (tempy-currenty<=600/n)) {//If the button is clicked on the current right int temp=a[number]; a[number]=a[number+1]; a[number+1]=temp; number =number+1; currentx=tempx/(600/m) * (600/m); currenty=tempy/(600/n) * (600/n); System.out.println ("To the right" +currentx+ "" +currenty);} else if ((tempy-currenty>=600/n) && (tempy-currenty<=2* (600/n)) && (tempx-currentx>=0) & & (tempx-currentx<=600/m)) {//If the button is clicked at the bottom of the current int temp=a[number]; a[number]=a[number+m]; a[number+m]=temp; =number+m; currentx=tempx/(600/m) * (600/m); currenty=tempy/(600/n) * (600/n); System.out.println ("+currentx+" to "+currenty"); Repaint ();//As to the last redraw at each time} @Overridepublic void mouseclicked (MouseEvent e) {//TODO auto-generated method stub} @Ove rridepublic void mouseentered (MouseEvent e) {//TODO auto-generated method stub} @Overridepublic void Mouseexited ( MouseEvent e) {//Todo auto-generated method stub} @Overridepublic void Mousereleased (MouseEvent e) {//Todo auto-generated Method Stub}public void Display (string file) {string s=file;new display (s);} public void Redraw (String s) {imagecon=new ImageIcon (s);//Record full picture Time=1;repaint ();} public class display extends jdialog{//display picture Congra jp;public display (STring s) {settitle ("Display Picture"); setlayout (null); SetBounds (400,300,300,300); Container Container=getcontentpane (); JLabel jl= New JLabel ("original picture"); Jl.setbounds (50,50,300,200); Container.add (JL); Container.setbackground (color.white); jp=new Congra (s); Jp.setbounds (0,0,250,250); Container.add (JP); SetVisible (True);}} public class Alert extends JDialog {imageicon li;public alert () {win g=new win (), G.setbounds (0,0,400,400); Settitle ("You Win! "); SetLayout (null); SetBounds (400,300,450,400); Container Container=getcontentpane (); Container.add (g); Container.setbackground (Color.White); SetVisible (TRUE); }} public class win extends jpanel{ImageIcon Li; Public win () {li=new ImageIcon ("./picture/you win.png"); Repaint (); } public void Paint (Graphics g) {Image r=li.getimage (); G.drawimage (R,0,0,400,400,this); } }}
The main is the two, then next is to play the window first (so-called robustness?). )
Alert2 class
public class Alert2 extends JDialog {public alert2 () {Settitle ("Game Over!"); SetLayout (null); SetBounds (400,300,450,400); Container Container=getcontentpane (); Container.setbackground (Color.White); JLabel jl= New JLabel ("Time to, Game over!"); Jl.setbounds (50,50,200,100); Container.add (JL); SetVisible (True);} }
Alert3 class
public class Alert3 extends JDialog {public alert3 () {Settitle ("note"); setlayout (null); SetBounds (400,300,300,200); Container Container=getcontentpane (); Container.setbackground (Color.White); JLabel jl= New JLabel ("Please enter the correct number of transverse longitudinal cuts!"); Jl.setbounds (50,50,200,100); Container.add (JL); SetVisible (True);} }
Alert4 class
public class Alert4 extends JDialog {public alert4 () {settitle ("Note!"); SetLayout (null); SetBounds (400,300,300,200); Container Container=getcontentpane (); Container.setbackground (Color.White); JLabel jl= New JLabel ("Please select Image First"); Jl.setbounds (50,50,200,100); Container.add (JL); SetVisible (True);} }
Java Big job puzzle game