Exemplo n.º 1
0
 def _process_computer_move(self, message):
     self.force_leds_off(log=True)  # can happen in case of a book move
     move = message.move
     ponder = message.ponder
     self.play_move = move
     self.play_fen = message.game.fen()
     self.play_turn = message.game.turn
     if ponder:
         game_copy = message.game.copy()
         game_copy.push(move)
         self.hint_move = ponder
         self.hint_fen = game_copy.fen()
         self.hint_turn = game_copy.turn
     else:
         self.hint_move = chess.Move.null()
         self.hint_fen = None
         self.hint_turn = None
     # Display the move
     side = self._get_clock_side(message.game.turn)
     beep = self.dgttranslate.bl(BeepLevel.CONFIG)
     disp = Dgt.DISPLAY_MOVE(move=move,
                             fen=message.game.fen(),
                             side=side,
                             wait=message.wait,
                             maxtime=0,
                             beep=beep,
                             devs={'ser', 'i2c', 'web'},
                             uci960=self.uci960,
                             lang=self.dgttranslate.language,
                             capital=self.dgttranslate.capital,
                             long=self.dgttranslate.notation)
     DgtObserver.fire(disp)
     DgtObserver.fire(
         Dgt.LIGHT_SQUARES(uci_move=move.uci(), devs={'ser', 'web'}))
     self.leds_are_on = True
Exemplo n.º 2
0
 def _exit_display(self, devs=None):
     if devs is None:  # prevent W0102 error
         devs = {'ser', 'i2c', 'web'}
     if self.play_move and self.dgtmenu.get_mode() in (Mode.NORMAL,
                                                       Mode.BRAIN,
                                                       Mode.REMOTE):
         side = self._get_clock_side(self.play_turn)
         beep = self.dgttranslate.bl(BeepLevel.BUTTON)
         text = Dgt.DISPLAY_MOVE(move=self.play_move,
                                 fen=self.play_fen,
                                 side=side,
                                 wait=True,
                                 maxtime=1,
                                 beep=beep,
                                 devs=devs,
                                 uci960=self.uci960,
                                 lang=self.dgttranslate.language,
                                 capital=self.dgttranslate.capital,
                                 long=self.dgttranslate.notation)
     else:
         text = None
         if self._inside_main_menu('dont_care_dev'):
             text = self.dgtmenu.get_current_text()
         if text:
             text.wait = True  # in case of "bad pos" message send before
         else:
             text = Dgt.DISPLAY_TIME(force=True, wait=True, devs=devs)
     DgtObserver.fire(text)
Exemplo n.º 3
0
 def _set_clock(self, side=ClockSide.NONE, devs=None):
     if devs is None:  # prevent W0102 error
         devs = {'ser', 'i2c', 'web'}
     time_left, time_right = self.time_control.get_internal_time(
         flip_board=self.dgtmenu.get_flip_board())
     DgtObserver.fire(
         Dgt.CLOCK_SET(time_left=time_left,
                       time_right=time_right,
                       devs=devs))
     DgtObserver.fire(Dgt.CLOCK_START(side=side, wait=True, devs=devs))
Exemplo n.º 4
0
 def _process_dgt_serial_nr(self):
     # logging.debug('Serial number {}'.format(message.number))  # actually used for watchdog (once a second)
     # molli: rolling display
     if not self._inside_main_menu():
         if self.dgtmenu.get_mode() == Mode.PONDER:
             if self.show_move_or_value >= self.dgtmenu.get_ponderinterval():
                 if self.hint_move:
                     side = self._get_clock_side(self.hint_turn)
                     beep = self.dgttranslate.bl(BeepLevel.NO)
                     text = Dgt.DISPLAY_MOVE(move=self.hint_move, fen=self.hint_fen, side=side, wait=True, maxtime=1,
                                             beep=beep, devs={'ser', 'i2c', 'web'}, uci960=self.uci960,
                                             lang=self.dgttranslate.language, capital=self.dgttranslate.capital,
                                             long=self.dgttranslate.notation)
                 else:
                     text = self.dgttranslate.text('N10_nomove')
             else:
                 text = self._combine_depth_and_score()
             text.wait = True
             DispatchDgt.fire(text)
             self.show_move_or_value = (self.show_move_or_value + 1) % (self.dgtmenu.get_ponderinterval() * 2)
         elif (self.dgtmenu.get_mode() == Mode.BRAIN and self.dgtmenu.get_rolldispbrain()) or (self.dgtmenu.get_mode() == Mode.NORMAL and self.dgtmenu.get_rolldispnorm()):
             #molli: allow rolling information display (time/score/hint_move) in BRAIN mode according to
             ##      ponder interval
             if self.play_move == chess.Move.null() and self.c_last_player == 'U':
                 if self.c_time_counter > 2 * self.dgtmenu.get_ponderinterval():
                     text = self._combine_depth_and_score()
                     text.wait = True
                     DispatchDgt.fire(text)
                     self.c_time_counter = (self.c_time_counter + 1) % (self.dgtmenu.get_ponderinterval() * 3)
                 elif self.c_time_counter > self.dgtmenu.get_ponderinterval():
                     if self.hint_move:
                         side = self._get_clock_side(self.hint_turn)
                         beep = self.dgttranslate.bl(BeepLevel.NO)
                         text = Dgt.DISPLAY_MOVE(move=self.hint_move, fen=self.hint_fen, side=side, wait=True, maxtime=1,
                                                 beep=beep, devs={'ser', 'i2c', 'web'}, uci960=self.uci960,
                                                 lang=self.dgttranslate.language, capital=self.dgttranslate.capital,
                                                 long=self.dgttranslate.notation)
                     else:
                         text = self.dgttranslate.text('N10_nomove')
                     text.wait = True
                     self.c_time_counter = (self.c_time_counter + 1) % (self.dgtmenu.get_ponderinterval() * 3)
                     DispatchDgt.fire(text)
                     if self.c_time_counter == 2 * self.dgtmenu.get_ponderinterval():
                         time.sleep(0.3)
                 else:
                     ## molli:  standard clock display
                     if self.c_time_counter == 0:
                         time.sleep(0.3)
                     self.c_time_counter = (self.c_time_counter + 1) % (self.dgtmenu.get_ponderinterval() * 3)
                     self._exit_display()
                     if self.c_time_counter == self.dgtmenu.get_ponderinterval():
                         time.sleep(0.3)
