def _name_for_location(world_list: WorldList, location: AreaIdentifier) -> str:
    loc = location.as_tuple
    if loc in prime1_elevators.RANDOM_PRIME_CUSTOM_NAMES and loc != (
            "Frigate Orpheon", "Exterior Docking Hangar"):
        return prime1_elevators.RANDOM_PRIME_CUSTOM_NAMES[loc]
    else:
        return world_list.area_name(world_list.area_by_area_location(location),
                                    separator=":")
Exemple #2
0
def distances_to_node(world_list: WorldList, starting_node: Node,
                      *,
                      ignore_elevators: bool = True,
                      cutoff: Optional[int] = None,
                      patches: Optional[GamePatches] = None,
                      ) -> Dict[Area, int]:
    """
    Compute the shortest distance from a node to all reachable areas.
    :param world_list:
    :param starting_node:
    :param ignore_elevators:
    :param cutoff: Exclude areas with a length longer that cutoff.
    :param patches:
    :return: Dict keyed by area to shortest distance to starting_node.
    """
    import networkx
    g = networkx.DiGraph()

    if patches is None:
        def get_elevator_connection_for(n: TeleporterNode):
            return n.default_connection

        def get_dock_connection_for(n: DockNode):
            return n.default_connection
    else:
        get_elevator_connection_for = patches.get_elevator_connection_for

        def get_dock_connection_for(n: DockNode):
            return patches.get_dock_connection_for(n).identifier

    for area in world_list.all_areas:
        g.add_node(area)

    for world in world_list.worlds:
        for area in world.areas:
            new_areas = set()
            for node in area.nodes:
                connection = None
                if isinstance(node, DockNode):
                    connection = get_dock_connection_for(node).area_identifier

                elif isinstance(node, TeleporterNode) and not ignore_elevators:
                    connection = get_elevator_connection_for(node)

                if connection is not None:
                    new_areas.add(world_list.area_by_area_location(connection))

            for next_area in new_areas:
                g.add_edge(area, next_area)

    return networkx.single_source_shortest_path_length(g, world_list.nodes_to_area(starting_node), cutoff)
Exemple #3
0
def _get_elevator_or_area_name(custom_names_to_use: dict[RandovaniaGame,
                                                         dict[tuple[str, str],
                                                              str]],
                               game: RandovaniaGame, world_list: WorldList,
                               area_location: AreaIdentifier,
                               include_world_name: bool) -> str:
    custom_names_by_game = custom_names_to_use.get(game, {})

    area_loc = area_location.as_tuple
    if area_loc in custom_names_by_game:
        return custom_names_by_game[area_loc]

    else:
        area = world_list.area_by_area_location(area_location)

        if include_world_name:
            return world_list.area_name(area)
        else:
            return area.name
Exemple #4
0
def pretty_print_node_type(node: Node, world_list: WorldList):
    if isinstance(node, DockNode):
        try:
            other = world_list.node_by_identifier(node.default_connection)
            other_name = world_list.node_name(other)
        except IndexError as e:
            other_name = (f"(Area {node.default_connection.area_name}, "
                          f"index {node.default_connection.node_name}) [{e}]")

        return f"{node.default_dock_weakness.name} to {other_name}"

    elif isinstance(node, TeleporterNode):
        other = world_list.area_by_area_location(node.default_connection)
        return f"Teleporter to {world_list.area_name(other)}"

    elif isinstance(node, PickupNode):
        return f"Pickup {node.pickup_index.index}; Major Location? {node.major_location}"

    elif isinstance(node, EventNode):
        return f"Event {node.event.long_name}"

    elif isinstance(node, ConfigurableNode):
        return f"Configurable Node"

    elif isinstance(node, LogbookNode):
        message = ""
        if node.lore_type == LoreType.REQUIRES_ITEM:
            message = f" ({node.required_translator.long_name})"
        return f"Logbook {node.lore_type.long_name}{message} for {node.string_asset_id:x}"

    elif isinstance(node, PlayerShipNode):
        unlocked_pretty = list(pretty_print_requirement(node.is_unlocked))
        if len(unlocked_pretty) > 1:
            unlocked_by = "Complex requirement"
        else:
            unlocked_by = unlocked_pretty[0][1]
        return f"Player Ship (Unlocked by {unlocked_by})"

    return ""
Exemple #5
0
def _find_area_with_teleporter(world_list: WorldList,
                               teleporter: NodeIdentifier) -> Area:
    return world_list.area_by_area_location(teleporter.area_location)