Package dynamic_reconfigure :: Module encoding

Source Code for Module dynamic_reconfigure.encoding

  1  # Software License Agreement (BSD License) 
  2  # 
  3  # Copyright (c) 2009, Willow Garage, Inc. 
  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 Willow Garage, Inc. 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  try: 
 34      import roslib; roslib.load_manifest('dynamic_reconfigure') 
 35  except Exception: 
 36      pass 
 37  import copy 
 38  import sys 
 39   
 40  from dynamic_reconfigure.msg import BoolParameter, DoubleParameter, IntParameter, ParamDescription, StrParameter 
 41  from dynamic_reconfigure.msg import Config as ConfigMsg 
 42  from dynamic_reconfigure.msg import ConfigDescription as ConfigDescrMsg 
 43  from dynamic_reconfigure.msg import Group as GroupMsg 
 44  from dynamic_reconfigure.msg import GroupState 
 45   
 46   
47 -class Config(dict):
48 - def __init__(self, *args, **kwargs):
49 dict.__init__(self, *args, **kwargs)
50
51 - def __getstate__(self):
52 return self.__dict__.items()
53
54 - def __setstate__(self, items):
55 for key, val in items: 56 self.__dict__[key] = val
57
58 - def __repr__(self):
59 return super(Config, self).__repr__()
60
61 - def __setitem__(self, key, value):
62 return super(Config, self).__setitem__(key, value)
63
64 - def __getitem__(self, name):
65 return super(Config, self).__getitem__(name)
66
67 - def __delitem__(self, name):
68 return super(Config, self).__delitem__(name)
69 70 __getattr__ = __getitem__ 71 __setattr__ = __setitem__ 72
73 - def copy(self):
74 return Config(self)
75
76 - def __deepcopy__(self, memo):
77 c = type(self)({}) 78 for key, value in self.items(): 79 c[copy.deepcopy(key)] = copy.deepcopy(value) 80 81 return c
82 83
84 -def encode_description(descr):
85 msg = ConfigDescrMsg() 86 msg.max = encode_config(descr.max) 87 msg.min = encode_config(descr.min) 88 msg.dflt = encode_config(descr.defaults) 89 msg.groups = encode_groups(None, descr.config_description) 90 return msg
91 92
93 -def encode_groups(parent, group):
94 group_list = [] 95 96 msg = GroupMsg() 97 98 msg.name = group['name'] 99 msg.id = group['id'] 100 msg.parent = group['parent'] 101 msg.type = group['type'] 102 103 for param in group['parameters']: 104 msg.parameters.append(ParamDescription(param['name'], param['type'], param['level'], param['description'], param['edit_method'])) 105 106 group_list.append(msg) 107 for next in group['groups']: 108 group_list.extend(encode_groups(msg, next)) 109 110 return group_list
111 112
113 -def encode_config(config, flat=True):
114 msg = ConfigMsg() 115 for k, v in config.items(): 116 ## @todo add more checks here? 117 if type(v) == int: 118 msg.ints.append(IntParameter(k, v)) 119 elif type(v) == bool: 120 msg.bools.append(BoolParameter(k, v)) 121 elif type(v) == str: 122 msg.strs.append(StrParameter(k, v)) 123 elif sys.version_info.major < 3 and isinstance(v, unicode): 124 msg.strs.append(StrParameter(k, v)) 125 elif type(v) == float: 126 msg.doubles.append(DoubleParameter(k, v)) 127 elif type(v) == dict or isinstance(v, Config): 128 if flat is True: 129 def flatten(g): 130 groups = [] 131 for _name, group in g['groups'].items(): 132 groups.extend(flatten(group)) 133 groups.append(GroupState(group['name'], group['state'], group['id'], group['parent'])) 134 return groups
135 msg.groups.append(GroupState(v['name'], v['state'], v['id'], v['parent'])) 136 msg.groups.extend(flatten(v)) 137 else: 138 msg.groups = [GroupState(x['name'], x['state'], x['id'], x['parent']) for x in v] 139 140 return msg 141 142
143 -def group_dict(group):
144 try: 145 state = group.state 146 except AttributeError: 147 state = True 148 if hasattr(group, 'type'): 149 type = group.type 150 else: 151 type = '' 152 return Config({ 153 'id': group.id, 154 'parent': group.parent, 155 'name': group.name, 156 'type': type, 157 'state': state, 158 'groups': Config({}), 159 'parameters': Config({}), 160 })
161 162
163 -def decode_description(msg):
164 mins = decode_config(msg.min) 165 maxes = decode_config(msg.max) 166 defaults = decode_config(msg.dflt) 167 groups = {} 168 grouplist = msg.groups 169 170 def params_from_msg(msg): 171 params = [] 172 for param in msg.parameters: 173 name = param.name 174 params.append({ 175 'name': name, 176 'min': mins[name], 177 'max': maxes[name], 178 'default': defaults[name], 179 'type': param.type, 180 'level': param.level, 181 'description': param.description, 182 'edit_method': param.edit_method, 183 }) 184 return params
185 186 # grab the default group 187 for group in grouplist: 188 if group.id == 0: 189 groups = group_dict(group) 190 groups['parameters'] = params_from_msg(group) 191 192 def build_tree(group): 193 children = Config({}) 194 for g in grouplist: 195 if g.id == 0: 196 pass 197 elif g.parent == group['id']: 198 gd = group_dict(g) 199 200 gd['parameters'] = params_from_msg(g) 201 gd['groups'] = build_tree(gd) 202 # add the dictionary into the tree 203 children[gd['name']] = gd 204 return children 205 206 groups['groups'] = build_tree(groups) 207 208 return groups 209 210
211 -def get_tree(m, group=None):
212 if group is None: 213 for x in m.groups: 214 if x.id == 0: 215 group = x 216 217 children = Config({}) 218 for g in m.groups: 219 if g.id == 0: 220 pass 221 elif g.parent == group.id: 222 gd = group_dict(g) 223 224 gd['groups'] = get_tree(m, g) 225 children[gd['name']] = gd 226 227 if group.id == 0: 228 ret = group_dict(group) 229 ret['groups'] = children 230 return ret 231 else: 232 return children
233 234
235 -def initial_config(msg, description=None):
236 d = Config([(kv.name, kv.value) for kv in msg.bools + msg.ints + msg.strs + msg.doubles]) 237 238 def gt(m, descr, group=None): 239 # get the default group 240 if group is None: 241 for x in m.groups: 242 if x.id == 0: 243 group = x 244 245 children = Config({}) 246 for g in m.groups: 247 if g.id == 0: 248 pass 249 elif g.parent == group.id: 250 gd = group_dict(g) 251 252 def find_state(gr, dr): 253 for g in dr['groups']: 254 if g['id'] == gr['id']: 255 gr['state'] = g['state'] 256 return 257 else: 258 find_state(gr, g) 259 return
260 261 find_state(gd, descr) 262 263 # Get the tree for this group 264 gd['groups'] = gt(m, descr, g) 265 children[gd['name']] = gd 266 267 if group.id == 0: 268 ret = group_dict(group) 269 ret['groups'] = children 270 return ret 271 else: 272 return children 273 274 if not msg.groups == [] and description is not None: 275 d["groups"] = gt(msg, description) 276 277 def add_params(group, descr): 278 for param in descr['parameters']: 279 group['parameters'][param['name']] = d[param['name']] 280 for _n, g in group['groups'].items(): 281 for dr in descr['groups']: 282 if dr['name'] == g['name']: 283 add_params(g, dr) 284 285 add_params(d['groups'], description) 286 287 return d 288 289
290 -def decode_config(msg, description=None):
291 if sys.version_info.major < 3: 292 for s in msg.strs: 293 if not isinstance(s.value, unicode): 294 try: 295 s.value.decode('ascii') 296 except UnicodeDecodeError: 297 s.value = s.value.decode('utf-8') 298 299 d = Config([(kv.name, kv.value) for kv in msg.bools + msg.ints + msg.strs + msg.doubles]) 300 if not msg.groups == [] and description is not None: 301 d["groups"] = get_tree(msg) 302 303 def add_params(group, descr): 304 for param in descr['parameters']: 305 if param['name'] in d.keys(): 306 group[param['name']] = d[param['name']] 307 for _n, g in group['groups'].items(): 308 for _nr, dr in descr['groups'].items(): 309 if dr['name'] == g['name']: 310 add_params(g, dr)
311 312 add_params(d['groups'], description) 313 314 return d 315 316
317 -def extract_params(group):
318 params = [] 319 params.extend(group['parameters']) 320 try: 321 for _n, g in group['groups'].items(): 322 params.extend(extract_params(g)) 323 except AttributeError: 324 for g in group['groups']: 325 params.extend(extract_params(g)) 326 return params
327 328
329 -def get_parents(group, descriptions):
330 parents = [] 331 for p in descriptions['group']: 332 if p['id'] == group['parent']: 333 parents.extend(get_parents(p, descriptions)) 334 parents.append(p) 335 return parents
336