Exemplo n.º 5
0
 def _process_dgt_serial_nr(self):
     # logging.debug('Serial number {}'.format(message.number))  # actually used for watchdog (once a second)
     if self.dgtmenu.get_mode(
     ) == Mode.PONDER and not self._inside_main_menu('dont_care_dev'):
         if self.show_move_or_value >= self.dgtmenu.get_ponderinterval():
             if self.hint_move:
                 side = self._get_clock_side(self.hint_turn)
                 beep = self.dgttranslate.bl(BeepLevel.NO)
                 text = Dgt.DISPLAY_MOVE(move=self.hint_move,
                                         fen=self.hint_fen,
                                         side=side,
                                         wait=True,
                                         maxtime=1,
                                         beep=beep,
                                         devs={'ser', 'i2c', 'web'},
                                         uci960=self.uci960,
                                         lang=self.dgttranslate.language,
                                         capital=self.dgttranslate.capital,
                                         long=self.dgttranslate.notation)
             else:
                 text = self.dgttranslate.text('N10_nomove')
         else:
             text = self._combine_depth_and_score()
         text.wait = True
         DgtObserver.fire(text)
         self.show_move_or_value = (self.show_move_or_value + 1) % (
             self.dgtmenu.get_ponderinterval() * 2)
Exemplo n.º 6
0
 def _process_new_pv(self, message):
     self.hint_move = message.pv[0]
     self.hint_fen = message.game.fen()
     self.hint_turn = message.game.turn
     # if message.mode == Mode.ANALYSIS and not self._inside_main_menu('dont_care_dev'):
     if message.mode == Mode.ANALYSIS:
         devs = {
             None if self._inside_main_menu(dev) else dev
             for dev in {'ser', 'i2c', 'web'}
         }
         devs.discard(None)
         side = self._get_clock_side(self.hint_turn)
         beep = self.dgttranslate.bl(BeepLevel.NO)
         disp = Dgt.DISPLAY_MOVE(move=self.hint_move,
                                 fen=self.hint_fen,
                                 side=side,
                                 wait=True,
                                 maxtime=0,
                                 beep=beep,
                                 devs=devs,
                                 uci960=self.uci960,
                                 lang=self.dgttranslate.language,
                                 capital=self.dgttranslate.capital,
                                 long=self.dgttranslate.notation)
         if devs:
             DgtObserver.fire(disp)
Exemplo n.º 7
0
 def _exit_display(self):
     if self.play_move and self.dgtmenu.get_mode() in (Mode.NORMAL, Mode.BRAIN, Mode.REMOTE):
         side = self._get_clock_side(self.play_turn)
         beep = self.dgttranslate.bl(BeepLevel.BUTTON)
         text = Dgt.DISPLAY_MOVE(move=self.play_move, fen=self.play_fen, side=side, wait=True, maxtime=1,
                                 beep=beep, devs={'ser', 'i2c', 'web'}, uci960=self.uci960,
                                 lang=self.dgttranslate.language, capital=self.dgttranslate.capital)
     else:
         text = None
         if self._inside_main_menu():
             text = self.dgtmenu.get_current_text()
         if text:
             text.wait = True  # in case of "bad pos" message send before
         else:
             text = Dgt.DISPLAY_TIME(force=True, wait=True, devs={'ser', 'i2c', 'web'})
     DispatchDgt.fire(text)
