Ejemplo n.º 1
0
 def xml(self):
     """ Return IPFGraph as XML element
     
     """
     graph = Element("IPFGraph")
     block_tree = SubElement(graph, "Blocks")
     for name in sorted(self.__blocks):
         row, column = self.get_block_cell(name)
         block_element = SubElement(block_tree, "Block", 
                                    {"name":name,
                                     "grid_row":str(row),
                                     "grid_column":str(column)})
         block_element.append(self.__blocks[name].xml())
         
     connection_tree = SubElement(graph, "Connections")
     for connection in sorted(self.connections):
         oport = connection._oport()
         iport = connection._iport()
         oblock = oport._owner_block()
         iblock = iport._owner_block()
         oblock_name = self.get_block_name(oblock)
         iblock_name = self.get_block_name(iblock)
         oport_name = oblock.get_port_name(oport)
         iport_name = iblock.get_port_name(iport)
         conection_element = SubElement(connection_tree, "Connection")
         con_output = SubElement(conection_element, 
                                "ConnectionOutput",
                                {"block" : oblock_name,
                                 "port" : oport_name})
         con_input = SubElement(conection_element, 
                                "ConnectionInput",
                                {"block" : iblock_name,
                                 "port" : iport_name})
     return graph
Ejemplo n.º 2
0
    def rearrange(self):
        """ Rearranges graph to layered structure
        
        """
        block_dict = dict()
        graph = digraph()
        for i, block_name in enumerate(self.__blocks):
            # Add 100 for each block number for make equal length of names
            # need check if blocks count greater than 900
            block_dict[block_name] = str(i + 100)
            graph.add_node(block_dict[block_name])
        for connection in self.connections:
            out_block_name = self.get_block_name(connection._oport()._owner_block())
            in_block_name = self.get_block_name(connection._iport()._owner_block())
            try:
                graph.add_edge( (block_dict[out_block_name],
                                 block_dict[in_block_name]) )
            except pygraph.classes.exceptions.AdditionError:
                continue
        
        # Export graph to DOT format
        dot = pygraph.readwrite.dot.write(graph)
        gvv = pygraphviz.AGraph()
        gvv.from_string(dot)
        # Arrange graph in layers
        gvv.layout('dot')
        
        # Parse DOT graph format to get nodes coordinates  
        dot =  gvv.to_string()
        dot = dot.replace('\n', ' ')
        x_coords = set()
        y_coords = set()
        nodes = []
        lines = dot.split(";")
        for line in lines:
            r = re.compile(r'\s*(?P<node_name>\w+)\s*\[height=".*",\s*pos="(?P<pos_x>[\w\.]+),(?P<pos_y>[\w\.]+)",\s*width=".*"\]')
            m = r.search(line)
            if m is not None:
                x = int(floor(float(m.group('pos_x'))/20)*20)
                y = int(floor(float(m.group('pos_y'))/20)*20)
                nodes.append( (m.group('node_name'), x, y) )
                x_coords.add(x)
                y_coords.add(y)
 
            xs = sorted(x_coords)
            ys = sorted(y_coords)
            row = dict()
            column = dict()
            for i, x in enumerate(xs):
                column[x] = i
            for i, y in enumerate(ys):
                row[y] = len(ys) - i - 1
    
            cell_nodes = []
            for node, x, y in nodes:
                cell_nodes.append( (node, row[y], column[x]) )
    
            self._grid_model = self._get_clear_grid_model()
            for node, row, column in cell_nodes:
                self._grid_model[row][column] = dict_key_from_value(block_dict, node)
                self._grid_height = max(self._grid_height, row + 1)
                self._grid_width = max(self._grid_width, column + 1)