Python Example:
import sys
from Tkinter import Canvas, Button, YES, BOTH, mainloop
from MplSudoku import *
dataFilename = "Sudoku.dat"
headerFont = 'Helvetica 20 bold'
fixedFont = 'Helvetica 14 bold'
solutionFont = 'Helvetica 13'
def createSudokuCanvas(boxCount, cellCount):
xoff = 40
yoff = 80
cellSize = 30
totalCount = boxCount * cellCount
sudokuSize = totalCount * cellSize + totalCount + boxCount + 2
width = sudokuSize + xoff * 2 - 2
height = sudokuSize + yoff * 2 - 2
canvas = Canvas(width=width, height=height, bg='white')
canvas.pack(expand=YES, fill=BOTH)
canvas.totalCount = totalCount
canvas.boxCount = boxCount
canvas.cellCount = cellCount
canvas.cellSize = cellSize
canvas.xoff = xoff
canvas.yoff = yoff
canvas.sudokuSize = sudokuSize
canvas.width = width
canvas.height = height
return canvas
def showSudokuHeader(canvas, headerText):
canvas.create_text(canvas.width / 2 + 2, canvas.yoff / 2 + 2, text=headerText, font=headerFont)
def showSudokuGrid(canvas):
lineLen = canvas.sudokuSize
xoff = canvas.xoff
yoff = canvas.yoff
x = xoff + 1
y = yoff + 1
for i in range(canvas.totalCount + 1):
if i % canvas.cellCount:
lineWidth = 1
else:
lineWidth = 2
canvas.create_line(x, yoff, x, yoff+lineLen, width=lineWidth)
canvas.create_line(xoff, y, xoff+lineLen, y, width=lineWidth)
x += canvas.cellSize + lineWidth
y += canvas.cellSize + lineWidth
def readSudokuDataFile(filename, size):
fixedValues = []
k = 0
file = open(filename, 'r')
for i, line in enumerate(file):
items = line[:-1].split(',')
if len(items) > 1:
if len(items) < size:
raise ValueError("The file '%s' contains %d items in line %d, instead of the
required %d." % (filename, len(items), i+1, size))
if k < size:
for j, item in enumerate(items):
if j < size:
fixedValues.append(int(item.strip()))
k += 1
file.close()
return fixedValues
def readSudokuSparseDataFile(filename):
fixedValues = []
file = open(filename, 'r')
for i, line in enumerate(file):
items = line[:-1].split(',')
if len(items) > 1:
if not len(items) == 3:
raise ValueError("The file '%s' contains '%' in line %d, instead of the correct
format 'Row, Col, Num'." % (filename, line[:-1], i+1))
entry = tuple(int(i) for i in items)
fixedValues.append(entry)
file.close()
return fixedValues
def getSudokuCellPos(canvas, rowcol):
return (rowcol-0.5) * (canvas.cellSize + 1) + ((rowcol-1)/canvas.cellCount) + 1
def getValue(row, col, size, values):
if values == None or len(values) == 0:
return 0
if type(values[0]).__name__ == 'list' or type(values[0]).__name__ == 'tuple':
for entry in values:
if row == entry[0] and col == entry[1]:
return entry[2]
return 0
else:
nr = (row - 1) * size + (col - 1)
return values[nr]
def showSudokuEntries(solValues, fixedValues, size, fontStr, canvas):
row = 1
col = 1
for nr in range(size * size):
ypos = canvas.yoff + getSudokuCellPos(canvas, row)
xpos = canvas.xoff + getSudokuCellPos(canvas, col)
if solValues == None:
fix = getValue(row, col, size, fixedValues)
if fix > 0:
canvas.create_text(xpos, ypos, text=str(fix), font=fontStr)
else:
val = getValue(row, col, size, solValues)
if val > 0:
canvas.create_text(xpos, ypos, text=str(val), font=fontStr)
if col < size:
col += 1
else:
col = 1
row += 1
def doLoadButton(canvas):
size = 9
dataDir = MplSudoku().DataDir
canvas.fixedValues = readSudokuDataFile(dataDir + dataFilename, size)
showSudokuEntries(None, canvas.fixedValues, size, fixedFont, canvas)
def doSolveButton(canvas):
size = 9
sudoku = MplSudoku()
result = sudoku.SolveModel("CoinMP", size, canvas.fixedValues)
if result == False:
print("There is no solution available with this input.\n" +
"The solver returned the following message:\n" +
str(sudoku.ResultString))
return
showSudokuEntries(sudoku.SolValues, canvas.fixedValues, size, solutionFont, canvas)
def doCloseButton(canvas):
sys.exit()
def createButton(canvas, text, x, y, cmd):
button = Button(canvas, text=text, width=8, command=cmd)
button.pack()
canvas.create_window(x, y, window=button)
def showSudokuButtons(canvas):
x = canvas.width / 2 - 100
y = canvas.height - canvas.yoff / 2
createButton(canvas, 'Load', x, y, lambda: doLoadButton(canvas))
createButton(canvas, 'Solve', x + 100, y, lambda: doSolveButton(canvas))
createButton(canvas, 'Close', x + 200, y, lambda: doCloseButton(canvas))
def runSudoku():
canvas = createSudokuCanvas(3,3)
showSudokuHeader(canvas, "MPL Sudoku")
showSudokuGrid(canvas)
showSudokuButtons(canvas)
mainloop()
if __name__ == '__main__':
runSudoku()