Exemplo n.º 8
0
 def _process_button3(self, dev: str):
     logging.debug('(%s) clock handle button 3 press', dev)
     if self._inside_updt_menu(dev):
         DgtObserver.fire(
             self.dgtmenu.updt_right())  # button3 cant exit the menu
     elif self._inside_main_menu(dev):
         DgtObserver.fire(
             self.dgtmenu.main_right())  # button3 cant exit the menu
     else:
         if self.hint_move:
             side = self._get_clock_side(self.hint_turn)
             beep = self.dgttranslate.bl(BeepLevel.BUTTON)
             text = Dgt.DISPLAY_MOVE(move=self.hint_move,
                                     fen=self.hint_fen,
                                     side=side,
                                     wait=False,
                                     maxtime=1,
                                     beep=beep,
                                     devs={'ser', 'i2c', 'web'},
                                     uci960=self.uci960,
                                     lang=self.dgttranslate.language,
                                     capital=self.dgttranslate.capital,
                                     long=self.dgttranslate.notation)
         else:
             text = self.dgttranslate.text('B10_nomove')
         DgtObserver.fire(text)
         self._exit_display(devs={dev})
Exemplo n.º 9
0
 def _process_button0(self, dev):
     logging.debug('(%s) clock handle button 0 press', dev)
     if self._inside_main_menu():
         text = self.dgtmenu.main_up(
         )  # button0 can exit the menu, so check
         if text:
             DispatchDgt.fire(text)
         else:
             self._exit_display()
     elif self._inside_updt_menu():
         self.dgtmenu.updt_up(dev)
         self._exit_display()  # button0 always exit the menu
     else:
         if self.last_move:
             side = self._get_clock_side(self.last_turn)
             beep = self.dgttranslate.bl(BeepLevel.BUTTON)
             text = Dgt.DISPLAY_MOVE(move=self.last_move,
                                     fen=self.last_fen,
                                     side=side,
                                     wait=False,
                                     maxtime=1,
                                     beep=beep,
                                     devs={'ser', 'i2c', 'web'},
                                     uci960=self.uci960,
                                     lang=self.dgttranslate.language,
                                     capital=self.dgttranslate.capital,
                                     long=self.dgttranslate.notation)
         else:
             text = self.dgttranslate.text('B10_nomove')
         DispatchDgt.fire(text)
         self._exit_display()
Exemplo n.º 10
0
    def _stopped_maxtimer(self, dev: str):
        self.maxtimer_running[dev] = False
        self.dgtmenu.disable_picochess_displayed(dev)

        if dev not in self.devices:
            logging.debug('delete not registered (%s) tasks', dev)
            self.tasks[dev] = []
            return
        if self.tasks[dev]:
            logging.debug('processing delayed (%s) tasks: %s', dev,
                          self.tasks[dev])
        else:
            logging.debug(
                '(%s) max timer finished - returning to time display', dev)
            DgtDisplay.show(
                Dgt.DISPLAY_TIME(force=False, wait=True, devs={dev}))
        while self.tasks[dev]:
            logging.debug('(%s) tasks has %i members', dev,
                          len(self.tasks[dev]))
            try:
                message = self.tasks[dev].pop(0)
            except IndexError:
                break
            with self.process_lock[dev]:
                self._process_message(message, dev)
            if self.maxtimer_running[
                    dev]:  # run over the task list until a maxtime command was processed
                remaining = len(self.tasks[dev])
                if remaining:
                    logging.debug('(%s) tasks stopped on %i remaining members',
                                  dev, remaining)
                else:
                    logging.debug('(%s) tasks completed', dev)
                break
Exemplo n.º 11
0
    def _setup_serial_port(self):
        def _success(device: str):
            self.device = device
            logging.debug('(ser) board connected to %s', self.device)
            return True

        waitchars = ['/', '-', '\\', '|']

        if self.watchdog_timer.is_running():
            logging.debug('watchdog timer is stopped now')
            self.watchdog_timer.stop()
        if self.serial:
            return True
        with self.lock:
            if self.given_device:
                if self._open_serial(self.given_device):
                    return _success(self.given_device)
            else:
                for file in listdir('/dev'):
                    if file.startswith('ttyACM') or file.startswith('ttyUSB') or file == 'rfcomm0':
                        dev = path.join('/dev', file)
                        if self._open_serial(dev):
                            return _success(dev)
                if self._open_bluetooth():
                    return _success('/dev/rfcomm123')

        # text = self.dgttranslate.text('N00_noboard', 'Board' + waitchars[self.wait_counter])
        bwait = 'Board' + waitchars[self.wait_counter]
        text = Dgt.DISPLAY_TEXT(l='no e-' + bwait, m='no' + bwait, s=bwait, wait=True, beep=False, maxtime=0.1,
                                devs={'i2c', 'web'})
        MsgDisplay.show(Message.DGT_EBOARD_ERROR(text=text))
        self.wait_counter = (self.wait_counter + 1) % len(waitchars)
        return False
