def _process_rooms()

in textworld/generator/world.py [0:0]


    def _process_rooms(self) -> None:
        for fact in self.facts:
            if not self.kb.types.is_descendant_of(fact.arguments[0].type, 'r'):
                continue  # Skip non room facts.

            room = self._get_room(fact.arguments[0])
            room.add_related_fact(fact)

            if fact.name.endswith("_of"):
                # Handle room positioning facts.
                exit = reverse_direction(fact.name.split("_of")[0])
                dest = self._get_room(fact.arguments[1])
                dest.add_related_fact(fact)
                assert exit not in room.exits
                room.exits[exit] = dest

        # Handle door link facts.
        for fact in self.facts:
            if fact.name != "link":
                continue

            src = self._get_room(fact.arguments[0])
            door = self._get_object(fact.arguments[1])
            dest = self._get_room(fact.arguments[2])
            door.add_related_fact(fact)
            src.content.append(door)

            exit_found = False
            for exit, room in src.exits.items():
                if dest == room:
                    src.doors[exit] = door
                    exit_found = True
                    break

            if not exit_found:
                # Need to position both rooms w.r.t. each other.
                src_free_exits = [exit for exit in DIRECTIONS if exit not in src.exits]
                for exit in src_free_exits:
                    r_exit = reverse_direction(exit)
                    if r_exit not in dest.exits:
                        src.exits[exit] = dest
                        dest.exits[r_exit] = src
                        src.doors[exit] = door
                        exit_found = True
                        break

            # Relax the Cartesian grid constraint.
            if not exit_found:
                # Need to position both rooms w.r.t. each other.
                src_free_exits = [exit for exit in DIRECTIONS if exit not in src.exits]
                dest_free_exits = [exit for exit in DIRECTIONS if exit not in dest.exits]
                if len(src_free_exits) > 0 and len(dest_free_exits) > 0:
                    exit = src_free_exits[0]
                    r_exit = dest_free_exits[0]
                    src.exits[exit] = dest
                    dest.exits[r_exit] = src
                    src.doors[exit] = door
                    exit_found = True

            if not exit_found:  # If there is still no exit found.
                raise NoFreeExitError("Cannot connect {} and {}.".format(src, dest))