curses.addch returning error but not indicating why

37 Views Asked by At

I'm writing a game in curses and for some reason I keep getting an error when trying to write to terminal. Previously I did not have a problem making the game boards in terminal. This issue started after I got the networking protocol written up. Here is my function:

def draw_player_board(stdscr, onion_address, max_y, max_x):
    try:
        # Fetch all players' data
        all_players_data = sorted(PLAYERS.values(), key=lambda x: x['player_id'] != onion_address)
        
        for player_data in all_players_data:
            cursor_positions = player_data["cursor_positions"]
            selected_color = player_data["selected_color"]
            grid = player_data["grid"]
            top_left_x = player_data["top_left_x"]
            top_left_y = player_data["top_left_y"]
            
            # Draw the grid border for the player's grid
            for i in range(GRID_ROWS + 2):
                if top_left_y + i < max_y:
                    if top_left_x - 1 >= 0:
                        logging.info(f"addch {top_left_y + i}, {top_left_x - 1} |")
                        ret = stdscr.addch(top_left_y + i, top_left_x - 1, '|')
                    if top_left_x + GRID_COLS < max_x:
                        logging.info(f"addch {top_left_y + i}, {top_left_x + GRID_COLS} |")
                        ret = stdscr.addch(top_left_y + i, top_left_x + GRID_COLS, '|')
            for i in range(GRID_COLS + 2):
                if top_left_y - 1 >= 0 and top_left_x + i < max_x:
                        logging.info(f"addch {top_left_y - 1}, {top_left_x + i}, _")
                        ret = stdscr.addch(top_left_y - 1, top_left_x + i, '_')
                if top_left_y + GRID_ROWS < max_y and top_left_x + i < max_x:
                        logging.info(f"addch {top_left_y + GRID_ROWS}, {top_left_x + i}, _")
                        ret = stdscr.addch(top_left_y + GRID_ROWS, top_left_x + i, '_')

            for col in range(GRID_ROWS):
                for row in range(GRID_COLS):
                    cell_x, cell_y = row + top_left_x, col + top_left_y
                    if (cell_x >= top_left_x and cell_x < top_left_x + GRID_COLS and
                        cell_y >= top_left_y and cell_y < top_left_y + GRID_ROWS):
                        if grid[col][row] != -1:
                            if cell_y < max_y and cell_x < max_x:
                                ret = stdscr.addch(cell_y, cell_x, "█", curses.color_pair(COLORS[grid[col][row]]))
                                logging.info(f"addch return value: {ret}")
                                player_data["top_left_x"] = cell_x
                                player_data["top_left_y"] = cell_y
                        else:
                            if cell_y < max_y and cell_x < max_x:
                                ret = stdscr.addch(cell_y, cell_x, " ")
                                logging.info(f"addch return value: {ret}")

            # Draw the player's cursor
            for cursor_position in cursor_positions:
                cursor_x, cursor_y = cursor_position
                if (cursor_x >= top_left_x and cursor_x < top_left_x + GRID_COLS and
                    cursor_y >= top_left_y and cursor_y < top_left_y + GRID_ROWS):
                    if cursor_y < max_y and cursor_x < max_x:
                        ret = stdscr.addch(cursor_y, cursor_x, "█", curses.color_pair(COLORS[selected_color]))
                        logging.info(f"addch return value: {ret}")
                else:
                    logging.info("Cursor outside of board bounds")
    except curses.error as curses_err:
        exc_type, exc_obj, exc_tb = sys.exc_info()
        fname = os.path.split(exc_tb.tb_frame.f_code.co_filename)[1]
        logging.info(f"Error in draw_player_board: {exc_type}, {fname}, {exc_tb.tb_lineno}, {curses_err}")
    except Exception as e:
        exc_type, exc_obj, exc_tb = sys.exc_info()
        fname = os.path.split(exc_tb.tb_frame.f_code.co_filename)[1]
        logging.info(f"Error in draw_player_board: {exc_type}, {fname}, {exc_tb.tb_lineno}, {e}")