Exemplo n.º 12
0
 def force_leds_off(self, log=False):
     """Clear the rev2 lights if they still on."""
     if self.leds_are_on:
         if log:
             logging.warning('(rev) leds still on')
         DgtObserver.fire(Dgt.LIGHT_CLEAR(devs={'ser', 'web'}))
         self.leds_are_on = False
Exemplo n.º 13
0
def read_engine_ini(engine_shell=None, engine_path=None):
    """Read engines.ini and creates a library list out of it."""
    config = configparser.ConfigParser()
    config.optionxform = str
    try:
        if engine_shell is None:
            if not engine_path:
                program_path = os.path.abspath(
                    os.path.join(os.path.dirname(__file__), os.pardir))
                engine_path = program_path + os.sep + 'engines' + os.sep + platform.machine(
                )
            config.read(engine_path + os.sep + 'engines.ini')
        else:
            with engine_shell.open(engine_path + os.sep + 'engines.ini',
                                   'r') as file:
                config.read_file(file)
    except FileNotFoundError:
        pass

    library = []
    for section in config.sections():
        parser = configparser.ConfigParser()
        parser.optionxform = str

        level_dict = {}
        if engine_shell is None:
            success = parser.read(engine_path + os.sep + section + '.uci')
        else:
            try:
                with engine_shell.open(engine_path + os.sep + section + '.uci',
                                       'r') as file:
                    parser.read_file(file)
                success = True
            except FileNotFoundError:
                success = False
        if success:
            for p_section in parser.sections():
                level_dict[p_section] = {}
                for option in parser.options(p_section):
                    level_dict[p_section][option] = parser[p_section][option]

        confsect = config[section]
        text = Dgt.DISPLAY_TEXT(l=confsect['large'],
                                m=confsect['medium'],
                                s=confsect['small'],
                                wait=True,
                                beep=False,
                                maxtime=0,
                                devs={'ser', 'i2c', 'web'})
        library.append({
            'file': engine_path + os.sep + section,
            'level_dict': level_dict,
            'text': text,
            'name': confsect['name'],
            'elo': confsect['elo']
        })
    return library
Exemplo n.º 14
0
 def _process_new_pv(self, message):
     self.hint_move = message.pv[0]
     self.hint_fen = message.game.fen()
     self.hint_turn = message.game.turn
     if message.mode == Mode.ANALYSIS and not self._inside_main_menu():
         side = self._get_clock_side(self.hint_turn)
         beep = self.dgttranslate.bl(BeepLevel.NO)
         disp = Dgt.DISPLAY_MOVE(move=self.hint_move, fen=self.hint_fen, side=side, wait=True, maxtime=0,
                                 beep=beep, devs={'ser', 'i2c', 'web'}, uci960=self.uci960,
                                 lang=self.dgttranslate.language, capital=self.dgttranslate.capital)
         DispatchDgt.fire(disp)
Exemplo n.º 15
0
def get_opening_books():
    """Build an opening book lib."""
    config = configparser.ConfigParser()
    config.optionxform = str
    program_path = os.path.dirname(os.path.realpath(__file__)) + os.sep
    book_path = program_path + 'books'
    config.read(book_path + os.sep + 'books.ini')

    library = []
    for section in config.sections():
        text = Dgt.DISPLAY_TEXT(l=config[section]['large'],
                                m=config[section]['medium'],
                                s=config[section]['small'],
                                wait=True,
                                beep=False,
                                maxtime=0,
                                devs={'ser', 'i2c', 'web'})
        library.append({'file': 'books' + os.sep + section, 'text': text})
    return library
