/**
  * Creates a new Sudoku with a given{@link DifficultyLevel} and a given {@link GameMode}. The
  * puzzles are taken from the cache if possible.<br>
  * If no puzzle could be generated (or the generation was aborted), <code>null</code> is returned.
  *
  * @param level
  * @param mode
  * @return
  */
 private Sudoku2 getSudoku(DifficultyLevel level, GameMode mode) {
   if (mode == GameMode.LEARNING) {
     // in LEARNING ANY puzzle is accepted, that has at least one Training Step in it
     level = Options.getInstance().getDifficultyLevel(DifficultyType.EXTREME.ordinal());
   }
   String preGenSudoku = BackgroundGeneratorThread.getInstance().getSudoku(level, mode);
   Sudoku2 tmpSudoku = null;
   SudokuSolver solver = SudokuSolverFactory.getDefaultSolverInstance();
   if (preGenSudoku == null) {
     // no pregenerated puzzle available -> do it in GUI
     GenerateSudokuProgressDialog dlg = new GenerateSudokuProgressDialog(null, true, level, mode);
     dlg.setVisible(true);
     tmpSudoku = dlg.getSudoku();
   } else {
     tmpSudoku = new Sudoku2();
     tmpSudoku.setSudoku(preGenSudoku, true);
     Sudoku2 solvedSudoku = tmpSudoku.clone();
     solver.solve(
         level,
         solvedSudoku,
         true,
         null,
         false,
         Options.getInstance().solverSteps,
         Options.getInstance().getGameMode());
     tmpSudoku.setLevel(solvedSudoku.getLevel());
     tmpSudoku.setScore(solvedSudoku.getScore());
   }
   if (tmpSudoku == null) {
     // couldnt create anything or was aborted
     return null;
   }
   if (mode == GameMode.LEARNING) {
     // solve the sudoku up until the first trainingStep
     List<SolutionStep> steps = solver.getSteps();
     for (SolutionStep step : steps) {
       if (step.getType().getStepConfig().isEnabledTraining()) {
         break;
       } else {
         // System.out.println("doStep(): " + step.getType().getStepName());
         solver.doStep(tmpSudoku, step);
       }
     }
   }
   return tmpSudoku;
 }