C#
ASP.NET
VSTO
Sudoku For Excel
This was just a tester for the Sudoku class. A simple example of Excel 'CodeBehind' with C# and Visual Studio Tools for Office.
using System; using System.Windows.Forms; using Office = Microsoft.Office.Core; using Excel = Microsoft.Office.Interop.Excel; using MSForms = Microsoft.Vbe.Interop.Forms; public class OfficeCodeBehind { private Excel.Worksheet thisWorksheet = null; private MSForms.CommandButton btnReset; private MSForms.CommandButton btnCheck; private MSForms.CommandButton btnApply; private MSForms.CommandButton btnSolve; private MSForms.TextBox txtMessage; private Excel.Range __theGrid; private Sudoku __sudoku; protected void ThisWorkbook_Open() { thisWorksheet = (Excel.Worksheet) ThisWorkbook.Sheets[ 1 ]; this.btnReset = (MSForms.CommandButton)this.FindControl( "btnReset" ); this.btnCheck = (MSForms.CommandButton)this.FindControl( "btnCheck" ); this.btnApply = (MSForms.CommandButton)this.FindControl( "btnApply" ); this.btnSolve = (MSForms.CommandButton)this.FindControl( "btnSolve" ); this.txtMessage = (MSForms.TextBox) this.FindControl( "txtMessage" ); if (this.btnReset != null ) { this.btnReset.Click += new MSForms.CommandButtonEvents_ClickEventHandler(btnReset_Click); } if (this.btnApply != null ) { this.btnApply.Click += new MSForms.CommandButtonEvents_ClickEventHandler(btnApply_Click); } if (this.btnSolve != null ) { this.btnSolve.Click += new MSForms.CommandButtonEvents_ClickEventHandler(btnSolve_Click); } if (this.btnCheck != null ) { this.btnCheck.Click += new MSForms.CommandButtonEvents_ClickEventHandler(btnCheck_Click); } txtMessage.Text = string.Empty; this.__theGrid = thisWorksheet.get_Range( "theGrid", Type.Missing ); this.__sudoku = new Sudoku9(); //the Grid may contain values from a previous session //so put any such values into the Sudoku array MapGridToSudokuArray(); FormatGrid(); } private void MapGridToSudokuArray() { for (int i = 1; i < 10; i++) { for (int j = 1; j < 10; j++) { Excel.Range currentCell = (Excel.Range) __theGrid.Cells[ i, j ]; if ( currentCell.Value2 != null ) { __sudoku[ i-1, j-1 ] = Convert.ToChar( currentCell.Value2 ); } } } } private void MapSudokuArrayToGrid() { for (int i = 0; i < 9; i++) { for (int j = 0; j < 9; j++) { char c = __sudoku[ i, j]; Excel.Range cell = (Excel.Range) __theGrid.Cells[ i+1, j+1 ]; if ( c != Sudoku.NULL_CHAR ) { cell.Value2 = c.ToString(); } else { cell.Value2 = string.Empty; } } } } private void FormatGrid() { for (int i = 0; i < 9; i++) { for (int j = 0; j < 9; j++) { char c = __sudoku[ i, j]; Excel.Range cell = (Excel.Range) __theGrid.Cells[ i+1, j+1 ]; if ( c != Sudoku.NULL_CHAR ) { cell.Font.ColorIndex = ExcelColorIndex.Black; } else { cell.Font.ColorIndex = ExcelColorIndex.Blue; } } } } //Only checks for no duplicates at the minute. //TODO: Add a clone method to the Sudoku class - //then you can clone the grid, solve it and compare //clone and original. private void btnCheck_Click() { for (int i = 1; i < 10; i++) { for (int j = 1; j < 10; j++) { Excel.Range currentCell = (Excel.Range) __theGrid.Cells[ i, j ]; if ( currentCell.Value2 != null && __sudoku[i-1,j-1] == Sudoku.NULL_CHAR && !(__sudoku.IsValidInCell( Convert.ToChar( currentCell.Value2 ), i-1, j-1 )) ) { currentCell.Font.ColorIndex = ExcelColorIndex.Red; this.txtMessage.Text += String.Format( "Cell {0},{1} is inconsistent.\n", i,j ); } } } } private void btnReset_Click() { this.__sudoku = new Sudoku9(); this.txtMessage.Text = String.Empty; this.__theGrid.Value2 = null; this.__theGrid.Font.ColorIndex = ExcelColorIndex.Blue; } private void btnApply_Click() { MapGridToSudokuArray(); FormatGrid(); } private void btnSolve_Click() { this.__sudoku.Solve(); MapSudokuArrayToGrid(); } }