Exemplo n.º 16
0
    def _process_board_message(self, message_id: int, message: tuple,
                               message_length: int):
        if False:  # switch-case
            pass
        elif message_id == DgtMsg.DGT_MSG_VERSION:
            if message_length != 2:
                logging.warning('illegal length in data')
            board_version = str(message[0]) + '.' + str(message[1])
            logging.debug('(ser) board version %0.2f', float(board_version))
            self.write_command([DgtCmd.DGT_SEND_BRD
                                ])  # Update the board => get first FEN
            if self.device.find('rfc') == -1:
                text_l, text_m, text_s = 'USB e-Board', 'USBboard', 'ok usb'
                self.channel = 'USB'
            else:
                btname5 = self.bt_name[-5:]
                if 'REVII' in self.bt_name:
                    text_l, text_m, text_s = 'RevII ' + btname5, 'Rev' + btname5, 'b' + btname5
                    self.is_revelation = True
                    self.write_command([DgtCmd.DGT_RETURN_LONG_SERIALNR])
                elif 'DGT_BT' in self.bt_name:
                    text_l, text_m, text_s = 'DGTBT ' + btname5, 'BT ' + btname5, 'b' + btname5
                else:
                    text_l, text_m, text_s = 'BT e-Board', 'BT board', 'ok bt'
                self.channel = 'BT'
                self.ask_battery_status()
            self.bconn_text = Dgt.DISPLAY_TEXT(l=text_l,
                                               m=text_m,
                                               s=text_s,
                                               wait=True,
                                               beep=False,
                                               maxtime=1.1,
                                               devs={'i2c', 'web'
                                                     })  # serial clock lateron
            DisplayMsg.show(
                Message.DGT_EBOARD_VERSION(text=self.bconn_text,
                                           channel=self.channel))
            self.startup_serial_clock()  # now ask the serial clock to answer
            if self.watchdog_timer.is_running():
                logging.warning('watchdog timer is already running')
            else:
                logging.debug('watchdog timer is started')
                self.watchdog_timer.start()

        elif message_id == DgtMsg.DGT_MSG_BWTIME:
            if message_length != 7:
                logging.warning('illegal length in data')
            if ((message[0] & 0x0f) == 0x0a) or ((message[3] & 0x0f)
                                                 == 0x0a):  # Clock ack message
                # Construct the ack message
                ack0 = ((message[1]) & 0x7f) | ((message[3] << 3) & 0x80)
                ack1 = ((message[2]) & 0x7f) | ((message[3] << 2) & 0x80)
                ack2 = ((message[4]) & 0x7f) | ((message[0] << 3) & 0x80)
                ack3 = ((message[5]) & 0x7f) | ((message[0] << 2) & 0x80)
                if ack0 != 0x10:
                    logging.warning('(ser) clock ACK error %s',
                                    (ack0, ack1, ack2, ack3))
                    if self.last_clock_command:
                        logging.debug(
                            '(ser) clock resending failed message [%s]',
                            self.last_clock_command)
                        self.write_command(self.last_clock_command)
                        self.last_clock_command = []  # only resend once
                    return
                else:
                    logging.debug('(ser) clock ACK okay [%s]', DgtAck(ack1))
                    if self.last_clock_command:
                        cmd = self.last_clock_command[3]  # type: DgtClk
                        if cmd.value != ack1 and ack1 < 0x80:
                            logging.warning(
                                '(ser) clock ACK [%s] out of sync - last: [%s]',
                                DgtAck(ack1), cmd)
                # @todo these lines are better as what is done on DgtHw but it doesnt work
                # if ack1 == DgtAck.DGT_ACK_CLOCK_SETNRUN.value:
                #     logging.info('(ser) clock out of set time now')
                #     self.in_settime = False
                if ack1 == DgtAck.DGT_ACK_CLOCK_BUTTON.value:
                    # this are the other (ack2-ack3) codes
                    # 05-49 33-52 17-51 09-50 65-53 | button 0-4 (single)
                    #       37-52 21-51 13-50 69-53 | button 0 + 1-4
                    #             49-51 41-50 97-53 | button 1 + 2-4
                    #                   25-50 81-53 | button 2 + 3-4
                    #                         73-53 | button 3 + 4
                    if ack3 == 49:
                        logging.info('(ser) clock button 0 pressed - ack2: %i',
                                     ack2)
                        DisplayMsg.show(Message.DGT_BUTTON(button=0,
                                                           dev='ser'))
                    if ack3 == 52:
                        logging.info('(ser) clock button 1 pressed - ack2: %i',
                                     ack2)
                        DisplayMsg.show(Message.DGT_BUTTON(button=1,
                                                           dev='ser'))
                    if ack3 == 51:
                        logging.info('(ser) clock button 2 pressed - ack2: %i',
                                     ack2)
                        DisplayMsg.show(Message.DGT_BUTTON(button=2,
                                                           dev='ser'))
                    if ack3 == 50:
                        logging.info('(ser) clock button 3 pressed - ack2: %i',
                                     ack2)
                        DisplayMsg.show(Message.DGT_BUTTON(button=3,
                                                           dev='ser'))
                    if ack3 == 53:
                        if ack2 == 69:
                            logging.info(
                                '(ser) clock button 0+4 pressed - ack2: %i',
                                ack2)
                            DisplayMsg.show(
                                Message.DGT_BUTTON(button=0x11, dev='ser'))
                        else:
                            logging.info(
                                '(ser) clock button 4 pressed - ack2: %i',
                                ack2)
                            DisplayMsg.show(
                                Message.DGT_BUTTON(button=4, dev='ser'))
                if ack1 == DgtAck.DGT_ACK_CLOCK_VERSION.value:
                    self.enable_ser_clock = True
                    main = ack2 >> 4
                    sub = ack2 & 0x0f
                    logging.debug('(ser) clock version %0.2f',
                                  float(str(main) + '.' + str(sub)))
                    if self.bconn_text:
                        self.bconn_text.devs = {
                            'ser'
                        }  # Now send the (delayed) message to serial clock
                        dev = 'ser'
                    else:
                        dev = 'err'
                    DisplayMsg.show(
                        Message.DGT_CLOCK_VERSION(main=main,
                                                  sub=sub,
                                                  dev=dev,
                                                  text=self.bconn_text))
            elif any(message[:7]):
                r_hours = message[0] & 0x0f
                r_mins = (message[1] >> 4) * 10 + (message[1] & 0x0f)
                r_secs = (message[2] >> 4) * 10 + (message[2] & 0x0f)
                l_hours = message[3] & 0x0f
                l_mins = (message[4] >> 4) * 10 + (message[4] & 0x0f)
                l_secs = (message[5] >> 4) * 10 + (message[5] & 0x0f)
                r_time = r_hours * 3600 + r_mins * 60 + r_secs
                l_time = l_hours * 3600 + l_mins * 60 + l_secs
                errtim = r_hours > 9 or l_hours > 9 or r_mins > 59 or l_mins > 59 or r_secs > 59 or l_secs > 59
                if errtim:  # complete illegal package received
                    logging.warning('(ser) clock illegal new time received %s',
                                    message)
                elif r_time > self.r_time or l_time > self.l_time:  # the new time is higher as the old => ignore
                    logging.warning(
                        '(ser) clock strange old time received %s l:%s r:%s',
                        message, hms_time(self.l_time), hms_time(self.r_time))
                    if self.in_settime:
                        logging.info(
                            '(ser) clock still in set mode, ignore received time'
                        )
                        errtim = True
                    elif r_time - self.r_time > 3600 or l_time - self.l_time > 3600:
                        logging.info(
                            '(ser) clock new time over 1h difference, ignore received time'
                        )
                        errtim = True
                else:
                    logging.info('(ser) clock new time received l:%s r:%s',
                                 hms_time(l_time), hms_time(r_time))
                    status = message[6] & 0x3f
                    connect = not status & 0x20
                    if connect:
                        right_side_down = -0x40 if status & 0x02 else 0x40
                        if self.lever_pos != right_side_down:
                            logging.debug(
                                '(ser) clock button status: 0x%x old lever: %s',
                                status, self.lever_pos)
                            if self.lever_pos is not None:
                                DisplayMsg.show(
                                    Message.DGT_BUTTON(button=right_side_down,
                                                       dev='ser'))
                            self.lever_pos = right_side_down
                    else:
                        logging.info(
                            '(ser) clock not connected, sending old time l:%s r:%s',
                            hms_time(self.l_time), hms_time(self.r_time))
                        l_time = self.l_time
                        r_time = self.r_time
                    if self.in_settime:
                        logging.info(
                            '(ser) clock still in set mode, sending old time l:%s r:%s',
                            hms_time(self.l_time), hms_time(self.r_time))
                        l_time = self.l_time
                        r_time = self.r_time
                    DisplayMsg.show(
                        Message.DGT_CLOCK_TIME(time_left=l_time,
                                               time_right=r_time,
                                               connect=connect,
                                               dev='ser'))
                    if not self.enable_ser_clock:
                        dev = 'rev' if 'REVII' in self.bt_name else 'ser'
                        if self.watchdog_timer.is_running(
                        ):  # a running watchdog means: board already found
                            logging.info('(%s) clock restarting setup', dev)
                            self.startup_serial_clock()
                        else:
                            logging.info(
                                '(%s) clock sends messages already but (%s) board still not found',
                                dev, dev)
                if not errtim:
                    self.r_time = r_time
                    self.l_time = l_time
            else:
                logging.debug('(ser) clock null message ignored')
            if self.clock_lock:
                logging.debug('(ser) clock unlocked after %.3f secs',
                              time.time() - self.clock_lock)
                self.clock_lock = False

        elif message_id == DgtMsg.DGT_MSG_BOARD_DUMP:
            if message_length != 64:
                logging.warning('illegal length in data')
            piece_to_char = {
                0x01: 'P',
                0x02: 'R',
                0x03: 'N',
                0x04: 'B',
                0x05: 'K',
                0x06: 'Q',
                0x07: 'p',
                0x08: 'r',
                0x09: 'n',
                0x0a: 'b',
                0x0b: 'k',
                0x0c: 'q',
                0x0d: '$',
                0x0e: '%',
                0x0f: '&',
                0x00: '.'
            }
            board = ''
            for character in message:
                board += piece_to_char[character & 0x0f]
            logging.debug('\n' + '\n'.join(
                board[0 + i:8 + i]
                for i in range(0, len(board), 8)))  # Show debug board
            # Create fen from board
            fen = ''
            empty = 0
            for square in range(0, 64):
                if message[square] != 0 and message[
                        square] < 0x0d:  # @todo for the moment ignore the special pieces
                    if empty > 0:
                        fen += str(empty)
                        empty = 0
                    fen += piece_to_char[message[square] & 0x0f]
                else:
                    empty += 1
                if (square + 1) % 8 == 0:
                    if empty > 0:
                        fen += str(empty)
                        empty = 0
                    if square < 63:
                        fen += '/'

            # Attention! This fen is NOT flipped
            logging.debug('raw fen [%s]', fen)
            DisplayMsg.show(Message.DGT_FEN(fen=fen, raw=True))

        elif message_id == DgtMsg.DGT_MSG_FIELD_UPDATE:
            if message_length != 2:
                logging.warning('illegal length in data')
            if self.field_timer_running:
                self.stop_field_timer()
            self.start_field_timer()

        elif message_id == DgtMsg.DGT_MSG_SERIALNR:
            if message_length != 5:
                logging.warning('illegal length in data')
            DisplayMsg.show(
                Message.DGT_SERIAL_NR(
                    number=''.join([chr(elem) for elem in message])))

        elif message_id == DgtMsg.DGT_MSG_LONG_SERIALNR:
            if message_length != 10:
                logging.warning('illegal length in data')
            number = ''.join([chr(elem) for elem in message])
            self.enable_revelation_pi = float(
                number[:4]) >= 3.25  # "3.250010001"=yes "0000000001"=no
            logging.info('(rev) clock in PiMode: %s - serial: %s',
                         'yes' if self.enable_revelation_pi else 'no', number)

        elif message_id == DgtMsg.DGT_MSG_BATTERY_STATUS:
            if message_length != 9:
                logging.warning('illegal length in data')
            DisplayMsg.show(Message.BATTERY(percent=message[0]))

        else:  # Default
            logging.warning('message not handled [%s]', DgtMsg(message_id))
