Package node_manager_fkie :: Module service_list_model
[frames] | no frames]

Source Code for Module node_manager_fkie.service_list_model

  1  # Software License Agreement (BSD License) 
  2  # 
  3  # Copyright (c) 2012, Fraunhofer FKIE/US, Alexander Tiderko 
  4  # All rights reserved. 
  5  # 
  6  # Redistribution and use in source and binary forms, with or without 
  7  # modification, are permitted provided that the following conditions 
  8  # are met: 
  9  # 
 10  #  * Redistributions of source code must retain the above copyright 
 11  #    notice, this list of conditions and the following disclaimer. 
 12  #  * Redistributions in binary form must reproduce the above 
 13  #    copyright notice, this list of conditions and the following 
 14  #    disclaimer in the documentation and/or other materials provided 
 15  #    with the distribution. 
 16  #  * Neither the name of Fraunhofer nor the names of its 
 17  #    contributors may be used to endorse or promote products derived 
 18  #    from this software without specific prior written permission. 
 19  # 
 20  # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 
 21  # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 
 22  # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 
 23  # FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 
 24  # COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 
 25  # INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 
 26  # BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 
 27  # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 
 28  # CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 
 29  # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 
 30  # ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 
 31  # POSSIBILITY OF SUCH DAMAGE. 
 32   
 33  from PySide import QtCore 
 34  from PySide import QtGui 
 35   
 36  import os 
 37   
 38  import roslib 
 39   
 40  import node_manager_fkie as nm 
