From d7f292f0abbffb24dc683d754a2ab4b8b2938cc0 Mon Sep 17 00:00:00 2001 From: Stijn Buys Date: Sat, 3 Aug 2013 09:31:17 +0000 Subject: Adds an option to mark cells with a unique solution. --- src/cell.h | 4 +++- src/mainwindow.cc | 18 ++++++++++++++++++ src/mainwindow.h | 6 ++++++ src/settings.cc | 3 ++- src/settings.h | 6 ++++++ src/solverwindow.cc | 12 +++++++++++- src/solverwindow.h | 4 ++++ src/sudokuwidget.cc | 38 ++++++++++++++++++++++++++++++-------- src/sudokuwidget.h | 11 ++++++++++- 9 files changed, 90 insertions(+), 12 deletions(-) (limited to 'src') diff --git a/src/cell.h b/src/cell.h index 4000846..5fe7999 100644 --- a/src/cell.h +++ b/src/cell.h @@ -30,10 +30,12 @@ public: /** * @brief return true of the current value for this cell is a valid possibility * */ + // FIXME the bool valid() should be replaced with a state() enum to indicate + // the difference between Input Error and Invalid Values inline bool valid() const { return cell_valid; } /** - * @brief return the current value for this cell_possibility + * @brief return the current value for this cell * */ inline int value() const { return cell_value; } diff --git a/src/mainwindow.cc b/src/mainwindow.cc index 8ab6c70..010d153 100644 --- a/src/mainwindow.cc +++ b/src/mainwindow.cc @@ -114,6 +114,12 @@ void MainWindow::initActions() action_validate ->setStatusTip(tr("Validate the sudoku")); connect(action_validate, SIGNAL(triggered()), this, SLOT(doValidate())); + // Settings -> Show Unique + action_hintunique = new QAction(tr("Mark solveable"), this); + action_hintunique->setStatusTip(tr("Mark cells with a unique solution")); + action_hintunique->setCheckable(true); + connect(action_hintunique, SIGNAL(triggered()), this, SLOT(doShowHintUnique())); + // Help -> About action_about = new QAction(tr("About..."), this); action_about ->setStatusTip(tr("About %1").arg(PACKAGE_NAME)); @@ -142,6 +148,9 @@ void MainWindow::initMenus() mainwindow_movemenu->addSeparator(); mainwindow_movemenu->addAction(action_validate); + mainwindow_settingsmenu = menuBar()->addMenu(tr("&Settings")); + mainwindow_settingsmenu->addAction(action_hintunique); + mainwindow_helpmenu = menuBar()->addMenu(tr("&Help")); mainwindow_helpmenu->addAction(action_about); } @@ -166,6 +175,8 @@ void MainWindow::updateTitle() action_revert->setEnabled(true); } + + action_hintunique->setChecked(mainwindow_solverwindow->showHintUnique()); } void MainWindow::updateStatus(const QString & text) @@ -208,6 +219,13 @@ void MainWindow::doValidate() mainwindow_solverwindow->doValidate(); } + +void MainWindow::doShowHintUnique() +{ + mainwindow_solverwindow->doShowHintUnique(); + updateTitle(); +} + void MainWindow::doQuit() { if (QMessageBox::question(this, tr("Quit"), tr("Exit the application?"), QMessageBox::Yes | QMessageBox::No) == QMessageBox::Yes) { diff --git a/src/mainwindow.h b/src/mainwindow.h index def0bc8..f18d212 100644 --- a/src/mainwindow.h +++ b/src/mainwindow.h @@ -30,6 +30,8 @@ private slots: void doValidate(); + void doShowHintUnique(); + void doAbout(); private: @@ -40,6 +42,7 @@ private: SolverWindow *mainwindow_solverwindow; QMenu *mainwindow_gamemenu; QMenu *mainwindow_movemenu; + QMenu *mainwindow_settingsmenu; QMenu *mainwindow_helpmenu; // Game menu actions @@ -58,6 +61,9 @@ private: QAction *action_search; QAction *action_validate; + // Settings menu actions + QAction *action_hintunique; + // Help menu actions QAction *action_about; }; diff --git a/src/settings.cc b/src/settings.cc index 19e3c17..14b40ec 100644 --- a/src/settings.cc +++ b/src/settings.cc @@ -16,7 +16,8 @@ Settings::Settings() : m_homePath(), m_colorInvalidValue(255, 0, 0), m_colorInputError(195, 195, 195), - m_colorSolved(192, 255, 192) + m_colorSolved(192, 255, 192), + m_colorHintUnique(255, 255, 127) { #ifdef _WIN32 // get the full path for "Applicaton Data" diff --git a/src/settings.h b/src/settings.h index 229d67a..18c4437 100644 --- a/src/settings.h +++ b/src/settings.h @@ -27,11 +27,17 @@ public: return m_colorSolved; } + inline const QColor & colorHintUnique() const + { + return m_colorHintUnique; + } + private: QString m_homePath; QColor m_colorInvalidValue; QColor m_colorInputError; QColor m_colorSolved; + QColor m_colorHintUnique; }; const Settings & globalSettings(); diff --git a/src/solverwindow.cc b/src/solverwindow.cc index 623caa3..de768cf 100644 --- a/src/solverwindow.cc +++ b/src/solverwindow.cc @@ -24,6 +24,11 @@ SolverWindow::SolverWindow() setLayout(windowlayout); } +const bool SolverWindow::showHintUnique() const +{ + return solverwindow_sudokuwidget->showHintUnique(); +} + void SolverWindow::openFromFile(const QString & filename) { QFile file(filename); @@ -187,7 +192,7 @@ void SolverWindow::doStep() } Sudoku solution(sudoku); - int solved = solution.solve_rules(); + int solved = solution.solve_coverage() + solution.solve_constraints(); if (solved == 0) { QMessageBox::warning(this, tr("Step"), tr("No more cells to solve!")); return; @@ -317,6 +322,11 @@ void SolverWindow::doValidate() QMessageBox::warning(this, tr("Validate"), tr("This sudoku is valid but can not be solved!")); } +void SolverWindow::doShowHintUnique() +{ + solverwindow_sudokuwidget->setShowHintUnique(!solverwindow_sudokuwidget->showHintUnique()); +} + void SolverWindow::step_constraints() { Sudoku sudoku; diff --git a/src/solverwindow.h b/src/solverwindow.h index 4729218..a0dec63 100644 --- a/src/solverwindow.h +++ b/src/solverwindow.h @@ -47,6 +47,10 @@ public slots: void doValidate(); + void doShowHintUnique(); + + const bool showHintUnique() const; + signals: void statusChanged(const QString &text); diff --git a/src/sudokuwidget.cc b/src/sudokuwidget.cc index 387f5d4..f9e364a 100644 --- a/src/sudokuwidget.cc +++ b/src/sudokuwidget.cc @@ -8,6 +8,8 @@ SudokuWidget::SudokuWidget() { + m_showHintUnique = true; + for (int row = 0; row < 9; row++) { for (int column = 0; column < 9 ; column++) { @@ -20,11 +22,21 @@ SudokuWidget::SudokuWidget() } } +void SudokuWidget::setShowHintUnique(const bool hintunique) +{ + if (hintunique != m_showHintUnique) { + m_showHintUnique = hintunique; + verify(); + } +} + void SudokuWidget::verify() { Sudoku values; for (int row = 0; row < 9; row++) { for (int column = 0; column < 9 ; column++) { + QPalette child_palette(palette()); + bool ok; QString str(sudokuwidget_value[row][column]->text()); int i = str.toInt(&ok); @@ -36,8 +48,9 @@ void SudokuWidget::verify() if (!sudokuwidget_value[row][column]->text().isEmpty()) { child_palette.setColor(QPalette::Base, globalSettings().colorInputError()); } - sudokuwidget_value[row][column]->setPalette(child_palette); } + + sudokuwidget_value[row][column]->setPalette(child_palette); } } @@ -51,10 +64,25 @@ void SudokuWidget::verify() // set background color depending on the validity of the cell value if (solved) { child_palette.setColor(QPalette::Base, globalSettings().colorSolved()); + sudokuwidget_value[row][column]->setPalette(child_palette); } else if (!values.cell(row, column).valid()) { child_palette.setColor(QPalette::Base, globalSettings().colorInvalidValue()); + sudokuwidget_value[row][column]->setPalette(child_palette); } - sudokuwidget_value[row][column]->setPalette(child_palette); + } else if ((i == 0) && (m_showHintUnique)) { + // cell is empty, check if it has a unique solution + int possibilities = 0; + for (int value = 0; value < 9; value++) { + if (values.cell(row, column).possibility(value)) { + possibilities++; + } + } + if (possibilities == 1) { + child_palette.setColor(QPalette::Base, globalSettings().colorHintUnique()); + sudokuwidget_value[row][column]->setPalette(child_palette); + } + + } } } @@ -73,20 +101,14 @@ void SudokuWidget::set_values(const Sudoku & values) { for (int row = 0; row < 9; row++) { for (int column = 0; column < 9 ; column++) { - QPalette child_palette(palette()); int i = values.cell(row, column).value(); if (i > 0) { QString str = QString::number(i); sudokuwidget_value[row][column]->setText(str); - // set background color depending on the validity of the cell value - if (!values.cell(row, column).valid()) { - child_palette.setColor(QPalette::Base, globalSettings().colorInvalidValue()); - } } else { sudokuwidget_value[row][column]->clear(); } - sudokuwidget_value[row][column]->setPalette(child_palette); } } diff --git a/src/sudokuwidget.h b/src/sudokuwidget.h index 9ca6098..fb13234 100644 --- a/src/sudokuwidget.h +++ b/src/sudokuwidget.h @@ -30,7 +30,15 @@ public: * @brief return the default size hint for this widget * */ virtual QSize sizeHint() const; - + + inline const bool showHintUnique() const + { + return m_showHintUnique; + } + + void setShowHintUnique(const bool hintunique = true); + + protected: /** * @brief handle paint events @@ -44,6 +52,7 @@ protected: private: QLineEdit * sudokuwidget_value[9][9]; + bool m_showHintUnique; private slots: void verify(); -- cgit v1.2.3