and the error:

INFO:root:addch 74, 0, _
INFO:root:Error in draw_player_board: <class '_curses.error'>, 
Line 962, add_wch() returned ERR

Here is my updated code:


def draw_player_board(stdscr, onion_address, max_y, max_x, scroll_position):
    try:
        # Ensure scroll_position is initialized
        if scroll_position is None:
            scroll_position = 0

        # Fetch all players' data
        all_players_data = sorted(PLAYERS.values(), key=lambda x: x['player_id'] != onion_address)
        # Determine the start and stop indices for the visible area
        start_index = max(scroll_position, 0)
        stop_index = min(scroll_position + max_y - 2, len(PLAYERS) * (GRID_ROWS + 2))

        # Create the visible_area slice
        visible_area = slice(start_index, stop_index, 1)
        logging.info(f"visible_area: {visible_area}")

        # Determine the visible area based on the scroll position
        top_row = max(0, scroll_position)
        bottom_row = min(len(PLAYERS) * (GRID_ROWS + 2), max_y + scroll_position)
        
        for player_data in all_players_data:
            cursor_positions = player_data["cursor_positions"]
            selected_color = player_data["selected_color"]
            grid = player_data["grid"]
            top_left_x = player_data["top_left_x"]
            top_left_y = player_data["top_left_y"]
            # Calculate the indices of all border cells in a single line

            # Draw the grid content
            for col in range(visible_area.start, visible_area.stop, visible_area.step):
                for row in range(GRID_COLS):
                    cell_x, cell_y = row + top_left_x, col + top_left_y
                    if (cell_x >= top_left_x and cell_x < top_left_x + GRID_COLS and
                        cell_y >= top_row and cell_y < bottom_row):
                        if grid[col][row] > 0:
                            stdscr.addch(cell_y - scroll_position, cell_x, "█", curses.color_pair(COLORS[grid[col][row]]))
                        elif grid[col][row] == -1:
                            stdscr.addch(cell_y - scroll_position, cell_x, " ")

            # Draw the player's cursor
            for cursor_position in cursor_positions:
                cursor_x, cursor_y = cursor_position
                if (cursor_x >= top_left_x and cursor_x < top_left_x + GRID_COLS and
                    cursor_y >= top_row and cursor_y < bottom_row):
                    stdscr.addch(cursor_y - scroll_position, cursor_x, "█", curses.color_pair(COLORS[selected_color]))
                else:
                    logging.info("Cursor outside of board bounds")


    except curses.error as curses_err:
        logging.error(f"Error in draw_player_board: {curses_err}")
    except Exception as e:
        exc_type, exc_obj, exc_tb = sys.exc_info()
        fname = os.path.split(exc_tb.tb_frame.f_code.co_filename)[1]
        logging.info(f"Error in draw_player_board: {exc_type}, {fname}, {exc_tb.tb_lineno}, {e}")


Currently I'm trying to integrate the following solution but it's still erroring out. I have tried changing the size of the game board to be something smaller. But it doesn't seem to change the error:

            # Left border
            for left_index in [(i, top_left_x - 1) for i in range(top_row, bottom_row)]:
                stdscr.addch(left_index[0], left_index[1], "|")
            # Right border
            for right_index in [(i, top_left_x + GRID_COLS) for i in range(top_row, bottom_row)]:
                stdscr.addch(right_index[0], right_index[1], "|")
            # Top border
            for top_index in [(top_left_y - scroll_position, i) for i in range(top_left_x, top_left_x + GRID_COLS + 1)]:
                stdscr.addch(top_index[0], top_index[1], "-")
            # Bottom border
            for bottom_index in [(top_left_y + GRID_ROWS - scroll_position, i) for i in range(top_left_x, top_left_x + GRID_COLS + 1)]:
                stdscr.addch(bottom_index[0], bottom_index[1], "-")


0

There are 0 best solutions below