41 42 -class ServiceItem(QtGui.QStandardItem):
43 ''' 44 The service item stored in the service model. This class stores the service as 45 L{master_discovery_fkie.ServiceInfo}. The name of the service is represented in HTML. 46 ''' 47 48 ITEM_TYPE = QtGui.QStandardItem.UserType + 37 49
50 - def __init__(self, service, parent=None):
51 ''' 52 Initialize the service item. 53 @param service: the service object to view 54 @type service: L{master_discovery_fkie.ServiceInfo} 55 ''' 56 QtGui.QStandardItem.__init__(self, self.toHTML(service.name)) 57 self.service = service 58 '''@ivar: service info as L{master_discovery_fkie.ServiceInfo}.'''
59
60 - def updateServiceView(self, parent):
61 ''' 62 Updates the view of the service on changes. 63 @param parent: the item containing this item 64 @type parent: L{PySide.QtGui.QStandardItem} 65 ''' 66 if not parent is None: 67 # update type view 68 child = parent.child(self.row(), 1) 69 if not child is None: 70 self.updateTypeView(self.service, child)
71
72 - def type(self):
73 return TopicItem.ITEM_TYPE
74 75 @classmethod
76 - def toHTML(cls, service_name):
77 ''' 78 Creates a HTML representation of the service name. 79 @param service_name: the service name 80 @type service_name: C{str} 81 @return: the HTML representation of the service name 82 @rtype: C{str} 83 ''' 84 ns, sep, name = service_name.rpartition('/') 85 result = '' 86 if sep: 87 result = ''.join(['<div>', '<span style="color:gray;">', str(ns), sep, '</span><b>', name, '</b></div>']) 88 else: 89 result = name 90 return result
91 92 @classmethod
93 - def getItemList(self, service):
94 ''' 95 Creates the list of the items from service. This list is used for the 96 visualization of service data as a table row. 97 @param service: the service data 98 @type service: L{master_discovery_fkie.ServiceInfo} 99 @return: the list for the representation as a row 100 @rtype: C{[L{ServiceItem} or L{PySide.QtGui.QStandardItem}, ...]} 101 ''' 102 items = [] 103 item = ServiceItem(service) 104 # removed tooltip for clarity !!! 105 # item.setToolTip(''.join(['<div><h4>', str(service.name), '</h4><dl><dt>', str(service.uri),'</dt></dl></div>'])) 106 items.append(item) 107 typeItem = QtGui.QStandardItem() 108 ServiceItem.updateTypeView(service, typeItem) 109 items.append(typeItem) 110 return items
111 112 @classmethod
113 - def updateTypeView(cls, service, item):
114 ''' 115 Updates the representation of the column contains the type of the service. 116 @param service: the service data 117 @type service: L{master_discovery_fkie.ServiceInfo} 118 @param item: corresponding item in the model 119 @type item: L{ServiceItem} 120 ''' 121 try: 122 service_class = service.get_service_class(nm.is_local(nm.nameres().getHostname(service.uri))) 123 item.setText(cls.toHTML(service_class._type)) 124 # removed tooltip for clarity !!! 125 # tooltip = '' 126 # tooltip = ''.join([tooltip, '<h4>', service_class._type, '</h4>']) 127 # tooltip = ''.join([tooltip, '<b><u>', 'Request', ':</u></b>']) 128 # tooltip = ''.join([tooltip, '<dl><dt>', str(service_class._request_class.__slots__), '</dt></dl>']) 129 # 130 # tooltip = ''.join([tooltip, '<b><u>', 'Response', ':</u></b>']) 131 # tooltip = ''.join([tooltip, '<dl><dt>', str(service_class._response_class.__slots__), '</dt></dl>']) 132 # 133 # item.setToolTip(''.join(['<div>', tooltip, '</div>'])) 134 item.setToolTip('') 135 except: 136 # import traceback 137 # print traceback.format_exc() 138 if not service.isLocal: 139 tooltip = ''.join(['<h4>', 'Service type is not available due to he running on another host.', '</h4>']) 140 item.setToolTip(''.join(['<div>', tooltip, '</div>']))
141
142 143 # def __eq__(self, item): 144 # ''' 145 # Compares the name of service. 146 # ''' 147 # if isinstance(item, str) or isinstance(item, unicode): 148 # return self.service.name.lower() == item.lower() 149 # elif not (item is None): 150 # return self.service.name.lower() == item.service.name.lower() 151 # return False 152 # 153 # def __gt__(self, item): 154 # ''' 155 # Compares the name of service. 156 # ''' 157 # if isinstance(item, str) or isinstance(item, unicode): 158 # return self.service.name.lower() > item.lower() 159 # elif not (item is None): 160 # return self.service.name.lower() > item.service.name.lower() 161 # return False 162 163 164 -class ServiceModel(QtGui.QStandardItemModel):
165 ''' 166 The model to manage the list with services in ROS network. 167 ''' 168 header = [('Name', 300), 169 ('Type', -1)] 170 '''@ivar: the list with columns C{[(name, width), ...]}''' 171
172 - def __init__(self):
173 ''' 174 Creates a new list model. 175 ''' 176 QtGui.QStandardItemModel.__init__(self) 177 self.setColumnCount(len(ServiceModel.header)) 178 self.setHorizontalHeaderLabels([label for label, width in ServiceModel.header])
179
180 - def flags(self, index):
181 ''' 182 @param index: parent of the list 183 @type index: L{PySide.QtCore.QModelIndex} 184 @return: Flag or the requestet item 185 @rtype: L{PySide.QtCore.Qt.ItemFlag} 186 @see: U{http://www.pyside.org/docs/pyside-1.0.1/PySide/QtCore/Qt.html} 187 ''' 188 if not index.isValid(): 189 return QtCore.Qt.NoItemFlags 190 return QtCore.Qt.ItemIsEnabled | QtCore.Qt.ItemIsSelectable
191
192 - def updateModelData(self, services):
193 ''' 194 Updates the service list model. New services will be inserted in sorting 195 order. Not available services removed from the model. 196 @param services: The dictionary with services 197 @type services: C{dict(service name : L{master_discovery_fkie.ServiceInfo})} 198 ''' 199 service_names = services.keys() 200 root = self.invisibleRootItem() 201 updated = [] 202 cputimes = os.times() 203 cputime_init = cputimes[0] + cputimes[1] 204 # remove or update the items 205 for i in reversed(range(root.rowCount())): 206 serviceItem = root.child(i) 207 if not serviceItem.service.name in service_names: 208 root.removeRow(i) 209 else: 210 serviceItem.service = services[serviceItem.service.name] 211 updated.append(serviceItem.service.name) 212 # add new items in sorted order 213 for (name, service) in services.items(): 214 if not service is None: 215 doAddItem = True 216 for i in range(root.rowCount()): 217 serviceItem = root.child(i) 218 if not name in updated: 219 if cmp(serviceItem.service.name.lower(), service.name.lower()) > 0: 220 root.insertRow(i, ServiceItem.getItemList(service)) 221 doAddItem = False 222 break 223 else: 224 doAddItem = False 225 break 226 if doAddItem: 227 root.appendRow(ServiceItem.getItemList(service))
228 # cputimes = os.times() 229 # cputime = cputimes[0] + cputimes[1] - cputime_init 230 # print " update services ", cputime, ', service count:', len(services) 231