📄 sudokume.java
字号:
// FIX : dropping though means the display gets changed
// and the _saveGame() alert screen is never shown.
case 402 : // Just quit
mode=MENU;
display.setCurrent(new GameSelection(display,SudokuME.this));
break;
case 500 : // Display about image
new AboutDisplay(this);
break;
case 600 : // Recreate working values and then set working lock
game.createWorking();
for(int x=0;x<game.gridSz;x++) {
for(int y=0;y<game.gridSz;y++) {
if(game.working[x][y]>0) {
game.working[x][y] |= 1 << game.gridSz;
}
}
}
break;
case 601 : // Remove working for locked cells with numbers
for(int x=0;x<game.gridSz;x++) {
for(int y=0;y<game.gridSz;y++) {
if(game.grid[x][y]>0 && game.locked[x][y]) {
game.working[x][y]=0;
}
}
}
break;
case 602 : // Remove working for cells with numbers
for(int x=0;x<game.gridSz;x++) {
for(int y=0;y<game.gridSz;y++) {
if(game.grid[x][y]>0) {
game.working[x][y]=0;
}
}
}
break;
case 603 : // Remove working for all cells
for(int x=0;x<game.gridSz;x++) {
for(int y=0;y<game.gridSz;y++) {
game.working[x][y]=0;
}
}
break;
case 700 : // Check grid for complete solution
if (game.findAllCollisions()) {
// Something missing
alert = new Alert("Sorry.", "Some cells are empty or wrong",null,AlertType.INFO);
} else {
// Congratulations - the game is complete!
alert = new Alert("Congratulations!", "Puzzle Completed",null,AlertType.INFO);
}
alert.setTimeout(3000);
display.setCurrent(alert,this);
break;
case 701 : // Is the grid solvable?
tempGrid = new byte[game.gridSz][game.gridSz];
for (int x=0;x<game.gridSz; x++) {
for (int y=0;y<game.gridSz;y++) {
tempGrid[x][y] = game.grid[x][y];
}
}
i = game.solve(tempGrid);
if (i == 1) {
alert= new Alert("Solvable!","This grid has a valid solution",null,AlertType.INFO);
} else if (i >= game.DEFAULT_MAX_SOLUTIONS) {
alert= new Alert("Solvable!","This grid has MULTIPLE (>"+(i-1)+") valid solution",null,AlertType.INFO);
} else if (i > 1) {
alert= new Alert("Solvable!","This grid has MULTIPLE ("+i+") valid solution",null,AlertType.INFO);
} else {
alert= new Alert("Not Solvable","No solution found for this grid - is there a mistake somewhere?",null,AlertType.WARNING);
}
alert.setTimeout(3000);
display.setCurrent(alert,this);
break;
case 702 : // solve grid
game.solve(game.grid, 1);
break;
case 703 : // provide a hint (solve the grid and then pick 1 improvement and insert it, place the cursor there)
tempGrid = new byte[game.gridSz][game.gridSz];
for (int x=0;x<game.gridSz; x++) {
for (int y=0;y<game.gridSz;y++) {
tempGrid[x][y] = game.grid[x][y];
}
}
if (game.solve(tempGrid,1) > 0) {
boolean foundDifference=false;
Random source=new Random();
int startX = source.nextInt()%game.gridSz;
if (startX < 0) startX = -startX;
int startY = source.nextInt()%game.gridSz;
if (startY < 0) startY = -startY;
//System.out.println("in hint: startX="+startX+",startY="+startY);
for (int x=0;x<game.gridSz && !foundDifference; x++) {
for (int y=0;y<game.gridSz && !foundDifference;y++) {
int nx = (x+startX)%game.gridSz;
int ny = (y+startY)%game.gridSz;
//System.out.println("in hint: nx="+nx+", ny="+ny);
//System.out.println("in hint: tempgrid="+tempGrid[nx][ny]+",gamegrid="+game.grid[nx][ny]);
if (tempGrid [nx][ny] != game.grid[nx][ny] ) {
int cx=cursorX , cy=cursorY;
cursorX = nx;
cursorY = ny;
undoUpdate(cx,cy);
keyNumPressed(tempGrid[nx][ny]);
game.working[nx][ny] = 0;
foundDifference = true;
}
}
}
if (foundDifference) {
break;
}
// no difference found - was the grid already solved?
alert= new Alert("Solved?","No difference found between solved grid and your grid",null,AlertType.ERROR);
} else {
alert= new Alert("Not Solvable","No solution found for this grid - is there a mistake somewhere?",null,AlertType.WARNING);
}
alert.setTimeout(3000);
display.setCurrent(alert,this);
break;
case 704 : // Fix errors copy the grid, remove all unlocked cells, solve it and then compare copy with solution. fix errors
tempGrid = new byte[game.gridSz][game.gridSz];
for (int x=0;x<game.gridSz; x++) {
for (int y=0;y<game.gridSz;y++) {
if (game.locked[x][y]) {
tempGrid[x][y] = game.grid[x][y];
} else {
tempGrid[x][y] = 0;
}
}
}
i = game.solve(tempGrid);
if (i == 1) {
int numErrors=0;
for (int x=0;x<game.gridSz; x++) {
for (int y=0;y<game.gridSz;y++) {
if ((game.grid[x][y] != 0) && (tempGrid[x][y] != game.grid[x][y])) {
game.grid[x][y] = 0;
numErrors++;
}
}
}
if (numErrors > 0) {
alert= new Alert("Fixed","Fixed "+numErrors+" errors in your grid",null,AlertType.WARNING);
} else {
alert= new Alert("No Errors","No mistakes found - you are going well",null,AlertType.INFO);
}
} else if (i == 0) {
alert= new Alert("No Solution","No solution found based only on locked cells - unlock some cells until this becomes solvable",null,AlertType.INFO);
} else {
alert= new Alert("Multiple Solutions","This puzzle has multiple solutions when calculated from locked cells! - lock more cells",null,AlertType.INFO);
}
alert.setTimeout(3000);
display.setCurrent(alert,this);
break;
case 800 : // Undo
undoRestore();
break;
case 900: // Autowork
programmedKeyCodes.autoWorking = !programmedKeyCodes.autoWorking;
break;
case 901: // InCell Work
programmedKeyCodes.workingInCell = !programmedKeyCodes.workingInCell;
break;
case 902: // Blank Work
programmedKeyCodes.blankWorking = !programmedKeyCodes.blankWorking;
break;
}
// -----Don't restart timer if we're departed for the about screen.
if(idCode!=500) startTimer();
}
private void _saveGame()
{ Alert alert;
game.timer=(int)(getTimer()/1000); // Number of seconds playing time
if(game.save()) {
alert = new Alert("Save Game","Your game has been saved.",null,AlertType.CONFIRMATION);
alert.setTimeout(3000);
} else {
alert= new Alert("Save Game","FAILED: "+GameData.lastErrorMessage,null,AlertType.ERROR);
alert.setTimeout(Alert.FOREVER);
}
display.setCurrent(alert,this);
}
}
// *****************************************************************
// About display.
// *****************************************************************
private class AboutDisplay extends Canvas implements CommandListener
{ private final String[][] HELP_TEXT =
{ { },
{ "About Screen", "[A]: Re-title Game" },
{ "In-Game (1/2)", "[Navi/Fire]: Move/Select","[B]: Grid/Working","[C]: Locked" },
{ "In-Game (2/2)", "[D+B]: Show Timer","[D+C]: Undo" },
{ "Tab:Load", "[U/D/Fire]: Move/Select","[L/R]: Details","[A]: Delete" },
{ "Tab:New", "[U/D/Fire]: Move/Select" },
{ "Tab:Online", "[U/D/Fire]: Move/Select","[A]: Retreat" }
};
private final String[] HELP_TEXT2 =
{
};
private Displayable parent; // Parent screen
private int fh; // Font height
private int mode=0; // What to display
private TextField titleTF; // Text field for re-titling
private Command formOkayCommand; // Form tf okay'd
private Command formCancelCommand; // Form tf cancelled
private Command exitCommand,nextCommand; // Commands
AboutDisplay(Displayable p)
{ exitCommand = new Command("Exit",Command.EXIT,1);
nextCommand = new Command("Next",Command.OK,1);
this.addCommand(exitCommand); this.addCommand(nextCommand);
this.setCommandListener(this);
formOkayCommand = new Command("Okay",Command.OK,1);
formCancelCommand = new Command("Cancel",Command.CANCEL,1);
parent=p;
fh=Font.getDefaultFont().getHeight();
display.setCurrent(this);
}
public void paint(Graphics g)
{ int w=getWidth() , h=getHeight();
int cen=w/2;
g.setColor(0xff,0xff,0xff); g.fillRect(0,0,w,h);
if(mode==0)
{ g.setColor(0x00,0x00,0x00);
g.drawString("-- SudokuME --" , cen,_line(0) , CENTERED);
g.drawString("(c) 2005" , cen,_line(1) , CENTERED);
g.drawString("S.E.Morris & C.Speirs" , cen,_line(2) , CENTERED);
g.setColor(0xff,0x00,0x00);
g.drawString(game.title, cen,h-_line(2) , CENTERED);
g.drawString(getTimerString() , cen,h-_line(1) , CENTERED);
}
else if(mode>0)
{ g.setColor(0x00,0x00,0x00);
g.drawString(HELP_TEXT[mode][0] , cen,_line(0) , CENTERED);
g.setColor(0x00,0x00,0xff);
for(int i=1;i<HELP_TEXT[mode].length;i++)
g.drawString(HELP_TEXT[mode][i] , 5,_line(1+i) , TOPLEFT);
}
}
public int _line(int l)
{ return 5+fh*l;
}
public void keyPressed(int keyCode)
{ switch(getGameAction(keyCode))
{ case GAME_A :
doRename();
break;
}
}
public void commandAction(Command c,Displayable d)
{ if(c==nextCommand)
{ mode=(mode+1)%HELP_TEXT.length; repaint();
}
else if(c==exitCommand)
{ display.setCurrent(parent);
startTimer();
}
else if(c==formOkayCommand)
{ game.title = titleTF.getString();
display.setCurrent(this);
}
else if(c==formCancelCommand)
{ display.setCurrent(this);
}
}
private void doRename()
{ Form form = new Form("Re-title game");
titleTF = new TextField("Title",game.title,20,TextField.ANY);
form.append(titleTF);
form.addCommand(formOkayCommand); form.addCommand(formCancelCommand);
form.setCommandListener(this);
display.setCurrent(form);
}
}
}
// Footnote [1]
// There is a particular problem with LCDUI as it does not automatically
// release its current Displayable when paused, and setCurrent(null)
// doesn't work. For one, setCurrent doesn't take effect immediately, so
// the app will be mothballed before the display is switched. Secondly,
// passing null to setCurrent doesn't actually clear the current
// Displayable anyway.
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -