31 EggVertexPool(
const string &name) :
EggNode(name) {
43 for (i = copy.
begin(); i != copy.
end(); ++i) {
57 nassertv(_index_vertices.size() == _unique_vertices.size());
59 IndexVertices::iterator ivi;
60 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
61 int index = (*ivi).first;
65 nassertv(vertex->_pool ==
this);
68 vertex->_pool =
nullptr;
72 _index_vertices.clear();
73 _unique_vertices.clear();
82 IndexVertices::const_iterator ivi;
83 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
99 IndexVertices::const_iterator ivi;
100 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
116 IndexVertices::const_iterator ivi = _index_vertices.find(index);
118 if (ivi == _index_vertices.end()) {
138 nassertr(index >= 0,
nullptr);
140 IndexVertices::const_iterator ivi = _index_vertices.find(index);
142 if (ivi == _index_vertices.end()) {
144 forward->_forward_reference =
true;
147 return (*ivi).second;
157 return _highest_index;
168 _highest_index = highest_index;
176 int num_dimensions = 0;
178 IndexVertices::const_iterator ivi;
179 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
184 return num_dimensions;
193 IndexVertices::const_iterator ivi;
194 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
196 if (vertex->has_normal()) {
210 IndexVertices::const_iterator ivi;
211 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
213 if (vertex->has_color()) {
227 IndexVertices::const_iterator ivi;
228 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
230 if (vertex->has_color() &&
231 (vertex->
get_color() != LColor(1.0, 1.0, 1.0, 1.0) ||
232 !vertex->_drgbas.empty())) {
250 has_overall_color =
true;
251 overall_color.set(1.0f, 1.0f, 1.0f, 1.0f);
255 IndexVertices::const_iterator ivi;
256 ivi = _index_vertices.begin();
261 while (ivi != _index_vertices.end()) {
262 vertex = (*ivi).second;
263 if (!vertex->
get_color().almost_equal(overall_color)) {
264 has_overall_color =
false;
270 has_overall_color =
true;
279 IndexVertices::const_iterator ivi;
280 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
296 IndexVertices::const_iterator ivi;
297 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
316 vector_string &tbn_names)
const {
317 pset<string> uv_names_set, uvw_names_set, tbn_names_set;
318 IndexVertices::const_iterator ivi;
319 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
324 uv_names_set.insert(uv_obj->get_name());
325 if (uv_obj->
has_w()) {
326 uvw_names_set.insert(uv_obj->get_name());
328 if (uv_obj->has_tangent() && uv_obj->has_binormal()) {
329 tbn_names_set.insert(uv_obj->get_name());
335 for (si = uv_names_set.begin(); si != uv_names_set.end(); ++si) {
336 uv_names.push_back(*si);
338 for (si = uvw_names_set.begin(); si != uvw_names_set.end(); ++si) {
339 uvw_names.push_back(*si);
341 for (si = tbn_names_set.begin(); si != tbn_names_set.end(); ++si) {
342 tbn_names.push_back(*si);
353 IndexVertices::const_iterator ivi;
354 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
359 aux_names_set.insert(aux_obj->get_name());
364 for (si = aux_names_set.begin(); si != aux_names_set.end(); ++si) {
365 aux_names.push_back(*si);
375 nassertr(_index_vertices.size() == _unique_vertices.size(),
377 return iterator(_index_vertices.begin());
386 return iterator(_index_vertices.end());
394 return _index_vertices.empty();
402 nassertr(_index_vertices.size() == _unique_vertices.size(), 0);
403 return _index_vertices.size();
426 nassertr(vertex->_pool ==
nullptr,
nullptr);
432 nassertr(index >= 0,
nullptr);
435 IndexVertices::const_iterator ivi = _index_vertices.find(index);
437 if (ivi != _index_vertices.end()) {
441 (*orig_vertex) = (*vertex);
442 orig_vertex->_forward_reference =
false;
443 _highest_index = std::max(_highest_index, index);
448 nassert_raise(
"duplicate vertex index");
452 _unique_vertices.insert(vertex);
453 _index_vertices[index] = vertex;
456 _highest_index = std::max(_highest_index, index);
459 vertex->_pool =
this;
460 vertex->_index = index;
473 UniqueVertices::iterator uvi;
474 uvi = _unique_vertices.find((
EggVertex *)©);
476 if (uvi != _unique_vertices.end()) {
492 UniqueVertices::iterator uvi;
493 uvi = _unique_vertices.find((
EggVertex *)©);
495 if (uvi != _unique_vertices.end()) {
512 nassertv(vertex->_pool ==
this);
515 nassertv(
get_vertex(vertex->_index) == vertex);
518 _index_vertices.erase(vertex->_index);
520 if (_highest_index == vertex->_index) {
522 if (_index_vertices.empty()) {
525 IndexVertices::reverse_iterator ivi = _index_vertices.rbegin();
526 while (ivi != _index_vertices.rend() &&
527 (*ivi).second->is_forward_reference()) {
530 if (ivi != _index_vertices.rend()) {
531 _highest_index = (*ivi).first;
542 UniqueVertices::iterator uvi;
543 uvi = _unique_vertices.find(vertex);
546 nassertv(uvi != _unique_vertices.end());
548 while ((*uvi) != vertex) {
551 nassertv(uvi != _unique_vertices.end());
554 _unique_vertices.erase(uvi);
556 vertex->_pool =
nullptr;
572 IndexVertices::const_iterator ivi;
573 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
578 vertex->_pool =
nullptr;
584 UniqueVertices::iterator uvi;
585 uvi = new_unique_vertices.find(vertex);
586 if (uvi != new_unique_vertices.end()) {
593 EggVertex::PrimitiveRef::iterator pi;
594 for (pi = pref.begin(); pi != pref.end(); ++pi) {
596 EggPrimitive::iterator pvi = prim->
find(vertex);
597 nassertr(pvi != prim->end(), 0);
598 prim->
replace(pvi, orig_vertex);
600 vertex->test_pref_integrity();
601 orig_vertex->test_pref_integrity();
604 vertex->_pool =
nullptr;
609 vertex->_index = new_index_vertices.size();
610 new_index_vertices.insert(IndexVertices::value_type(vertex->_index, vertex));
611 new_unique_vertices.insert(vertex);
617 _unique_vertices.swap(new_unique_vertices);
618 _index_vertices.swap(new_index_vertices);
619 _highest_index = (int)_index_vertices.size() - 1;
621 nassertr(_index_vertices.size() == _unique_vertices.size(), num_removed);
632 IndexVertices::iterator ivi;
633 for (ivi = _index_vertices.begin(); ivi != _index_vertices.end(); ++ivi) {
642 class IsLocalVertexSplitter {
659 LVector3d translation = mat.get_row3(3);
661 if (translation == LVector3d(0.0, 0.0, 0.0)) {
665 for (i =
begin(); i !=
end(); ++i) {
680 verts.reserve(
size());
684 for (
const IndexVertices::value_type &v : _index_vertices) {
685 verts.push_back(v.second);
688 std::copy(
begin(),
end(), std::back_inserter(verts));
691 Verts::const_iterator vi;
692 for (vi = verts.begin(); vi != verts.end(); ++vi) {
697 if (num_global_coord != 0) {
699 if (num_local_coord != 0) {
710 LMatrix4d local_mat = mat;
711 local_mat.set_row(3, LVector3d(0.0, 0.0, 0.0));
714 for (i =
begin(); i !=
end(); ++i) {
728 class SortByExternalIndex {
749 SortedVertices sorted_vertices;
750 sorted_vertices.reserve(
size());
752 for (i =
begin(); i !=
end(); ++i) {
753 sorted_vertices.push_back(*i);
756 std::sort(sorted_vertices.begin(), sorted_vertices.end(), SortByExternalIndex());
761 for (vi = 0; vi < (int)sorted_vertices.size(); ++vi) {
764 new_index_vertices[vi] = vertex;
768 _index_vertices.swap(new_index_vertices);
775 write(std::ostream &out,
int indent_level)
const {
779 for (i =
begin(); i !=
end(); ++i) {
780 (*i)->write(out, indent_level+2);
798 r_transform(
const LMatrix4d &mat,
const LMatrix4d &, CoordinateSystem) {
808 r_transform_vertices(
const LMatrix4d &mat) {
bool empty() const
Returns true if the pool is empty.
A base class for any of a number of kinds of geometry primitives: polygons, point lights,...
The set of UV's that may or may not be assigned to a vertex.
void split_vertex(EggVertex *vert, const FunctionObject &sequence)
Splits a vertex into two or more vertices, each an exact copy of the original and in the same vertex ...
bool has_uvs() const
Returns true if any vertex in the pool has a uv defined, false if none of them do.
This is an iterator adaptor that converts any iterator that returns a pair (e.g.
PrimitiveRef::size_type pref_size() const
Returns the number of elements between pref_begin() and pref_end().
void set_highest_index(int highest_index)
Artificially changes the "highest index number", so that a newly created vertex will begin at this nu...
int get_num_dimensions() const
Returns the number of dimensions the vertex uses.
void write_header(std::ostream &out, int indent_level, const char *egg_keyword) const
Writes the first line of the egg object, e.g.
int get_num_dimensions() const
Returns the maximum number of dimensions used by any vertex in the pool.
EggVertex * add_vertex(EggVertex *vertex, int index=-1)
Adds the indicated vertex to the pool.
bool has_aux() const
Returns true if the vertex has any auxiliary data, false otherwise.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
EggVertex * get_vertex(int index) const
Returns the vertex in the pool with the indicated index number, or NULL if no vertices have that inde...
EggVertex * get_forward_vertex(int index)
Returns the vertex in the pool with the indicated index number.
void check_overall_color(bool &has_overall_color, LColor &overall_color) const
Scans the vertex pool for different colors on different vertices.
const_aux_iterator aux_end() const
Returns an iterator that allows walking through the complete set of auxiliary data on the vertex.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
void clear_grefs()
Removes all group references from the vertex, so that it is not assigned to any group.
LColor get_color() const
Returns the color set on this particular attribute.
size_type size() const
Returns the number of vertices in the pool.
bool has_normals() const
Returns true if any vertex in the pool has a normal defined, false if none of them do.
iterator end() const
Returns an iterator that can be used to traverse through all the vertices in the pool.
void write(std::ostream &out, int indent_level) const
Writes the vertex pool to the indicated output stream in Egg format.
This is our own Panda specialization on the default STL vector.
iterator begin() const
Returns an iterator that can be used to traverse through all the vertices in the pool.
bool has_aux() const
Returns true if any vertex in the pool has auxiliary data defined, false if none of them do.
int get_index() const
Returns the index number of the vertex within its pool.
int get_highest_index() const
Returns the highest index number used by any vertex in the pool (except forward references).
bool has_w() const
Returns true if the texture coordinate has a third, w component, false if it is just a normal 2-d tex...
void get_uv_names(vector_string &uv_names, vector_string &uvw_names, vector_string &tbn_names) const
Returns the list of UV names that are defined by any vertices in the pool, as well as the subset of U...
bool is_local_coord() const
Returns true if this node's vertices are not in the global coordinate space.
bool has_defined_vertices() const
Returns true if any vertices in the pool are fully defined vertices, false if all vertices are forwar...
bool has_colors() const
Returns true if any vertex in the pool has a color defined, false if none of them do.
void transform(const LMatrix4d &mat)
Applies the indicated transformation matrix to the vertex.
Any one-, two-, three-, or four-component vertex, possibly with attributes such as a normal.
std::ostream & indent(std::ostream &out, int indent_level)
A handy function for doing text formatting.
int remove_unused_vertices()
Removes all vertices from the pool that are not referenced by at least one primitive.
iterator find(EggVertex *vertex)
Returns the iterator pointing to the indicated vertex, or end() if the vertex is not part of the prim...
void add_unused_vertices_to_prim(EggPrimitive *prim)
Adds all of the unused vertices in this vertex pool to the indicated primitive, in ascending order.
bool has_uv() const
Returns true if the vertex has an unnamed UV coordinate pair, false otherwise.
The set of named auxiliary data that may or may not be assigned to a vertex.
const_aux_iterator aux_begin() const
Returns an iterator that allows walking through the complete set of auxiliary data on the vertex.
EggVertex * find_matching_vertex(const EggVertex ©)
If the EggVertexPool already has a vertex matching the indicated vertex, returns it; otherwise,...
bool is_forward_reference() const
Returns true if the vertex is a forward reference to some vertex that hasn't been defined yet.
const_uv_iterator uv_begin() const
Returns an iterator that allows walking through the complete set of named UV's on the vertex.
A base class for things that may be directly added into the egg hierarchy.
void sort_by_external_index()
Re-orders (and re-numbers) the vertices in this vertex pool so that they appear in increasing order b...
int get_external_index() const
Returns the number set by set_external_index().
void replace(iterator position, EggVertex *vertex)
Replaces the vertex at the indicated position with the indicated vertex.
int get_num_global_coord() const
Returns the number of primitives that own this vertex whose vertices are interpreted in the global co...
This is our own Panda specialization on the default STL set.
TypeHandle is the identifier used to differentiate C++ class types.
int get_num_local_coord() const
Returns the number of primitives that own this vertex whose vertices are interpreted to be in a local...
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
void get_aux_names(vector_string &aux_names) const
Returns the list of auxiliary data names that are defined by any vertices in the pool.
EggVertex * create_unique_vertex(const EggVertex ©)
Creates a new vertex in the pool that is a copy of the indicated one and returns it.
A collection of vertices.
EggVertex * add_vertex(EggVertex *vertex)
Adds the indicated vertex to the end of the primitive's list of vertices, and returns it.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
void transform(const LMatrix4d &mat)
Applies the indicated transformation matrix to all the vertices.
const_uv_iterator uv_end() const
Returns an iterator that allows walking through the complete set of named UV's on the vertex.
bool has_forward_vertices() const
Returns true if any vertices in the pool are undefined forward-reference vertices,...
bool has_nonwhite_colors() const
Returns true if any vertex in the pool has a color defined other than white, false if no vertices hav...
void remove_vertex(EggVertex *vertex)
Removes the vertex from the pool.