live simulation with visualization (real time)
authorGustavo J. A. M. Carneiro <gjc@inescporto.pt>
Wed, 06 Aug 2008 17:55:01 +0100
changeset 3523 118a0ac0ecfa
parent 3522 c99a7cc43e72
child 3524 149adba9cc96
live simulation with visualization (real time)
examples/visualizer.py
--- a/examples/visualizer.py	Wed Aug 06 17:53:20 2008 +0100
+++ b/examples/visualizer.py	Wed Aug 06 17:55:01 2008 +0100
@@ -1,8 +1,9 @@
 # -*- python; coding: utf-8 -*-
 
 LAYOUT_ALGORITHM = 'neato' # ['neato'|'dot'|'twopi'|'circo'|'fdp'|'nop']
-NS3_POSITION_SCALE = 100
-
+REPRESENT_CHANNELS_AS_NODES = 1
+NS3_POSITION_SCALE = 1
+SAMPLE_PERIOD = 0.1
 
 import ns3
 
@@ -11,6 +12,8 @@
     import gtk
     import goocanvas
     import gobject
+    import threading
+    gobject.threads_init()
 except ImportError:
     pygraphviz = None
     goocanvas = None
@@ -85,6 +88,30 @@
         self.canvas_item.set_property("data", "M %r %r L %r %r" % (pos1_x, pos1_y, pos2_x, pos2_y))
 
 
+
+class SimulationThread(threading.Thread):
+    def __init__(self, viz):
+        super(SimulationThread, self).__init__()
+        assert isinstance(viz, Visualizer)
+        self.viz = viz # Visualizer object
+        self.lock = threading.Lock()
+        self.target_time = 0 # in seconds
+        self.quit = False
+        
+    def run(self):
+        while not ns3.Simulator.IsFinished() and not self.quit:
+            #print "sim: Wait for lock"
+            self.lock.acquire()
+            try:
+                #print "sim: Run until: ", self.target_time
+                ns3.pyviz.SimulatorRunUntil(ns3.Seconds(self.target_time))
+                #print "sim: Run until: ", self.target_time, ": finished."
+            finally:
+                self.lock.release()
+            #print "sim: Release lock, Wait for view event."
+            self.viz.view_updated.wait() # wait until the main (view) thread finishes updating the view
+            #print "sim: View updated, loop iteration done."
+
 class Visualizer(object):
 
     def __init__(self):
@@ -93,6 +120,9 @@
         self.window = None
         self.canvas = None
 
+        self.view_updated = threading.Event()
+        self.simulation = SimulationThread(self)
+
     def create_gui(self):
         self.window = gtk.Window()
         vbox = gtk.VBox(); vbox.show()
@@ -142,10 +172,10 @@
             for devI in range(node.GetNDevices()):
                 device = node.GetDevice(devI)
                 channel = device.GetChannel()
-                if isinstance(channel, ns3.BridgeChannel):
+                if isinstance(channel, (ns3.BridgeChannel, ns3.WifiChannel)):
                     continue
                 if channel.GetNDevices() > 2:
-                    if 1:
+                    if REPRESENT_CHANNELS_AS_NODES:
                         # represent channels as white nodes
                         if mobility is None:
                             channel_name = "Channel %s" % hash(channel)
@@ -209,21 +239,46 @@
         link.canvas_item.set_property("parent", self.canvas.get_root_item())
 
     def update_view(self):
-        pass
+        #print "update_view"
+        for node in self.nodes.itervalues():
+            if node.has_mobility:
+                ns3_node = ns3.NodeList.GetNode(node.node_index)
+                mobility = ns3_node.GetObject(ns3.MobilityModel.GetTypeId())
+                if mobility is not None:
+                    pos = mobility.GetPosition()
+                    node.set_position(pos.x*NS3_POSITION_SCALE, pos.y*NS3_POSITION_SCALE)
+                
+                
 
-    def sample_timeout(self):
-        
-        
+    def update_view_timeout(self):
+        #print "view: update_view_timeout"
+        self.simulation.lock.acquire()
+        try:
+            self.update_view()
+            #print "view: target time increased from %f to %f" % \
+            #    (self.simulation.target_time, self.simulation.target_time + SAMPLE_PERIOD)
+            self.simulation.target_time += SAMPLE_PERIOD
+        finally:
+            self.simulation.lock.release()
+        #print "view: self.view_updated.set()"
+        self.view_updated.set()
+        self.view_updated.clear()
+        #print "view: done."
+        return True
 
-        return True
 
     def start(self):
         self.create_gui()
         self.scan_topology()
         self.window.connect("delete-event", lambda window, event: gtk.main_quit())
-        gobject.timeout_add(100, sample_timeout)
+        gobject.timeout_add(int(SAMPLE_PERIOD*1e3), self.update_view_timeout)
+        self.simulation.start()
         gtk.main()
 
+        self.simulation.quit = True
+        self.view_updated.set()
+        self.simulation.join()
+
 
 def start():
     if goocanvas is None: