Added support for EXTERNPROTO's and fixed a bug where relative Inline URL's that included a path didn't load

This commit is contained in:
2009-01-06 12:30:28 +00:00
parent 823aa30cba
commit 70c5417ed6

View File

@@ -258,6 +258,10 @@ def is_nodeline(i, words):
if lines[i].startswith('PROTO'):
words[:] = lines[i].split()
return NODE_NORMAL, i+1 # TODO - assumes the next line is a '[\n', skip that
if lines[i].startswith('EXTERNPROTO'):
words[:] = lines[i].split()
return NODE_ARRAY, i+1 # TODO - assumes the next line is a '[\n', skip that
'''
proto_type, new_i = is_protoline(i, words, proto_field_defs)
if new_i != -1:
@@ -437,6 +441,17 @@ class vrmlNode(object):
except:
return None
def findSpecRecursive(self, spec):
self_real = self.getRealNode()
if spec == self_real.getSpec():
return self
for child in self_real.children:
if child.findSpecRecursive(spec):
return child
return None
def getPrefix(self):
if self.id:
return self.id[0]
@@ -453,6 +468,9 @@ class vrmlNode(object):
def getProtoName(self):
return self.getSpecialTypeName('PROTO')
def getExternprotoName(self):
return self.getSpecialTypeName('EXTERNPROTO')
def getChildrenBySpec(self, node_spec): # spec could be Transform, Shape, Appearance
self_real = self.getRealNode()
@@ -496,14 +514,19 @@ class vrmlNode(object):
# where the parent of this object is not the real parent
# - In this case we have added the proto as a child to a node instancing it.
# This is a bit arbitary, but its how Proto's are done with this importer.
if child.getProtoName() == None:
if child.getProtoName() == None and child.getExternprotoName() == None:
child.getSerialized(results, ancestry)
else:
if DEBUG: print 'getSerialized() is proto:', child.getProtoName(), self.getSpec()
if child.getProtoName()==self.getSpec():
if DEBUG: print 'getSerialized() is proto:', child.getProtoName(), child.getExternprotoName(), self.getSpec()
self_spec = self.getSpec()
if child.getProtoName() == self_spec or child.getExternprotoName() == self_spec:
if DEBUG: "FoundProto!"
child.getSerialized(results, ancestry)
return results
@@ -869,19 +892,52 @@ class vrmlNode(object):
# print self.id, self.getFilename()
# If we were an inline then try load the file
# Check if this node was an inline or externproto
url_ls = []
if self.node_type == NODE_NORMAL and self.getSpec() == 'Inline':
ancestry = [] # Warning! - PROTO's using this wont work at all.
url = self.getFieldAsString('url', None, ancestry)
if url:
url_ls = [(url, None)]
del ancestry
elif self.getExternprotoName():
# externproto
url_ls = []
for f in self.fields:
if type(f)==str:
f = [f]
for ff in f:
for f_split in ff.split('"'):
# print f_split
# "someextern.vrml#SomeID"
if '#' in f_split:
f_split, f_split_id = f_split.split('#') # there should only be 1 # anyway
url_ls.append( (f_split, f_split_id) )
else:
url_ls.append( (f_split, None) )
# Was either an Inline or an EXTERNPROTO
if url_ls:
if url != None:
# print url_ls
for url, extern_key in url_ls:
print url
urls = []
urls.append( url )
urls.append( BPySys.caseInsensitivePath(urls[-1]) )
urls.append( dirName(self.getFilename()) + url )
urls.append( BPySys.caseInsensitivePath(urls[-1]) )
urls.append( dirName(self.getFilename()) + baseName(url) )
urls.append( BPySys.caseInsensitivePath(urls[-1]) )
@@ -918,7 +974,7 @@ class vrmlNode(object):
lines.insert(0, 'root_node____')
lines.append('}')
'''
ff = open('/root/test.txt', 'w')
ff = open('/tmp/test.txt', 'w')
ff.writelines([l+'\n' for l in lines])
'''
@@ -926,9 +982,28 @@ class vrmlNode(object):
child.setRoot(url) # initialized dicts
child.parse(0)
# if self.getExternprotoName():
if not extern_key: # if none is spesified - use the name
extern_key = self.getSpec()
if extern_key:
self.children.remove(child)
child.parent = None
extern_child = child.findSpecRecursive(extern_key)
if extern_child:
self.children.append(extern_child)
extern_child.parent = self
if DEBUG: print "\tEXTERNPROTO ID found!:", extern_key
else:
print "\tEXTERNPROTO ID not found!:", extern_key
# Watch it! - restore lines
lines[:] = lines_old
return new_i
@@ -967,6 +1042,8 @@ class vrmlNode(object):
self.getDefDict()[ key ] = self
key = self.getProtoName()
if not key: key = self.getExternprotoName()
proto_dict = self.getProtoDict()
if key != None:
proto_dict[ key ] = self
@@ -1167,11 +1244,11 @@ def vrml_parse(path):
lines.append('}')
# Use for testing our parsed output, so we can check on line numbers.
'''
ff = open('/tmp/test.txt', 'w')
ff.writelines([l+'\n' for l in lines])
ff.close()
'''
# Now evaluate it
node_type, new_i = is_nodeline(0, [])