Exemplo n.º 17
0
    def _process_message(self, message):
        if False:  # switch-case
            pass

        elif isinstance(message, Message.ENGINE_READY):
            self._process_engine_ready(message)

        elif isinstance(message, Message.ENGINE_STARTUP):
            self._process_engine_startup(message)

        elif isinstance(message, Message.ENGINE_FAIL):
            DgtObserver.fire(self.dgttranslate.text('Y10_erroreng'))
            self.dgtmenu.set_engine_restart(False)

        elif isinstance(message, Message.COMPUTER_MOVE):
            self._process_computer_move(message)

        elif isinstance(message, Message.NEW_GAME):
            self._process_new_game(message)

        elif isinstance(message, Message.COMPUTER_MOVE_DONE):
            self._process_computer_move_done()

        elif isinstance(message, Message.USER_MOVE_DONE):
            self._process_user_move_done(message)

        elif isinstance(message, Message.REVIEW_MOVE_DONE):
            self._process_review_move_done(message)

        elif isinstance(message, Message.ALTERNATIVE_MOVE):
            self.force_leds_off()
            self.play_mode = message.play_mode
            DgtObserver.fire(self.dgttranslate.text('B05_altmove'))

        elif isinstance(message, Message.NEW_LEVEL):
            if not self.dgtmenu.get_engine_restart():
                DgtObserver.fire(message.level_text)

        elif isinstance(message, Message.TIME_CONTROL):
            self._process_time_control(message)

        elif isinstance(message, Message.NEW_BOOK):
            if not self.dgtmenu.get_confirm() or not message.show_ok:
                DgtObserver.fire(message.book_text)

        elif isinstance(message, Message.TAKE_BACK):
            self.force_leds_off()
            self._reset_moves_and_score()
            DgtObserver.fire(self.dgttranslate.text('C10_takeback'))
            DgtObserver.fire(
                Dgt.DISPLAY_TIME(force=True,
                                 wait=True,
                                 devs={'ser', 'i2c', 'web'}))

        elif isinstance(message, Message.GAME_ENDS):
            if not self.dgtmenu.get_engine_restart(
            ):  # filter out the shutdown/reboot process
                text = self.dgttranslate.text(message.result.value)
                text.beep = self.dgttranslate.bl(BeepLevel.CONFIG)
                text.maxtime = 0.5
                DgtObserver.fire(text)
                if self.dgtmenu.get_mode() == Mode.PONDER:
                    self._reset_moves_and_score()
                    text.beep = False
                    text.maxtime = 1
                    self.score = text

        elif isinstance(message, Message.INTERACTION_MODE):
            if not self.dgtmenu.get_confirm() or not message.show_ok:
                DgtObserver.fire(message.mode_text)

        elif isinstance(message, Message.PLAY_MODE):
            self.play_mode = message.play_mode
            DgtObserver.fire(message.play_mode_text)

        elif isinstance(message, Message.NEW_SCORE):
            self._process_new_score(message)

        elif isinstance(message, Message.BOOK_MOVE):
            self.score = self.dgttranslate.text('N10_score', None)
            DgtObserver.fire(self.dgttranslate.text('N10_bookmove'))

        elif isinstance(message, Message.NEW_PV):
            self._process_new_pv(message)

        elif isinstance(message, Message.NEW_DEPTH):
            self.depth = message.depth

        elif isinstance(message, Message.IP_INFO):
            self.dgtmenu.int_ip = message.info['int_ip']
            self.dgtmenu.ext_ip = message.info['ext_ip']

        elif isinstance(message, Message.STARTUP_INFO):
            self._process_startup_info(message)

        elif isinstance(message, Message.SEARCH_STARTED):
            logging.debug('search started')

        elif isinstance(message, Message.SEARCH_STOPPED):
            logging.debug('search stopped')

        elif isinstance(message, Message.CLOCK_START):
            self._process_clock_start(message)

        elif isinstance(message, Message.CLOCK_STOP):
            DgtObserver.fire(Dgt.CLOCK_STOP(devs=message.devs, wait=True))

        elif isinstance(message, Message.DGT_BUTTON):
            self._process_button(message)

        elif isinstance(message, Message.DGT_FEN):
            if self.dgtmenu.inside_updt_menu():
                logging.debug('inside update menu => ignore fen %s',
                              message.fen)
            else:
                self._process_fen(message.fen, message.raw)

        elif isinstance(message, Message.DGT_CLOCK_VERSION):
            DgtObserver.fire(
                Dgt.CLOCK_VERSION(main=message.main,
                                  sub=message.sub,
                                  devs={message.dev}))
            text = self.dgttranslate.text('Y21_picochess', devs={message.dev})
            text.rd = ClockIcons.DOT
            DgtObserver.fire(text)

            if message.dev == 'ser':  # send the "board connected message" to serial clock
                DgtObserver.fire(message.text)
            self._set_clock(devs={message.dev})
            self._exit_display(devs={message.dev})

        elif isinstance(message, Message.DGT_CLOCK_TIME):
            time_white = message.time_left
            time_black = message.time_right
            if self.dgtmenu.get_flip_board():
                time_white, time_black = time_black, time_white
            EvtObserver.fire(
                Event.CLOCK_TIME(time_white=time_white,
                                 time_black=time_black,
                                 connect=message.connect,
                                 dev=message.dev))

        elif isinstance(message, Message.CLOCK_TIME):
            self.low_time = message.low_time
            if self.low_time:
                logging.debug('time too low, disable confirm - w: %i, b: %i',
                              message.time_white, message.time_black)

        elif isinstance(message, Message.DGT_SERIAL_NR):
            self._process_dgt_serial_nr()

        elif isinstance(message, Message.DGT_JACK_ERROR
                        ):  # only working in case of 2 clocks connected!
            DgtObserver.fire(self.dgttranslate.text('Y00_errorjack'))

        elif isinstance(message, Message.DGT_EBOARD_VERSION):
            if self.dgtmenu.inside_updt_menu():
                logging.debug(
                    'inside update menu => board channel not displayed')
            else:
                DgtObserver.fire(message.text)
                self._exit_display(devs={'i2c', 'web'
                                         })  # ser is done, when clock found

        elif isinstance(message, Message.DGT_EBOARD_ERROR):
            if self.dgtmenu.inside_updt_menu(
            ) or self.dgtmenu.inside_main_menu():
                logging.debug('inside menu => board error not displayed')
            else:
                DgtObserver.fire(message.text)

        elif isinstance(message, Message.DGT_CLOCK_ERROR):
            pass

        elif isinstance(message, Message.SWITCH_SIDES):
            self.play_move = chess.Move.null()
            self.play_fen = None
            self.play_turn = None

            self.hint_move = chess.Move.null()
            self.hint_fen = None
            self.hint_turn = None
            self.force_leds_off()
            logging.debug('user ignored move %s', message.move)

        elif isinstance(message, Message.EXIT_MENU):
            self._exit_display(devs={message.dev})

        elif isinstance(message, Message.WRONG_FEN):
            DgtObserver.fire(self.dgttranslate.text('C10_setpieces'))

        elif isinstance(message, Message.BATTERY_BT):
            if message.percent == 0x7f:
                percent = ' NA'
            elif message.percent > 99:
                percent = ' 99'
            else:
                percent = str(message.percent)
            self.dgtmenu.battery = percent

        elif isinstance(message, Message.REMOTE_ROOM):
            self.dgtmenu.inside_room = message.inside

        else:  # Default
            pass