Ejemplo n.º 1
0
 def test_kakuro_not_solution(self):
     game = GameField(3, 3)
     cell_column = Cell(CellType.RULES, column_rule=3, length_column=2)
     cell_row = Cell(CellType.RULES, row_rule=17, length_row=2)
     game.init_cell(0, 1, cell_column)
     game.init_cell(1, 0, cell_row)
     solver = Solver(game)
     with self.assertRaises(exc.KakuroNotSolution):
         self.assertRaises(solver.solve())
Ejemplo n.º 2
0
def get_solve(input_file, output_file):
    parser = Parser()
    try:
        pairs = parser.parse(input_file)
    except exc.IncorrectFileArgument as e:
        print('Incorrect file{0}'.format(input_file))
        return
    except Exception as fe:
        print('Unrecognized error in file')
        return
    dimension = pairs[0]
    game = GameField(dimension, dimension)
    for cells in pairs[1:]:
        for key in cells.keys():
            game.init_cell(key[0], key[1], cells[key])
    solver = Solver(game)
    painter = Painter(64)
    try:
        solution = solver.solve()
    except exc.KakuroNotSolution as e:
        print('Not solution')
        return
    painter.paint(solution, output_file, dimension)
Ejemplo n.º 3
0
 def test_init_put_rule_cell_column(self):
     game = GameField(10, 10)
     cell = Cell(CellType.RULES, column_rule=10, length_column=2)
     game.init_cell(5, 5, cell)
     self.assertEqual(CellType.PLAY, game.field[6][5].get_type())
     self.assertEqual(CellType.PLAY, game.field[7][5].get_type())
Ejemplo n.º 4
0
 def test_init_put_rule_cell_row(self):
     game = GameField(10, 10)
     cell = Cell(CellType.RULES, row_rule=10, length_row=2)
     game.init_cell(5, 5, cell)
     self.assertEqual(CellType.PLAY, game.field[5][6].get_type())
     self.assertEqual(CellType.PLAY, game.field[5][7].get_type())
Ejemplo n.º 5
0
 def test_init_put_play_cell(self):
     game = GameField(10, 10)
     cell = Cell(CellType.PLAY, value=10)
     game.init_cell(5, 5, cell)
     self.assertEqual(cell, game.field[5][5])
Ejemplo n.º 6
0
class SolverTest(unittest.TestCase):
    def setUp(self):
        self.game = GameField(4, 4)
        self.game.init_cell(
            0, 1, Cell(CellType.RULES, column_rule=16, length_column=2))
        self.game.init_cell(
            0, 2, Cell(CellType.RULES, column_rule=15, length_column=3))
        self.game.init_cell(1, 0,
                            Cell(CellType.RULES, row_rule=17, length_row=2))
        self.game.init_cell(2, 0,
                            Cell(CellType.RULES, row_rule=15, length_row=3))
        self.game.init_cell(3, 1, Cell(CellType.RULES,
                                       row_rule=3,
                                       length_row=2))
        self.game.init_cell(
            1, 3, Cell(CellType.RULES, column_rule=4, length_column=2))

    def test_get_list(self):
        solver = Solver(self.game)
        expected = [
            self.game.field[1][1], self.game.field[1][2],
            self.game.field[2][1], self.game.field[2][2],
            self.game.field[2][3], self.game.field[3][2], self.game.field[3][3]
        ]
        solver.get_list()
        self.assertEqual(expected, solver.all_cells)

    def test_correct_solve(self):
        solver = Solver(self.game)
        self.game.field[1][1].set_value(9)
        self.game.field[1][2].set_value(8)
        self.game.field[2][1].set_value(7)
        self.game.field[2][2].set_value(5)
        self.game.field[2][3].set_value(3)
        self.game.field[3][2].set_value(2)
        self.game.field[3][3].set_value(1)
        self.assertTrue(solver.is_correct_solve())

    def test_kakuro_not_solution(self):
        game = GameField(3, 3)
        cell_column = Cell(CellType.RULES, column_rule=3, length_column=2)
        cell_row = Cell(CellType.RULES, row_rule=17, length_row=2)
        game.init_cell(0, 1, cell_column)
        game.init_cell(1, 0, cell_row)
        solver = Solver(game)
        with self.assertRaises(exc.KakuroNotSolution):
            self.assertRaises(solver.solve())
