mirror of
https://github.com/panda3d/panda3d.git
synced 2025-10-03 02:15:43 -04:00
support instancing syntax
This commit is contained in:
parent
d2d151010f
commit
83d21bc2b1
@ -121,6 +121,14 @@ EggGroup::
|
||||
void EggGroup::
|
||||
set_group_type(GroupType type) {
|
||||
if (type != get_group_type()) {
|
||||
#ifndef NDEBUG
|
||||
if (type != GT_instance) {
|
||||
// Only valid to change to a non-instance type if we have no
|
||||
// group refs.
|
||||
nassertv(_group_refs.empty());
|
||||
}
|
||||
#endif
|
||||
|
||||
// Make sure the user didn't give us any stray bits.
|
||||
nassertv((type & ~F_group_type)==0);
|
||||
_flags = (_flags & ~F_group_type) | type;
|
||||
@ -259,6 +267,13 @@ write(ostream &out, int indent_level) const {
|
||||
<< "<Scalar> blenda { " << c[3] << " }\n";
|
||||
}
|
||||
|
||||
GroupRefs::const_iterator gri;
|
||||
for (gri = _group_refs.begin(); gri != _group_refs.end(); ++gri) {
|
||||
EggGroup *group_ref = (*gri);
|
||||
indent(out, indent_level + 2)
|
||||
<< "<Ref> { " << group_ref->get_name() << " }\n";
|
||||
}
|
||||
|
||||
// We have to write the children nodes before we write the vertex
|
||||
// references, since we might be referencing a vertex that's defined
|
||||
// in one of those children nodes!
|
||||
@ -767,6 +782,65 @@ test_vref_integrity() const {
|
||||
|
||||
#endif // NDEBUG
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: EggGroup::add_group_ref
|
||||
// Access: Published
|
||||
// Description: Adds a new <Ref> entry to the group. This declares
|
||||
// an internal reference to another node, and is used to
|
||||
// implement scene-graph instancing; it is only valid if
|
||||
// the group_type is GT_instance.
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void EggGroup::
|
||||
add_group_ref(EggGroup *group) {
|
||||
nassertv(get_group_type() == GT_instance);
|
||||
_group_refs.push_back(group);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: EggGroup::get_num_group_refs
|
||||
// Access: Published
|
||||
// Description: Returns the number of <Ref> entries within this
|
||||
// group. See add_group_ref().
|
||||
////////////////////////////////////////////////////////////////////
|
||||
int EggGroup::
|
||||
get_num_group_refs() const {
|
||||
return _group_refs.size();
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: EggGroup::get_group_ref
|
||||
// Access: Published
|
||||
// Description: Returns the nth <Ref> entry within this group. See
|
||||
// add_group_ref().
|
||||
////////////////////////////////////////////////////////////////////
|
||||
EggGroup *EggGroup::
|
||||
get_group_ref(int n) const {
|
||||
nassertr(n >= 0 && n < (int)_group_refs.size(), NULL);
|
||||
return _group_refs[n];
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: EggGroup::remove_group_ref
|
||||
// Access: Published
|
||||
// Description: Removes the nth <Ref> entry within this group. See
|
||||
// add_group_ref().
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void EggGroup::
|
||||
remove_group_ref(int n) {
|
||||
nassertv(n >= 0 && n < (int)_group_refs.size());
|
||||
_group_refs.erase(_group_refs.begin() + n);
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////
|
||||
// Function: EggGroup::clear_group_refs
|
||||
// Access: Published
|
||||
// Description: Removes all of the <Ref> entries within this group.
|
||||
// See add_group_ref().
|
||||
////////////////////////////////////////////////////////////////////
|
||||
void EggGroup::
|
||||
clear_group_refs() {
|
||||
_group_refs.clear();
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
@ -285,6 +285,12 @@ PUBLISHED:
|
||||
void test_vref_integrity() const { }
|
||||
#endif // NDEBUG
|
||||
|
||||
void add_group_ref(EggGroup *group);
|
||||
int get_num_group_refs() const;
|
||||
EggGroup *get_group_ref(int n) const;
|
||||
void remove_group_ref(int n);
|
||||
void clear_group_refs();
|
||||
|
||||
static GroupType string_group_type(const string &strval);
|
||||
static DartType string_dart_type(const string &strval);
|
||||
static DCSType string_dcs_type(const string &strval);
|
||||
@ -353,6 +359,9 @@ private:
|
||||
TagData _tag_data;
|
||||
VertexRef _vref;
|
||||
|
||||
typedef pvector< PT(EggGroup) > GroupRefs;
|
||||
GroupRefs _group_refs;
|
||||
|
||||
|
||||
public:
|
||||
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -79,6 +79,10 @@ static Textures textures;
|
||||
typedef pmap<string, PT_EggMaterial > Materials;
|
||||
static Materials materials;
|
||||
|
||||
// Group names to groups.
|
||||
typedef pmap<string, PT(EggGroup) > Groups;
|
||||
static Groups groups;
|
||||
|
||||
// We need to be able to save the index number requested for a vertex
|
||||
// temporarily.
|
||||
static int vertex_index;
|
||||
@ -101,6 +105,7 @@ egg_init_parser(istream &in, const string &filename,
|
||||
vertex_pools.clear();
|
||||
textures.clear();
|
||||
materials.clear();
|
||||
groups.clear();
|
||||
|
||||
egg_stack.push_back(tos);
|
||||
egg_top_node = top_node;
|
||||
@ -140,6 +145,7 @@ egg_cleanup_parser() {
|
||||
vertex_pools.clear();
|
||||
textures.clear();
|
||||
materials.clear();
|
||||
groups.clear();
|
||||
}
|
||||
|
||||
%}
|
||||
@ -208,6 +214,7 @@ egg_cleanup_parser() {
|
||||
%type <_egg> texture_name
|
||||
%type <_egg> material_name
|
||||
%type <_egg> vertex_pool_name
|
||||
%type <_egg> group_name
|
||||
|
||||
%type <_number> real
|
||||
%type <_number> integer
|
||||
@ -1137,8 +1144,12 @@ group:
|
||||
}
|
||||
'{' group_body '}'
|
||||
{
|
||||
$$ = egg_stack.back();
|
||||
EggGroup *group = DCAST(EggGroup, egg_stack.back());
|
||||
$$ = group;
|
||||
egg_stack.pop_back();
|
||||
if (group->has_name()) {
|
||||
groups[group->get_name()] = group;
|
||||
}
|
||||
Thread::consider_yield();
|
||||
}
|
||||
;
|
||||
@ -1180,8 +1191,12 @@ instance:
|
||||
}
|
||||
'{' group_body '}'
|
||||
{
|
||||
$$ = egg_stack.back();
|
||||
EggGroup *group = DCAST(EggGroup, egg_stack.back());
|
||||
$$ = group;
|
||||
egg_stack.pop_back();
|
||||
if (group->has_name()) {
|
||||
groups[group->get_name()] = group;
|
||||
}
|
||||
}
|
||||
;
|
||||
|
||||
@ -1419,6 +1434,15 @@ group_body:
|
||||
| group_body transform
|
||||
| group_body group_vertex_ref
|
||||
| group_body switchcondition
|
||||
| group_body REF '{' group_name '}'
|
||||
{
|
||||
EggGroup *group = DCAST(EggGroup, egg_stack.back());
|
||||
if (group->get_group_type() != EggGroup::GT_instance) {
|
||||
eggyyerror("<Ref> valid only within <Instance>");
|
||||
} else if ($4 != (EggObject *)NULL) {
|
||||
group->add_group_ref(DCAST(EggGroup, $4));
|
||||
}
|
||||
}
|
||||
| group_body node
|
||||
{
|
||||
DCAST(EggGroup, egg_stack.back())->add_child(DCAST(EggNode, $2));
|
||||
@ -2825,6 +2849,26 @@ vertex_pool_name:
|
||||
}
|
||||
;
|
||||
|
||||
/*
|
||||
* group_name
|
||||
*
|
||||
* enter:
|
||||
* exit: Returns an EggGroup pointer, or NULL.
|
||||
*
|
||||
*/
|
||||
group_name:
|
||||
required_name
|
||||
{
|
||||
string name = $1;
|
||||
Groups::iterator vpi = groups.find(name);
|
||||
if (vpi == groups.end()) {
|
||||
eggyyerror("Unknown group " + name);
|
||||
$$ = PT(EggObject)();
|
||||
} else {
|
||||
$$ = (*vpi).second;
|
||||
}
|
||||
}
|
||||
;
|
||||
|
||||
/*
|
||||
* required_name
|
||||
|
@ -1758,6 +1758,7 @@ make_lod(EggBin *egg_bin, PandaNode *parent) {
|
||||
lod_node->add_switch(instance._d->_switch_in, instance._d->_switch_out);
|
||||
}
|
||||
|
||||
_groups[egg_bin] = lod_node;
|
||||
return create_group_arc(egg_bin, parent, lod_node);
|
||||
}
|
||||
|
||||
@ -1897,6 +1898,19 @@ make_node(EggGroup *egg_group, PandaNode *parent) {
|
||||
if (node == (PandaNode *)NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// Associate any instances with this node.
|
||||
int num_group_refs = egg_group->get_num_group_refs();
|
||||
for (int gri = 0; gri < num_group_refs; ++gri) {
|
||||
EggGroup *group_ref = egg_group->get_group_ref(gri);
|
||||
Groups::const_iterator gi = _groups.find(group_ref);
|
||||
if (gi != _groups.end()) {
|
||||
PandaNode *node_ref = (*gi).second;
|
||||
node->add_child(node_ref);
|
||||
}
|
||||
}
|
||||
|
||||
_groups[egg_group] = node;
|
||||
return create_group_arc(egg_group, parent, node);
|
||||
}
|
||||
|
||||
|
@ -224,6 +224,9 @@ private:
|
||||
Materials _materials;
|
||||
Materials _materials_bface;
|
||||
|
||||
typedef pmap<PT(EggGroup), PT(PandaNode) > Groups;
|
||||
Groups _groups;
|
||||
|
||||
typedef pset<PandaNode *> ExtraNodes;
|
||||
ExtraNodes _decals;
|
||||
ExtraNodes _sequences;
|
||||
|
Loading…
x
Reference in New Issue
Block a user