summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorThomas Günther <tom@toms-cafe.de>2008-03-16 23:20:33 +0100
committerThomas Günther <tom@toms-cafe.de>2008-03-16 23:20:33 +0100
commit1a2247ccdfaba348b80fb2482c27e71b7cb17b92 (patch)
tree524beb5da87e819aa20d06ac4f650a579160b667
parent7aaa70fa39a1e9968ff08ffab4462231e80fbb67 (diff)
downloadvdr-plugin-sudoku-1a2247ccdfaba348b80fb2482c27e71b7cb17b92.tar.gz
vdr-plugin-sudoku-1a2247ccdfaba348b80fb2482c27e71b7cb17b92.tar.bz2
Added commands to load and save puzzles from/to the sudoku-list file
-rw-r--r--HISTORY1
-rw-r--r--README23
-rw-r--r--commands.cpp4
-rw-r--r--list.cpp202
-rw-r--r--list.h114
-rw-r--r--menu.cpp50
-rw-r--r--menu.h14
-rw-r--r--puzzle.cpp110
-rw-r--r--puzzle.h22
-rw-r--r--sudoku.cpp4
-rw-r--r--tools/sudoku_generator.cpp36
11 files changed, 523 insertions, 57 deletions
diff --git a/HISTORY b/HISTORY
index 63b2ad8..a69edb3 100644
--- a/HISTORY
+++ b/HISTORY
@@ -35,3 +35,4 @@ ____-__-__: Version _._._
- Paint numbers with a larger font (VDR >= 1.5.4).
- Changed the background color of marked cells to darkgreen.
- Added commands menu.
+- Added commands to load and save puzzles from/to the sudoku-list file.
diff --git a/README b/README
index aec9ac4..797e9e2 100644
--- a/README
+++ b/README
@@ -56,6 +56,24 @@ Each time the plug-in is started from the main menu the same puzzle is shown. A
new puzzle is only generated on VDR startup or if it has been requested by
selecting this command in the commands menu, which is opened with the blue key.
+In the commands menu you can load and save puzzles from/to the sudoku-list file.
+This file is located at the plugins folder inside the configuration folder of
+VDR. If you don't specify a configuration folder, your videodir is used (e.g.
+/video0/plugins/sudoku/sudoku-list).
+
+The sudoku-list file contains lines with a sudoku dump and an optional
+description. The sudoku dump has to begin at the first position of the line.
+The delimiter between sudoku dump and description is a space. All behind the
+first space is considered as description.
+
+A sudoku dump consists of up to three parts. The first part contains only the
+givens, the second part all numbers set so far (including the givens), and the
+third part the marked cells. They are delimited from each other by a colon. All
+except of the first part is optional. The parts are strings with 81 digits or
+underlines. An underline is considered as a zero. All other characters, except
+of colons and spaces, which terminate the string, are ignored. They could be
+used to structure the dump, e.g. plus signs after each 9 digits/underlines.
+
Setup:
------
@@ -106,6 +124,11 @@ Commands menu:
--------------
- Generate a new puzzle Generate a random puzzle.
+- Load a puzzle Load a puzzle from the sudoku list. In the list menu
+ you can also delete sudokus from the list or edit the
+ descriptions.
+- Save the puzzle Add the puzzle to the sudoku list, together with an
+ optional description.
- Reset the puzzle Reset the numbers in all cells, excluding the givens.
- Exit Quit the plug-in.
diff --git a/commands.cpp b/commands.cpp
index 2319e81..37dd5b8 100644
--- a/commands.cpp
+++ b/commands.cpp
@@ -17,7 +17,7 @@
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
- * $Id: commands.cpp 113 2008-03-16 20:12:52Z tom $
+ * $Id: commands.cpp 114 2008-03-16 22:20:33Z tom $
*/
#include "commands.h"
@@ -39,6 +39,8 @@ CommandMenu::CommandMenu() :
{
SetHasHotkeys();
Add(new Command(hk(tr("Generate a new puzzle")), &Menu::generate));
+ Add(new Command(hk(tr("Load a puzzle")), &Menu::load));
+ Add(new Command(hk(tr("Save the puzzle")), &Menu::save));
Add(new Command(hk(tr("Reset the puzzle")), &Menu::reset));
Add(new Command(hk(tr("Exit")), &Menu::exit));
command = NULL;
diff --git a/list.cpp b/list.cpp
new file mode 100644
index 0000000..e282cff
--- /dev/null
+++ b/list.cpp
@@ -0,0 +1,202 @@
+/*
+ * Sudoku: A plug-in for the Video Disk Recorder
+ *
+ * Copyright (C) 2008, Thomas Günther <tom@toms-cafe.de>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * $Id: list.cpp 114 2008-03-16 22:20:33Z tom $
+ */
+
+#include "list.h"
+#include "i18n.h"
+#include <vdr/config.h>
+#include <vdr/osdbase.h>
+#include <vdr/osd.h>
+#include <vdr/menuitems.h>
+#include <assert.h>
+
+using namespace SudokuPlugin;
+
+
+//--- class SudokuPlugin::ListLine ---------------------------------------------
+
+/** Default constructor for cConfig<ListLine> */
+ListLine::ListLine()
+{
+}
+
+/** Constructor */
+ListLine::ListLine(const char* sudoku, const char* description) :
+ sudoku(sudoku), description(description)
+{
+ assert(sudoku != NULL);
+ assert(description != NULL);
+}
+
+/** Get the sudoku dump. */
+const char* ListLine::get_sudoku() const
+{
+ assert((const char*)sudoku != NULL);
+ return sudoku;
+}
+
+/** Get the description. */
+const char* ListLine::get_description() const
+{
+ assert((const char*)description != NULL);
+ return description;
+}
+
+/** Set the description. */
+void ListLine::set_description(const char* new_description)
+{
+ assert(new_description != NULL);
+ description = skipspace(new_description);
+}
+
+/** Parse a line of the sudoku list. */
+bool ListLine::Parse(const char* line)
+{
+ const char *delim = strchr(line, ' ');
+ if (delim)
+ {
+ sudoku = cString(strndup(line, delim - line), true);
+ description = skipspace(delim);
+ }
+ else
+ {
+ sudoku = line;
+ description = "";
+ }
+ assert((const char*)sudoku != NULL);
+ assert((const char*)description != NULL);
+ return !isempty(sudoku);
+}
+
+/** Save a line of the sudoku list. */
+bool ListLine::Save(FILE* file) const
+{
+ return fprintf(file, "%s %s\n", *sudoku, *description) > 0;
+}
+
+
+//--- class SudokuPlugin::ListMenu ---------------------------------------------
+
+/** Constructor */
+ListMenu::ListMenu(const char* filename, const char* new_sudoku) :
+ cOsdMenu(tr("Sudoku list")), selected(-1), save_mode(new_sudoku)
+{
+ list.Load(filename);
+ if (save_mode)
+ list.Add(new ListLine(new_sudoku));
+ refresh();
+ if (save_mode)
+ {
+ SetCurrent(Last());
+ AddSubMenu(new ListEdit(*list.Get(Current())));
+ ProcessKey(kRight); // enter edit mode
+ }
+}
+
+/** Get the selected sudoku. */
+const char* ListMenu::get_selected_sudoku() const
+{
+ ListLine* line = list.Get(selected);
+ if (line)
+ return line->get_sudoku();
+ return NULL;
+}
+
+/** Process user events. */
+eOSState ListMenu::ProcessKey(eKeys key)
+{
+ bool had_submenu = HasSubMenu();
+ if (key == kBlue && !HasSubMenu())
+ key = kBack;
+ if (key == kGreen && !HasSubMenu() && !save_mode)
+ key = kOk;
+ eOSState state = cOsdMenu::ProcessKey(key);
+ if (state == osUnknown)
+ {
+ state = osContinue;
+ switch (key)
+ {
+ case kRed:
+ if (Current() >= 0 && Current() < list.Count())
+ return AddSubMenu(new ListEdit(*list.Get(Current())));
+ break;
+ case kYellow:
+ if (Current() >= 0 && Current() < list.Count())
+ list.Del(list.Get(Current()));
+ refresh();
+ list.Save();
+ break;
+ case kOk:
+ if (Current() >= 0 && Current() < list.Count() && !save_mode)
+ selected = Current();
+ state = osBack;
+ break;
+ default:
+ break;
+ }
+ }
+ if (had_submenu && !HasSubMenu())
+ {
+ refresh();
+ list.Save();
+ }
+ return state;
+}
+
+/** Refresh the list menu. */
+void ListMenu::refresh()
+{
+ int current = Current();
+ Clear();
+ SetHasHotkeys();
+ for (ListLine* line = list.First(); line; line = list.Next(line))
+ Add(new cOsdItem(hk(line->get_description())));
+ SetCurrent(Get(current));
+ SetHelp(trVDR("Button$Edit"), save_mode ? NULL : tr("Button$Load"),
+ trVDR("Button$Delete"), tr("Button$Back"));
+ Display();
+}
+
+
+//--- class SudokuPlugin::ListEdit ---------------------------------------------
+
+/** Constructor */
+ListEdit::ListEdit(ListLine& line) :
+ cOsdMenu(tr("Edit sudoku list"), 15), line(line)
+{
+ strn0cpy(description, line.get_description(), sizeof(description));
+ Add(new cMenuEditStrItem(tr("Description"), description, sizeof(description)));
+}
+
+/** Process user events. */
+eOSState ListEdit::ProcessKey(eKeys key)
+{
+ eOSState state = cOsdMenu::ProcessKey(key);
+ if (state == osUnknown)
+ {
+ if (key == kOk)
+ {
+ line.set_description(description);
+ state = osBack;
+ }
+ }
+ return state;
+}
diff --git a/list.h b/list.h
new file mode 100644
index 0000000..a2d1c8d
--- /dev/null
+++ b/list.h
@@ -0,0 +1,114 @@
+/*
+ * Sudoku: A plug-in for the Video Disk Recorder
+ *
+ * Copyright (C) 2008, Thomas Günther <tom@toms-cafe.de>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with this program; if not, write to the Free Software Foundation, Inc.,
+ * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * $Id: list.h 114 2008-03-16 22:20:33Z tom $
+ */
+
+#ifndef VDR_SUDOKU_LIST_H
+#define VDR_SUDOKU_LIST_H
+
+#include "sudoku.h"
+#include <vdr/osdbase.h>
+#include <vdr/tools.h>
+
+
+namespace SudokuPlugin
+{
+
+ //--- class SudokuPlugin::ListLine -------------------------------------------
+
+ /** Line in sudoku list */
+ class ListLine : public cListObject
+ {
+ cString sudoku;
+ cString description;
+
+ /** Default constructor for cConfig<ListLine> */
+ ListLine();
+ friend class cConfig<ListLine>;
+
+ public:
+
+ /** Constructor */
+ ListLine(const char* sudoku, const char* description = "");
+
+ /** Get the sudoku dump. */
+ const char* get_sudoku() const;
+
+ /** Get the description. */
+ const char* get_description() const;
+
+ /** Set the description. */
+ void set_description(const char* new_description);
+
+ /** Parse a line of the sudoku list. */
+ bool Parse(const char* line);
+
+ /** Save a line of the sudoku list. */
+ bool Save(FILE* file) const;
+ };
+
+
+ //--- class SudokuPlugin::ListMenu -------------------------------------------
+
+ /** Sudoku list menu */
+ class ListMenu : public cOsdMenu
+ {
+ cConfig<ListLine> list;
+ int selected;
+ bool save_mode;
+
+ public:
+
+ /** Constructor */
+ ListMenu(const char* filename, const char* new_sudoku = NULL);
+
+ /** Get the selected sudoku. */
+ const char* get_selected_sudoku() const;
+
+ /** Process user events. */
+ virtual eOSState ProcessKey(eKeys key);
+
+ private:
+
+ /** Refresh the list menu. */
+ void refresh();
+ };
+
+
+ //--- class SudokuPlugin::ListEdit -------------------------------------------
+
+ /** Sudoku list edit menu */
+ class ListEdit : public cOsdMenu
+ {
+ ListLine& line;
+ char description[100];
+
+ public:
+
+ /** Constructor */
+ ListEdit(ListLine& line);
+
+ /** Process user events. */
+ virtual eOSState ProcessKey(eKeys key);
+ };
+
+} // namespace SudokuPlugin
+
+#endif // VDR_SUDOKU_LIST_H
diff --git a/menu.cpp b/menu.cpp
index 1400dc1..a65b9cc 100644
--- a/menu.cpp
+++ b/menu.cpp
@@ -17,7 +17,7 @@
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
- * $Id: menu.cpp 113 2008-03-16 20:12:52Z tom $
+ * $Id: menu.cpp 114 2008-03-16 22:20:33Z tom $
*/
#include "menu.h"
@@ -25,6 +25,7 @@
#include "setup.h"
#include "bitmap.h"
#include "commands.h"
+#include "list.h"
#include "i18n.h"
#include <vdr/config.h>
#include <vdr/osdbase.h>
@@ -35,6 +36,9 @@ using namespace SudokuPlugin;
using namespace Sudoku;
+// Definition of the file name of the sudoku list
+#define SUDOKU_LIST "sudoku-list"
+
// Definitions for grid structure
#define CELL_SIZE 42
#define CELL_POS(i) ((i) * (CELL_SIZE + 2) + (i)/RDIM * 3 + 5)
@@ -61,8 +65,8 @@ using namespace Sudoku;
//--- class SudokuPlugin::Menu -------------------------------------------------
/** Constructor */
-Menu::Menu(const SetupData& setup, Puzzle& puzzle, Pos& curr) :
- cOsdObject(true), setup(setup), puzzle(puzzle), curr(curr)
+Menu::Menu(const SetupData& setup, const char* confdir, Puzzle& puzzle, Pos& curr) :
+ cOsdObject(true), setup(setup), confdir(confdir), puzzle(puzzle), curr(curr)
{
xPos = (720 - GRID_SIZE) / 2;
yPos = (576 - GRID_SIZE) / 2;
@@ -79,11 +83,13 @@ Menu::Menu(const SetupData& setup, Puzzle& puzzle, Pos& curr) :
mini_font = NULL;
#endif
command_menu = NULL;
+ list_menu = NULL;
}
/** Destructor */
Menu::~Menu()
{
+ delete list_menu;
delete command_menu;
#if VDRVERSNUM >= 10504
delete maxi_font;
@@ -127,6 +133,21 @@ eOSState Menu::ProcessKey(eKeys key)
return state;
}
+ if (list_menu)
+ {
+ eOSState state = list_menu->ProcessKey(key);
+ if (state == osBack)
+ {
+ state = osContinue;
+ const char* sudoku = list_menu->get_selected_sudoku();
+ if (sudoku)
+ puzzle = Puzzle(sudoku);
+ DELETENULL(list_menu);
+ Show();
+ }
+ return state;
+ }
+
eOSState state = cOsdObject::ProcessKey(key);
if (state == osUnknown)
{
@@ -209,6 +230,29 @@ eOSState Menu::generate()
return osContinue;
}
+/** Load a puzzle. */
+eOSState Menu::load()
+{
+ if (osd)
+ osd->Flush();
+ DELETENULL(osd);
+ list_menu = new ListMenu(AddDirectory(confdir, SUDOKU_LIST));
+ list_menu->Display();
+ return osUnknown;
+}
+
+/** Save the puzzle. */
+eOSState Menu::save()
+{
+ if (osd)
+ osd->Flush();
+ DELETENULL(osd);
+ list_menu = new ListMenu(AddDirectory(confdir, SUDOKU_LIST),
+ puzzle.get_dump());
+ list_menu->Display();
+ return osUnknown;
+}
+
/** Reset the puzzle. */
eOSState Menu::reset()
{
diff --git a/menu.h b/menu.h
index 5912626..6dcde4c 100644
--- a/menu.h
+++ b/menu.h
@@ -17,7 +17,7 @@
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
- * $Id: menu.h 113 2008-03-16 20:12:52Z tom $
+ * $Id: menu.h 114 2008-03-16 22:20:33Z tom $
*/
#ifndef VDR_SUDOKU_MENU_H
@@ -35,6 +35,7 @@ namespace SudokuPlugin
class SetupData;
class Bitmap;
class CommandMenu;
+ class ListMenu;
//--- class SudokuPlugin::Menu -----------------------------------------------
@@ -42,6 +43,7 @@ namespace SudokuPlugin
class Menu : public cOsdObject
{
const SetupData& setup;
+ const char* confdir;
Sudoku::Puzzle& puzzle;
Sudoku::Pos& curr;
int xPos, yPos;
@@ -52,11 +54,13 @@ namespace SudokuPlugin
const cFont* maxi_font;
const cFont* mini_font;
CommandMenu* command_menu;
+ ListMenu* list_menu;
public:
/** Constructor */
- Menu(const SetupData& setup, Sudoku::Puzzle& puzzle, Sudoku::Pos& curr);
+ Menu(const SetupData& setup, const char* confdir,
+ Sudoku::Puzzle& puzzle, Sudoku::Pos& curr);
/** Destructor */
virtual ~Menu();
@@ -70,6 +74,12 @@ namespace SudokuPlugin
/** Generate a new puzzle. */
eOSState generate();
+ /** Load a puzzle. */
+ eOSState load();
+
+ /** Save the puzzle. */
+ eOSState save();
+
/** Reset the puzzle. */
eOSState reset();
diff --git a/puzzle.cpp b/puzzle.cpp
index 947e7ba..77d94db 100644
--- a/puzzle.cpp
+++ b/puzzle.cpp
@@ -17,11 +17,12 @@
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
- * $Id: puzzle.cpp 109 2008-01-06 19:43:20Z tom $
+ * $Id: puzzle.cpp 114 2008-03-16 22:20:33Z tom $
*/
#include "puzzle.h"
#include "generator.h"
+#include <string.h>
#include <assert.h>
using namespace Sudoku;
@@ -30,14 +31,42 @@ using namespace Sudoku;
//--- class Sudoku::Numbers ----------------------------------------------------
/** Constructor */
-Numbers::Numbers()
+Numbers::Numbers(const char* dump) :
+ numbers_dump()
{
reset();
+
+ if (dump)
+ for (unsigned int i = 0; *dump && *dump != ':' && i < SDIM; ++i, ++dump)
+ if (*dump == '+')
+ --i;
+ else if (*dump > '0' && *dump - '0' <= DIM)
+ content[i] = *dump - '0';
+
+ assert(!numbers_dump);
}
/** Destructor */
Numbers::~Numbers()
{
+ delete[] numbers_dump;
+}
+
+/** Get the numbers as dump */
+const char* Numbers::get_dump() const
+{
+ if (!numbers_dump)
+ numbers_dump = new char[SDIM + DIM];
+ assert(numbers_dump);
+
+ char* dump = numbers_dump;
+ unsigned int n;
+ for (unsigned int row = 0; row < DIM; ++row, *dump++ = '+')
+ for (unsigned int col = 0; col < DIM; ++col, ++dump)
+ *dump = (n = get(Pos(col, row))) ? '0' + n : '_';
+ *--dump = 0;
+
+ return numbers_dump;
}
/** Remove all numbers. */
@@ -77,12 +106,72 @@ unsigned int Numbers::get(Pos pos) const
//--- class Sudoku::Puzzle -----------------------------------------------------
/** Constructor */
-Puzzle::Puzzle(unsigned int givens_count, bool symmetric)
+Puzzle::Puzzle(const char* dump) :
+ puzzle_dump()
+{
+ // Set givens from the first part of the dump (before the first colon)
+ givens = Numbers(dump);
+ reset();
+
+ // Set numbers from the second part (between the first and the second colon)
+ if (dump)
+ dump = strchr(dump, ':');
+ if (dump)
+ {
+ Numbers numbers(++dump);
+ for (unsigned int i = 0; i < SDIM; ++i)
+ if (numbers.get(i) != 0)
+ set(i, numbers.get(i));
+ }
+
+ // Set marks from the third part (behind the second colon)
+ if (dump)
+ dump = strchr(dump, ':');
+ if (dump)
+ marks = Numbers(++dump);
+
+ assert(!puzzle_dump);
+}
+
+/** Constructor with generation of a random puzzle */
+Puzzle::Puzzle(unsigned int givens_count, bool symmetric) :
+ puzzle_dump()
{
if (givens_count == 0)
clear_givens();
else
generate(givens_count, symmetric);
+
+ assert(!puzzle_dump);
+}
+
+/** Destructor */
+Puzzle::~Puzzle()
+{
+ delete[] puzzle_dump;
+}
+
+/** Get the puzzle as dump */
+const char* Puzzle::get_dump() const
+{
+ if (!puzzle_dump)
+ puzzle_dump = new char[3 * (SDIM + DIM)];
+ assert(puzzle_dump);
+
+ // Set givens as first part of the dump
+ strcpy(puzzle_dump, givens.get_dump());
+ if (!untouched())
+ {
+ // Set numbers as second part of the dump
+ strcat(puzzle_dump, ":");
+ strcat(puzzle_dump, Numbers::get_dump());
+
+ // Set marks as third part of the dump
+ strcat(puzzle_dump, ":");
+ strcat(puzzle_dump, marks.get_dump());
+ }
+
+ return puzzle_dump;
}
/** Reset the puzzle (including marks). */
@@ -106,8 +195,7 @@ void Puzzle::reset(bool clear_marks)
// Reset marked cells.
if (clear_marks)
- for (i = 0; i < SDIM; ++i)
- marks[i] = false;
+ marks.reset();
}
/** Set the number into this cell. */
@@ -157,9 +245,7 @@ void Puzzle::clear_givens()
/** No cells set? */
bool Puzzle::untouched() const
{
- unsigned int i;
-
- for (i = 0; i < SDIM; ++i)
+ for (unsigned int i = 0; i < SDIM; ++i)
if (get(i) != givens.get(i))
return false;
@@ -190,9 +276,7 @@ bool Puzzle::ambiguous(Pos pos) const
/** All cells set and no errors? */
bool Puzzle::solved() const
{
- unsigned int i;
-
- for (i = 0; i < SDIM; ++i)
+ for (unsigned int i = 0; i < SDIM; ++i)
if (get(i) == 0 || !correct(i))
return false;
@@ -203,14 +287,14 @@ bool Puzzle::solved() const
bool Puzzle::marked(Pos pos) const
{
assert(pos <= Pos::last());
- return marks[pos];
+ return marks.get(pos) != 0;
}
/** Toggle the mark for this cell. */
void Puzzle::toggle_mark(Pos pos)
{
assert(pos <= Pos::last());
- marks[pos] = !marks[pos];
+ marks.set(pos, marks.get(pos) != 0 ? 0 : 1);
}
/** Get the next free cell with minimal possible numbers. */
diff --git a/puzzle.h b/puzzle.h
index e9d4f13..726030e 100644
--- a/puzzle.h
+++ b/puzzle.h
@@ -17,7 +17,7 @@
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
- * $Id: puzzle.h 109 2008-01-06 19:43:20Z tom $
+ * $Id: puzzle.h 114 2008-03-16 22:20:33Z tom $
*/
#ifndef VDR_SUDOKU_PUZZLE_H
@@ -80,15 +80,19 @@ namespace Sudoku
class Numbers
{
unsigned int content[SDIM];
+ mutable char* numbers_dump;
public:
/** Constructor */
- Numbers();
+ Numbers(const char* dump = 0);
/** Destructor */
virtual ~Numbers();
+ /** Get the numbers as dump */
+ virtual const char* get_dump() const;
+
/** Remove all numbers. */
virtual void reset();
@@ -109,14 +113,24 @@ namespace Sudoku
class Puzzle : public Numbers
{
Numbers givens;
- bool marks[SDIM];
+ Numbers marks;
bool numbers[SDIM][DIM+1];
unsigned int count[SDIM];
+ mutable char* puzzle_dump;
public:
/** Constructor */
- Puzzle(unsigned int givens_count = 0, bool symmetric = true);
+ Puzzle(const char* dump = 0);
+
+ /** Constructor with generation of a random puzzle */
+ Puzzle(unsigned int givens_count, bool symmetric = true);
+
+ /** Destructor */
+ virtual ~Puzzle();
+
+ /** Get the puzzle as dump */
+ virtual const char* get_dump() const;
/** Reset the puzzle (including marks). */
virtual void reset();
diff --git a/sudoku.cpp b/sudoku.cpp
index dd35ea5..a62b475 100644
--- a/sudoku.cpp
+++ b/sudoku.cpp
@@ -17,7 +17,7 @@
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
- * $Id: sudoku.cpp 106 2007-12-03 23:28:24Z tom $
+ * $Id: sudoku.cpp 114 2008-03-16 22:20:33Z tom $
*/
#include "sudoku.h"
@@ -105,7 +105,7 @@ bool Plugin::Start()
*/
cOsdObject* Plugin::MainMenuAction()
{
- return new Menu(setup, puzzle, curr);
+ return new Menu(setup, ConfigDirectory(Name()), puzzle, curr);
}
/** Setup menu page to adjust the setup parameters of the plugin
diff --git a/tools/sudoku_generator.cpp b/tools/sudoku_generator.cpp
index 621440e..cba0e5d 100644
--- a/tools/sudoku_generator.cpp
+++ b/tools/sudoku_generator.cpp
@@ -17,7 +17,7 @@
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
- * $Id: sudoku_generator.cpp 106 2007-12-03 23:28:24Z tom $
+ * $Id: sudoku_generator.cpp 114 2008-03-16 22:20:33Z tom $
*/
#include "../puzzle.h"
@@ -126,20 +126,7 @@ void print_sudoku(const Numbers& sudoku1, const Numbers& sudoku2,
void dump_sudoku(const Numbers& sudoku)
{
- for (unsigned int row = 0; row < DIM; ++row)
- {
- for (unsigned int col = 0; col < DIM; ++col)
- {
- unsigned int n = sudoku.get(Pos(col, row));
- if (n)
- printf("%d", n);
- else
- printf("_");
- }
- if (row < DIM-1)
- printf("+");
- }
- printf("\n");
+ printf("%s\n", sudoku.get_dump());
}
int generate_puzzle(unsigned int givens_count, bool non_sym, bool dump)
@@ -156,24 +143,9 @@ int generate_puzzle(unsigned int givens_count, bool non_sym, bool dump)
return 0;
}
-Numbers dump_to_numbers(const char *dump)
-{
- Numbers numbers;
- for (Pos p = Pos::first(); *dump && p <= Pos::last(); ++dump)
- {
- if (*dump != '+')
- {
- if (*dump > '0' && *dump - '0' <= DIM)
- numbers.set(p, *dump - '0');
- p = p.next();
- }
- }
- return numbers;
-}
-
int solve_puzzle(const char *dump)
{
- Numbers numbers(dump_to_numbers(dump));
+ Numbers numbers(dump);
bool given_marks[SDIM];
for (Pos p = Pos::first(); p <= Pos::last(); p = p.next())
given_marks[p] = numbers.get(p) != 0;
@@ -193,7 +165,7 @@ int solve_puzzle(const char *dump)
int print_puzzle(const char *dump)
{
- Numbers numbers(dump_to_numbers(dump));
+ Numbers numbers(dump);
print_sudoku(numbers);
return 0;
}