X-Git-Url: http://git.mutantstargoat.com/user/nuclear/?p=laserbrain_demo;a=blobdiff_plain;f=src%2Fmetascene.cc;h=aae7482b5b4f728286bc0a52b0a0ab72d8b2dacd;hp=99a9daf9ca238f880b86672b98416c3dd2a35aed;hb=dbcb9345c23c5c027d808915962843e7db2d14aa;hpb=72b941af07bbf2673539ad4eea073e68d3bcbbfc diff --git a/src/metascene.cc b/src/metascene.cc index 99a9daf..aae7482 100644 --- a/src/metascene.cc +++ b/src/metascene.cc @@ -10,8 +10,11 @@ #endif static bool proc_node(Scene *scn, struct ts_node *node); +static bool proc_scenefile(Scene *scn, struct ts_node *node); static struct ts_attr *attr_inscope(struct ts_node *node, const char *name); +static void print_scene_graph(SceneNode *n, int level); + bool load_scene(Scene *scn, const char *fname) { struct ts_node *root = ts_load(fname); @@ -23,6 +26,10 @@ bool load_scene(Scene *scn, const char *fname) bool res = proc_node(scn, root); ts_free_tree(root); + + printf("loaded scene: %s\n", fname); + printf("scene graph:\n"); + print_scene_graph(scn->nodes, 0); return res; } @@ -38,25 +45,7 @@ static bool proc_node(Scene *scn, struct ts_node *node) // do this last to allow other contents of the node to do their thing if(strcmp(node->name, "scenefile") == 0) { - const char *fname = ts_get_attr_str(node, "file"); - if(fname) { - struct ts_attr *adpath = attr_inscope(node, "datapath"); - if(adpath && adpath->val.type == TS_STRING) { - printf("adding data path: %s\n", adpath->val.str); - datamap_set_path(adpath->val.str); - } - - int namesz = datamap_lookup(fname, 0, 0); - char *namebuf = (char*)alloca(namesz + 1); - if(datamap_lookup(fname, namebuf, namesz + 1)) { - fname = namebuf; - } - - if(!(scn->load(fname, SCNLOAD_FLIPTEX))) { - return false; - } - } - datamap_reset(); + return proc_scenefile(scn, node); } else if(strcmp(node->name, "remap") == 0) { const char *match = ts_get_attr_str(node, "match"); @@ -69,6 +58,61 @@ static bool proc_node(Scene *scn, struct ts_node *node) return true; } +static bool proc_scenefile(Scene *scn, struct ts_node *node) +{ + const char *fname = ts_get_attr_str(node, "file"); + if(fname) { + // datapath + struct ts_attr *adpath = attr_inscope(node, "datapath"); + if(adpath && adpath->val.type == TS_STRING) { + printf("adding data path: %s\n", adpath->val.str); + datamap_set_path(adpath->val.str); + } + + // walkmesh + char *walkmesh_regexp = 0; + struct ts_attr *awmesh = attr_inscope(node, "walkmesh"); + if(awmesh && awmesh->val.type == TS_STRING) { + walkmesh_regexp = awmesh->val.str; + } + + int namesz = datamap_lookup(fname, 0, 0); + char *namebuf = (char*)alloca(namesz + 1); + if(datamap_lookup(fname, namebuf, namesz + 1)) { + fname = namebuf; + } + + if(!(scn->load(fname, SCNLOAD_FLIPTEX))) { + return false; + } + + // extract the walk mesh if necessary + // XXX as written, this will match even objects loaded by previous scenefile blocks + Scene *wscn; + if(walkmesh_regexp && (wscn = scn->extract_nodes(walkmesh_regexp))) { + // apply all transformations to the meshes + wscn->apply_xform(); + + int nmeshes = wscn->meshes.size(); + for(int i=0; imeshes[i]; + + if(scn->walk_mesh) { + scn->walk_mesh->append(*m); + } else { + scn->walk_mesh = m; + wscn->remove_mesh(m); // to save it from destruction + } + } + + delete wscn; + } + } + datamap_reset(); + + return true; +} + static struct ts_attr *attr_inscope(struct ts_node *node, const char *name) { struct ts_attr *attr = 0; @@ -78,3 +122,23 @@ static struct ts_attr *attr_inscope(struct ts_node *node, const char *name) } return attr; } + +static void print_scene_graph(SceneNode *n, int level) +{ + if(!n) return; + + for(int i=0; iget_num_objects(); + if(nobj) { + printf("%s - %d obj\n", n->get_name(), n->get_num_objects()); + } else { + printf("%s\n", n->get_name()); + } + + for(int i=0; iget_num_children(); i++) { + print_scene_graph(n->get_child(i), level + 1); + } +}