diff --git a/agent.py b/agent.py index cb42721..55b3926 100644 --- a/agent.py +++ b/agent.py @@ -2,47 +2,23 @@ import random from termcolor import colored from src.Engine import Engine from src.obj.Waiter import Waiter -from src.obj.Block import Block from src.obj.Kitchen import Kitchen -from src.obj.Table import Table -from src.controller.UserController import UserController -from src.controller.StateController import StateController +from src.controller.LayoutController import LayoutController + from src.controller.ImageController import ImageController -from Network.Predictor import Predictor print(colored("Initialization...", "green")) SCREEN_SIZE = [800, 800] SQUARE_SIZE = 80 SLEEP_DURATION = 0.125 +COUNT_OF_OBJECTS = 25 store = ImageController(SQUARE_SIZE) - waiter = Waiter([0, 0], 0, SQUARE_SIZE, SCREEN_SIZE, store) kitchen = Kitchen([0, 0], 0, SQUARE_SIZE, SCREEN_SIZE, store) -objects = [] - -for i in range(25): - - pos = [0, 0] - - while any([o.compare_pos(pos) for o in objects]) or pos == [0, 0]: - pos = [random.randint(1, SCREEN_SIZE[0]/SQUARE_SIZE - 1), - random.randint(1, SCREEN_SIZE[0]/SQUARE_SIZE - 1)] - - if (random.randint(0, 1)): - objects.append(Block(pos, 0, SQUARE_SIZE, SCREEN_SIZE, store)) - else: - objects.append(Table(pos, 0, SQUARE_SIZE, SCREEN_SIZE, store)) - -user = UserController(waiter) -state = StateController(waiter) -predictor = Predictor() -engine = Engine(SCREEN_SIZE, SQUARE_SIZE, kitchen, - user, state, predictor, SLEEP_DURATION) - -for o in objects: - engine.subscribe(o) +engine = Engine(SCREEN_SIZE, SQUARE_SIZE, kitchen, waiter, SLEEP_DURATION) +layout = LayoutController(engine, store).create_and_subscribe(COUNT_OF_OBJECTS) print(colored("Starting model...", "green")) diff --git a/src/Engine.py b/src/Engine.py index 308843b..d57a9be 100644 --- a/src/Engine.py +++ b/src/Engine.py @@ -15,7 +15,7 @@ from src.obj.PriorityItem import PriorityItem class Engine: - def __init__(self, screen_size, square_size, kitchen: Kitchen, user: UserController, state: StateController, predictor: Predictor, sleep_duration): + def __init__(self, screen_size, square_size, kitchen: Kitchen, waiter: Waiter, sleep_duration): pygame.display.set_caption('Waiter Agent') self.action_clock = 0 @@ -23,9 +23,9 @@ class Engine: self.tree = TreeEngine() self.kitchen: Kitchen = kitchen - self.user: Waiter = user - self.state: StateController = state - self.predictor: Predictor = predictor + self.user: UserController = UserController(waiter) + self.state: StateController = StateController(waiter) + self.predictor: Predictor = Predictor() self.screen_size: list[int] = screen_size self.screen = pygame.display.set_mode(self.screen_size) @@ -70,19 +70,18 @@ class Engine: self.user.handler(self) if self.paused: return + if not self.state.path: if self.goals: if not self.state.graphsearch(self) and self.goals: self.objects.remove(self.goals.pop().parent) - self.predict() + else: # went path - state = self.user.obj.changeState(self.state.path.pop()) self.clock_increment(state.cost) - # ''' print(colored("Action:\t", "blue")+f"{state.agent_role}", end='\t') print(colored("Cost:\t", "blue")+f"{state.cost}", end='\t') print(colored("Cost so far: ", "blue") + @@ -93,7 +92,6 @@ class Engine: f"{self.user.obj.basket_capacity}", end='\t') print(colored("Memory capacity: ", "blue") + f"{self.user.obj.memory_capacity}") - # ''' # waiter interaction @@ -201,7 +199,5 @@ class Engine: item: PriorityItem = goal_queue.get() if item.priority == 2: self.appendGoal(self.kitchen) - if self.kitchen.compare_pos(self.user.obj.position): - self.clock_increment(100) else: self.appendGoal(item.obj) diff --git a/src/controller/LayoutController.py b/src/controller/LayoutController.py new file mode 100644 index 0000000..17621d4 --- /dev/null +++ b/src/controller/LayoutController.py @@ -0,0 +1,47 @@ +import random +from src.obj.Block import Block +from src.obj.Table import Table + + +class LayoutController(): + def __init__(self, engine, store): + ''' + That class controls the location of objects on the map. + + `param: enginie (Enginie)` - class of enginie core + `param: store (ImageController)` - class of image controller + ''' + self.enginie = engine + self.store = store + + def create_and_subscribe(self, count): + ''' + That function generate a location and a type of objects + and subscribe they to action list in the engine + + `param: count (int)` - number of objects to be created + ''' + + num_squares = self.enginie.num_squares + square_size = self.enginie.square_size + screen_size = self.enginie.screen_size + store = self.store + objects = [] + + for _ in range(count): + + pos = [0, 0] + + while any([o.compare_pos(pos) for o in objects]) or pos == [0, 0]: + pos = [random.randint(1, num_squares - 1), + random.randint(1, num_squares - 1)] + + if (random.randint(0, 1)): + objects.append( + Block(pos, 0, square_size, screen_size, store)) + else: + objects.append( + Table(pos, 0, square_size, screen_size, store)) + + for o in objects: + self.enginie.subscribe(o) diff --git a/src/controller/StateController.py b/src/controller/StateController.py index ee9a3fc..c25ef2a 100644 --- a/src/controller/StateController.py +++ b/src/controller/StateController.py @@ -17,6 +17,7 @@ class StateController: self.fringe = PriorityQueue() def build_path(self, goal_state, engine): + goal_state.cost = goal_state.cost if goal_state.agent_role != "blank" else 100 total_cost = goal_state.cost self.path.append(goal_state) engine.goals.pop() diff --git a/src/controller/UserController.py b/src/controller/UserController.py index daf68ba..0bc4875 100644 --- a/src/controller/UserController.py +++ b/src/controller/UserController.py @@ -1,4 +1,3 @@ -import time import pygame from termcolor import colored diff --git a/src/obj/Table.py b/src/obj/Table.py index ee951d5..40d3bc4 100644 --- a/src/obj/Table.py +++ b/src/obj/Table.py @@ -13,8 +13,9 @@ class Table(Object): def isActual(self, current_time): if self.is_actual and self.agent_role == "table": - if current_time - self.waiting_time > 1000: - self.reset(current_time) + if current_time - self.waiting_time > 300: + self.reset_role(current_time) + self.reset_status() return self.is_actual @@ -58,10 +59,13 @@ class Table(Object): self.waiting_time = current_time return super().change_role(new_role) - def reset(self, current_time): + def reset_role(self, current_time): + self.change_role("table", current_time) + self.unsetMark() + + def reset_status(self): self.is_actual = False self.mark = Mark(self, "unknown") - self.change_role("table", current_time) def set_order(self, current_time): if self.agent_role == "table": diff --git a/src/obj/Waiter.py b/src/obj/Waiter.py index 63271bb..2240848 100644 --- a/src/obj/Waiter.py +++ b/src/obj/Waiter.py @@ -3,7 +3,7 @@ from src.obj.Object import Object class Waiter(Object): - def __init__(self, position, orientation, square_size, screen_size, store, basket=[], memory=[], battery=300): + def __init__(self, position, orientation, square_size, screen_size, store, basket=[], memory=[], battery=200): super().__init__("waiter", position, orientation, square_size, screen_size, store) self.battery = battery self.basket_capacity = 4 @@ -14,10 +14,11 @@ class Waiter(Object): self.prev_orientation = copy.copy(self.orientation) def changeState(self, state): + if state.agent_role == "blank": + return state + self.position = copy.deepcopy(state.position) self.orientation = copy.copy(state.orientation) - self.basket = copy.copy(state.basket) - self.memory = copy.copy(state.memory) self.battery -= state.cost return state @@ -48,7 +49,7 @@ class Waiter(Object): def deliver_dish(self, table, current_time): if table in self.basket: - table.reset(current_time) + table.reset_role(current_time) self.basket.remove(table) self.basket_capacity += 1 @@ -73,7 +74,7 @@ class Waiter(Object): return 1 if self.battery >= 100 else 0 def recharge(self): - self.battery = 300 + self.battery = 200 def left(self): self.orientation = (self.orientation + 1) % 4