|
@@ -1,330 +0,0 @@
|
|
|
-from Tkinter import *
|
|
|
-
|
|
|
-class TrafficLightGUI(Frame):
|
|
|
-
|
|
|
- def __init__(self, behaviour, master=None, title="TrafficLight"):
|
|
|
-
|
|
|
- self.behaviour=behaviour
|
|
|
-
|
|
|
- # Initialize superclass
|
|
|
- Frame.__init__(self, master)
|
|
|
-
|
|
|
- # parent frame, destruction protocol
|
|
|
- self.root=master
|
|
|
- self.root.protocol("WM_DELETE_WINDOW", self.wmQuit)
|
|
|
-
|
|
|
- # Initialize packer
|
|
|
- self.pack(fill=BOTH, expand=1)
|
|
|
-
|
|
|
- # Create all widgets in the Frame
|
|
|
- self.__createWidgets()
|
|
|
-
|
|
|
-
|
|
|
- def __createWidgets(self):
|
|
|
-
|
|
|
- self.root.configure(bg="black")
|
|
|
-# self.root.pack(side=LEFT, fill=BOTH, expand=1)
|
|
|
-
|
|
|
- Label(self.root, text="", bg="black",
|
|
|
- height=2, width=10).pack(side=TOP, padx = 2, pady=2)
|
|
|
-
|
|
|
- self.redLight=Label(self.root, text="", bg="red",
|
|
|
- relief=GROOVE, height=5, width=10)
|
|
|
- self.redLight.pack(side=TOP, padx = 2, pady=4)
|
|
|
-
|
|
|
- self.yellowLight=Label(self.root, text="", bg="black",
|
|
|
- relief=GROOVE, height=5, width=10)
|
|
|
- self.yellowLight.pack(side=TOP, padx = 2, pady=4)
|
|
|
-
|
|
|
- self.greenLight=Label(self.root, text="", bg="black",
|
|
|
- relief=GROOVE, height=5, width=10)
|
|
|
- self.greenLight.pack(side=TOP, padx = 2, pady=4)
|
|
|
-
|
|
|
- Label(self.root, text="",bg="black",
|
|
|
- height=5, width=10).pack(side=TOP,padx=2,pady=2)
|
|
|
-
|
|
|
-# Begin generated code
|
|
|
-
|
|
|
- Button(self.root, text="PoliceInterrupt",
|
|
|
- command=self.PoliceInterruptPressed, width=10, wraplength=70).pack(side=TOP, fill=Y, padx=5, pady=2)
|
|
|
-
|
|
|
- Button(self.root, text="Quit",
|
|
|
- command=self.QuitPressed, width=10, wraplength=70).pack(side=TOP, fill=Y, padx = 5, pady = 2)
|
|
|
-# End generated code
|
|
|
-
|
|
|
- # binding with behaviour
|
|
|
-
|
|
|
-# Begin generated code
|
|
|
- def PoliceInterruptPressed(self):
|
|
|
- self.behaviour.event("PoliceInterrupt")
|
|
|
-
|
|
|
- def QuitPressed(self):
|
|
|
- self.behaviour.event("Quit")
|
|
|
-# End generated code
|
|
|
-
|
|
|
- def wmQuit(self):
|
|
|
- self.root.destroy()
|
|
|
-
|
|
|
- # the behaviour can call these methods to change the GUI
|
|
|
-
|
|
|
- def setGreenOn(self):
|
|
|
- self.greenLight["bg"] = "green"
|
|
|
-
|
|
|
- def setGreenOff(self):
|
|
|
- self.greenLight["bg"] = "black"
|
|
|
-
|
|
|
- def setRedOn(self):
|
|
|
- self.redLight["bg"] = "red"
|
|
|
-
|
|
|
- def setRedOff(self):
|
|
|
- self.redLight["bg"] = "black"
|
|
|
-
|
|
|
- def setYellowOn(self):
|
|
|
- self.yellowLight["bg"] = "yellow"
|
|
|
-
|
|
|
- def setYellowOff(self):
|
|
|
- self.yellowLight["bg"] = "black"
|
|
|
-
|
|
|
-import sys
|
|
|
-
|
|
|
-class TrafficLightBehaviour:
|
|
|
-
|
|
|
- def __init__(self, scale=1):
|
|
|
-
|
|
|
- self.scale = scale
|
|
|
- self.currentState = None
|
|
|
-
|
|
|
- self.scheduledTIMEOUT = None
|
|
|
-
|
|
|
- def initModel(self, gui):
|
|
|
-
|
|
|
- self.gui = gui
|
|
|
-
|
|
|
- # Begin generated code
|
|
|
- self.initState = "red"
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOn()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*3000, self.eventTIMEOUT)
|
|
|
- # End generated code
|
|
|
-
|
|
|
- self.currentState = self.initState
|
|
|
-
|
|
|
- def eventTIMEOUT(self):
|
|
|
- self.event("TIMEOUT")
|
|
|
-
|
|
|
- def event(self, eventName):
|
|
|
- # Note that below, setting coloured lights can be optimized by checking source
|
|
|
- # and target light settings and only updating those lights that changed.
|
|
|
- # In the following, the more naieve approach of re-setting all lights is taken.
|
|
|
-
|
|
|
- # Remove a scheduled timeout, if any,
|
|
|
- # to ensure that if we interrupted a transition scheduled in the future
|
|
|
- # that scheduled transition is removed
|
|
|
- if self.scheduledTIMEOUT is not None:
|
|
|
- self.gui.after_cancel(self.scheduledTIMEOUT)
|
|
|
- self.scheduledTIMEOUT = None
|
|
|
- # Switch based on all states
|
|
|
- if False:
|
|
|
- pass
|
|
|
- # for all states in the automaton
|
|
|
- # Begin generated code
|
|
|
- elif self.currentState == "blinkYellow":
|
|
|
- if False:
|
|
|
- pass
|
|
|
- # For all transitions from this state
|
|
|
- elif eventName == "Quit":
|
|
|
- self.currentState = "quit" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- elif eventName == "PoliceInterrupt":
|
|
|
- self.currentState = "red" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOn()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*3000, self.eventTIMEOUT)
|
|
|
- elif eventName == "TIMEOUT":
|
|
|
- self.currentState = "blinkBlack" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*500, self.eventTIMEOUT)
|
|
|
- else:
|
|
|
- print("ERROR: unexpected event %s received\n" % eventName)
|
|
|
- sys.exit(1)
|
|
|
- elif self.currentState == "blinkBlack":
|
|
|
- if False:
|
|
|
- pass
|
|
|
- # For all transitions from this state
|
|
|
- elif eventName == "Quit":
|
|
|
- self.currentState = "quit" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- elif eventName == "PoliceInterrupt":
|
|
|
- self.currentState = "red" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOn()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*3000, self.eventTIMEOUT)
|
|
|
- elif eventName == "TIMEOUT":
|
|
|
- self.currentState = "blinkYellow" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOn()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*500, self.eventTIMEOUT)
|
|
|
- else:
|
|
|
- print("ERROR: unexpected event %s received\n" % eventName)
|
|
|
- sys.exit(1)
|
|
|
- elif self.currentState == "red":
|
|
|
- if False:
|
|
|
- pass
|
|
|
- # For all transitions from this state
|
|
|
- elif eventName == "Quit":
|
|
|
- self.currentState = "quit" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- elif eventName == "PoliceInterrupt":
|
|
|
- self.currentState = "blinkYellow" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOn()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*500, self.eventTIMEOUT)
|
|
|
- elif eventName == "TIMEOUT":
|
|
|
- self.currentState = "green" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOn()
|
|
|
- self.gui.setRedOff()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*2000, self.eventTIMEOUT)
|
|
|
- else:
|
|
|
- print("ERROR: unexpected event %s received\n" % eventName)
|
|
|
- sys.exit(1)
|
|
|
- elif self.currentState == "green":
|
|
|
- if False:
|
|
|
- pass
|
|
|
- # For all transitions from this state
|
|
|
- elif eventName == "Quit":
|
|
|
- self.currentState = "quit" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- elif eventName == "PoliceInterrupt":
|
|
|
- self.currentState = "blinkYellow" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOn()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*500, self.eventTIMEOUT)
|
|
|
- elif eventName == "TIMEOUT":
|
|
|
- self.currentState = "yellow" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOn()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*1000, self.eventTIMEOUT)
|
|
|
- else:
|
|
|
- print("ERROR: unexpected event %s received\n" % eventName)
|
|
|
- sys.exit(1)
|
|
|
- elif self.currentState == "yellow":
|
|
|
- if False:
|
|
|
- pass
|
|
|
- # For all transitions from this state
|
|
|
- elif eventName == "Quit":
|
|
|
- self.currentState = "quit" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- elif eventName == "PoliceInterrupt":
|
|
|
- self.currentState = "blinkYellow" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOn()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOff()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*500, self.eventTIMEOUT)
|
|
|
- elif eventName == "TIMEOUT":
|
|
|
- self.currentState = "red" # target of the transition
|
|
|
- # The visual representation associated with the target state
|
|
|
- self.gui.setYellowOff()
|
|
|
- self.gui.setGreenOff()
|
|
|
- self.gui.setRedOn()
|
|
|
- # If the target state has an outgoing timed transition,
|
|
|
- # upon entering that target state, a timeout needs to be scheduled.
|
|
|
- # Keep track of scheduledTIMEOUT to be able to cancel it later if interrupted
|
|
|
- # before the timeout expires
|
|
|
- self.scheduledTIMEOUT = self.gui.after(self.scale*3000, self.eventTIMEOUT)
|
|
|
- else:
|
|
|
- print("ERROR: unexpected event %s received\n" % eventName)
|
|
|
- sys.exit(1)
|
|
|
- elif self.currentState == "quit":
|
|
|
- # if no outgoing transitions: no code generated
|
|
|
- pass
|
|
|
- # End generated code
|
|
|
- else:
|
|
|
- print("ERROR: unexpected currentState %s\n" % self.currentState)
|
|
|
- sys.exit(1)
|
|
|
-
|
|
|
-if __name__=="__main__":
|
|
|
- behaviour=TrafficLightBehaviour()
|
|
|
-
|
|
|
- root=Tk()
|
|
|
- # Initialize the GUI with the behaviour model as a parameter
|
|
|
- gui=TrafficLightGUI(behaviour, root)
|
|
|
-
|
|
|
- # Be sure to initialize the behaviour model after the GUI is created
|
|
|
- behaviour.initModel(gui)
|
|
|
-
|
|
|
- # The Tkinter main event loop
|
|
|
- root.mainloop()
|