Ejemplo n.º 7
0
class GUI:
    def __init__(self, root, dimension):
        self.root = root
        self.dimension = dimension
        self.img_for_button = PhotoImage(
            file=os.path.join(os.getcwd(), 'img', 'cell.gif'))
        self.list_button = []
        self.size_button = 64
        self.all_img = []
        self.draw_menu()
        self.root.mainloop()

    def draw_field(self):
        for x in range(0, self.dimension):
            line_button = []
            for y in range(0, self.dimension):
                line_button.append(Button(self.root))
                line_button[y]['command'] = partial(self.open_setting_window,
                                                    x, y)
                line_button[y]['image'] = self.img_for_button
                line_button[y].grid(row=x, column=y)
            self.list_button.append(line_button)

    def open_setting_window(self, x, y):
        setting_root = Tk()
        self.setting_new_root(setting_root, x, y)

    def setting_new_root(self, setting_root, x, y):
        width = 10
        height = 2
        row_label = Label(setting_root, width=width, height=height, text="Row")
        column_label = Label(setting_root,
                             width=width,
                             height=height,
                             text="Column")
        sum_label = Label(setting_root, width=width, height=height, text="Sum")
        length_label = Label(setting_root,
                             width=width,
                             height=height,
                             text="Length")
        sum_row = Entry(setting_root, width=width)
        sum_column = Entry(setting_root, width=width)
        length_row = Entry(setting_root, width=width)
        length_column = Entry(setting_root, width=width)
        apply = Button(setting_root, width=width, height=height, text='Apply')
        apply['command'] = partial(self.put_cell, sum_row, length_row,
                                   sum_column, length_column, x, y,
                                   setting_root)
        cancel = Button(setting_root,
                        width=width,
                        height=height,
                        text='Cancel')
        cancel['command'] = partial(self.close_window, setting_root)
        row_label.grid(row=1, column=0)
        column_label.grid(row=2, column=0)
        sum_label.grid(row=0, column=1)
        length_label.grid(row=0, column=2)
        sum_row.grid(row=1, column=1)
        sum_column.grid(row=2, column=1)
        length_row.grid(row=1, column=2)
        length_column.grid(row=2, column=2)
        apply.grid(row=3, column=0)
        cancel.grid(row=3, column=2)
        setting_root.mainloop()

    def close_window(self, side_root):
        side_root.destroy()
        side_root.quit()

    def put_cell(self, sum_row, length_row, sum_column, length_column, x, y,
                 root):
        try:
            row_rule = int(sum_row.get())
            column_rule = int(sum_column.get())
            row = int(length_row.get())
            column = int(length_column.get())
        except Exception as e:
            self.throw_exception('Argument error',
                                 'One or more argument are NaN', root)
            return
        if not self.check_arguments(row_rule, column_rule, row, column, x, y,
                                    root):
            return
        self.close_window(root)
        cell = Cell(CellType.RULES,
                    row_rule=row_rule,
                    column_rule=column_rule,
                    length_row=row,
                    length_column=column)
        self.game_field.init_cell(x, y, cell)
        self.redraw()

    def check_arguments(self, row_rule, column_rule, row, column, x, y,
                        setting_root):
        if column_rule > 45 or row_rule > 45:
            self.throw_exception('Argument error',
                                 'The amount can not exceed 45', setting_root)
            return False
        if row_rule < 0 or column_rule < 0 or row < 0 or column < 0:
            self.throw_exception('Argument error',
                                 'One or more argument less zero',
                                 setting_root)
            return False
        if x + column >= self.dimension:
            self.throw_exception('Argument error', 'Row length too large',
                                 setting_root)
            return False
        if y + row >= self.dimension:
            self.throw_exception('Argument error', 'Column length too large',
                                 setting_root)
            return False
        return True

    def redraw(self):
        for x in range(0, self.dimension):
            for y in range(0, self.dimension):
                if self.game_field.field[x][y].is_rules():
                    row = self.game_field.field[x][y].get_rules()[0]
                    column = self.game_field.field[x][y].get_rules()[1]
                    img = self.get_image_for_button(row, column)
                    self.list_button[x][y]['image'] = img
                if self.game_field.field[x][y].get_type() == CellType.PLAY:
                    value = self.game_field.field[x][y].get_value()
                    self.list_button[x][y][
                        'image'] = self.get_image_value_cell(value)
        self.root.update()

    def get_image_for_button(self, row, column):
        img = Image.new('RGB', (self.size_button, self.size_button), 'white')
        drawer = ImageDraw.Draw(img)
        if row > 0:
            to_str = str(int(row))
            numbers = self.count_number(row)
            drawer.text([self.size_button // 2, 0],
                        text=to_str[0:numbers],
                        fill='black',
                        align='center')
        if column > 0:
            to_str = str(int(column))[0:3]
            numbers = self.count_number(column)
            drawer.text([0, self.size_button // 2],
                        text=to_str[0:numbers],
                        fill='black')
        drawer.line([0, 0, self.size_button, self.size_button], 'black')
        p_img = ImageTk.PhotoImage(img)
        self.all_img.append(p_img)
        return p_img

    def count_number(self, n):
        i = 0
        while n > 0:
            n = n // 10
            i += 1
        return i

    def get_image_value_cell(self, value):
        img = Image.new('RGB', (self.size_button, self.size_button), 'white')
        drawer = ImageDraw.Draw(img)
        drawer.text([self.size_button // 2, self.size_button // 2],
                    text=str(value),
                    fill='black',
                    align='center')
        p_img = ImageTk.PhotoImage(img)
        self.all_img.append(p_img)
        return p_img

    def draw_menu(self):
        menu_bar = Menu(self.root)
        file_menu = Menu(menu_bar)
        file_menu.add_command(label='Create new kakuro',
                              command=self.start_setting)
        file_menu.add_command(label='Open from file',
                              command=self.open_from_file)
        file_menu.add_command(label="Save kakuro to image file",
                              command=self.save)
        menu_bar.add_cascade(label='File', menu=file_menu)
        solve_menu = Menu(menu_bar, tearoff=0)
        solve_menu.add_command(label='Solve', command=self.solve)
        menu_bar.add_cascade(label="Solution", menu=solve_menu)
        self.root.config(menu=menu_bar)

    def solve(self):
        solver = Solver(self.game_field)
        solution = solver.solve()
        if solution is None:
            return
        self.game_field.field = solution
        self.redraw()

    def start_setting(self):
        start_setting_root = Tk()
        start_setting_root.title('Create new kakuro')
        width = 15
        height = 2
        label_d = Label(start_setting_root,
                        text='Select the dimension',
                        width=width,
                        height=height)
        entry_d = Entry(start_setting_root, width=width)
        create_button = Button(start_setting_root,
                               width=width,
                               height=height,
                               text='Create')
        cancel = Button(start_setting_root,
                        width=width,
                        height=height,
                        text='Cancel')
        cancel['command'] = partial(self.close_window, start_setting_root)
        create_button['command'] = partial(self.start_new_kakuro, entry_d,
                                           start_setting_root)
        label_d.grid(row=0, column=0, padx=10)
        entry_d.grid(row=0, column=2)
        create_button.grid(row=1, column=0)
        cancel.grid(row=1, column=2)
        start_setting_root.mainloop()

    def start_new_kakuro(self, entry_dimension, start_root, dimension=0):
        try:
            if dimension == 0:
                dimension = int(entry_dimension.get())
        except Exception as e:
            self.throw_exception('Incorrect dimension', 'Dimension is NaN',
                                 start_root)
            return
        if dimension < 1:
            self.throw_exception('Incorrect dimension',
                                 'Dimension is less zero', start_root)
            return
        if dimension > 10:
            self.throw_exception('Incorrect dimension', 'Dimension too large',
                                 start_root)
            return
        self.init_new_kakuro(dimension)
        self.close_window(start_root)

    def init_new_kakuro(self, dimension):
        self.game_field = GameField(dimension, dimension)
        self.dimension = dimension
        self.all_img.clear()
        self.list_button.clear()
        self.draw_field()
        self.root.geometry("{0}x{1}".format(dimension * 70, dimension * 70))
        self.root.update()

    def throw_exception(self, title, msg, start_root):
        messagebox.showerror(title, msg)
        self.close_window(start_root)

    def open_from_file(self):
        open_file_path = filedialog.askopenfilename(
            title="Select file",
            defaultextension=".kk",
            filetypes=(('kk files', '*.kk'), ("all files", "*.*")))
        parser = Parser()
        if len(open_file_path) != 0:
            try:
                pairs = parser.parse(open_file_path)
            except exc.IncorrectFileArgument as e:
                messagebox.showerror('Incorrect file', e.msg)
                return
            except Exception as fe:
                messagebox.showerror('Incorrect file',
                                     'Unrecognized error in file')
                return
            dimension = pairs[0]
            self.init_new_kakuro(int(dimension))
            for cells in pairs[1:]:
                for key in cells.keys():
                    self.game_field.init_cell(key[0], key[1], cells[key])
                    self.redraw()

    def save(self):
        path = filedialog.asksaveasfile(mode='w',
                                        defaultextension='.png',
                                        filetypes=(('png files', '*.png'),
                                                   ("all files", "*.*")))
        if path is not None:
            painter = Painter(self.size_button)
            painter.paint(self.game_field.field, path.name, self.dimension)
Ejemplo n.º 8
0
class CommandLineMode:
    def __init__(self, dimension):
        self.game = GameField(dimension, dimension)
        self.dimansion = dimension
        self.all_line = []

    def add_cell(self, line):
        frame = line.split('|')
        if len(frame) != 6:
            print('Incorrect line')
            return
        try:
            pos_x = self.get_frame(frame[0])
            pos_y = self.get_frame(frame[1])
            row_sum = self.get_frame(frame[2])
            row_length = self.get_frame(frame[3])
            column_sum = self.get_frame(frame[4])
            column_length = self.get_frame(frame[5])
        except Exception as e:
            print('incorrect line')
            return
        cell = Cell(CellType.RULES,
                    row_rule=row_sum,
                    column_rule=column_sum,
                    length_row=row_length,
                    length_column=column_length)
        self.game.init_cell(pos_x, pos_y, cell)
        self.all_line.append(line)

    def get_frame(self, frame):
        return int(frame.rstrip().lstrip())

    def interpret(self, line):
        if ':' in line:
            command = line.split(':')[0].lstrip().rstrip()
            date = line.split(':')[1].lstrip().rstrip()
            if command == 'add':
                self.add_cell(date)
                return
            if command == 'save_png':
                self.save_png(date)
                return
            if command == 'save_kk':
                self.save_kk(date)
                return
        if line == 'solve':
            self.solve()
        print('Incorrect command')

    def save_png(self, path):
        if not path.endswith('.png'):
            path += '.png'
        pa = Painter(64)
        pa.paint(self.game.field, path, self.dimansion)

    def save_kk(self, date):
        if not date.endswith('kk'):
            date += '.kk'
        with open(date, 'w') as f:
            f.write(self.dimansion + '\n')
            for line in self.all_line:
                f.write(line + '\n')

    def solve(self):
        solver = Solver(self.game)
        try:
            solver.solve()
            print('Accepted')
        except Exception as e:
            print("Can not find solution")
Ejemplo n.º 9
0
def print_field(field):
    for x in range(0, len(field)):
        line = ""
        for y in range(0, len(field)):
            if field[x][y].get_type() == CellType.NO_ACTIVE:
                line += ' # \t'
            if field[x][y].get_type() == CellType.PLAY:
                line += ' ' + str(field[x][y].get_value()) + ' \t'
            if field[x][y].get_type() == CellType.RULES:
                line += ' ' + str(field[x][y].get_rules()[1]) + '\\' + str(
                    field[x][y].get_rules()[0]) + '\t'
        print(line)


if __name__ == '__main__':
    game = GameField(4, 4)
    #print_field(game.field)
    #print('===================================')
    game.init_cell(0, 1, Cell(CellType.RULES, column_rule=16, length_column=2))
    game.init_cell(0, 2, Cell(CellType.RULES, column_rule=15, length_column=3))
    game.init_cell(1, 0, Cell(CellType.RULES, row_rule=17, length_row=2))
    game.init_cell(2, 0, Cell(CellType.RULES, row_rule=15, length_row=3))
    game.init_cell(3, 1, Cell(CellType.RULES, row_rule=3, length_row=2))
    game.init_cell(1, 3, Cell(CellType.RULES, column_rule=4, length_column=2))
    print_field(game.field)
    #solver = Solver(game)
    #new_field = solver.solve()
    #print_field(new_field)
    print(tuple([1, 2, 3]))