diff options
Diffstat (limited to 'scene/resources/surface_tool.cpp')
-rw-r--r-- | scene/resources/surface_tool.cpp | 164 |
1 files changed, 65 insertions, 99 deletions
diff --git a/scene/resources/surface_tool.cpp b/scene/resources/surface_tool.cpp index 4b392e23b7..1a2dcc84bb 100644 --- a/scene/resources/surface_tool.cpp +++ b/scene/resources/surface_tool.cpp @@ -36,43 +36,50 @@ #define EQ_VERTEX_DIST 0.00001 bool SurfaceTool::Vertex::operator==(const Vertex &p_vertex) const { - - if (vertex != p_vertex.vertex) + if (vertex != p_vertex.vertex) { return false; + } - if (uv != p_vertex.uv) + if (uv != p_vertex.uv) { return false; + } - if (uv2 != p_vertex.uv2) + if (uv2 != p_vertex.uv2) { return false; + } - if (normal != p_vertex.normal) + if (normal != p_vertex.normal) { return false; + } - if (binormal != p_vertex.binormal) + if (binormal != p_vertex.binormal) { return false; + } - if (color != p_vertex.color) + if (color != p_vertex.color) { return false; + } - if (bones.size() != p_vertex.bones.size()) + if (bones.size() != p_vertex.bones.size()) { return false; + } for (int i = 0; i < bones.size(); i++) { - if (bones[i] != p_vertex.bones[i]) + if (bones[i] != p_vertex.bones[i]) { return false; + } } for (int i = 0; i < weights.size(); i++) { - if (weights[i] != p_vertex.weights[i]) + if (weights[i] != p_vertex.weights[i]) { return false; + } } return true; } uint32_t SurfaceTool::VertexHasher::hash(const Vertex &p_vtx) { - uint32_t h = hash_djb2_buffer((const uint8_t *)&p_vtx.vertex, sizeof(real_t) * 3); h = hash_djb2_buffer((const uint8_t *)&p_vtx.normal, sizeof(real_t) * 3, h); h = hash_djb2_buffer((const uint8_t *)&p_vtx.binormal, sizeof(real_t) * 3, h); @@ -86,7 +93,6 @@ uint32_t SurfaceTool::VertexHasher::hash(const Vertex &p_vtx) { } void SurfaceTool::begin(Mesh::PrimitiveType p_primitive) { - clear(); primitive = p_primitive; @@ -95,7 +101,6 @@ void SurfaceTool::begin(Mesh::PrimitiveType p_primitive) { } void SurfaceTool::add_vertex(const Vector3 &p_vertex) { - ERR_FAIL_COND(!begun); Vertex vtx; @@ -159,8 +164,8 @@ void SurfaceTool::add_vertex(const Vector3 &p_vertex) { format |= Mesh::ARRAY_FORMAT_VERTEX; } -void SurfaceTool::add_color(Color p_color) { +void SurfaceTool::add_color(Color p_color) { ERR_FAIL_COND(!begun); ERR_FAIL_COND(!first && !(format & Mesh::ARRAY_FORMAT_COLOR)); @@ -168,8 +173,8 @@ void SurfaceTool::add_color(Color p_color) { format |= Mesh::ARRAY_FORMAT_COLOR; last_color = p_color; } -void SurfaceTool::add_normal(const Vector3 &p_normal) { +void SurfaceTool::add_normal(const Vector3 &p_normal) { ERR_FAIL_COND(!begun); ERR_FAIL_COND(!first && !(format & Mesh::ARRAY_FORMAT_NORMAL)); @@ -179,7 +184,6 @@ void SurfaceTool::add_normal(const Vector3 &p_normal) { } void SurfaceTool::add_tangent(const Plane &p_tangent) { - ERR_FAIL_COND(!begun); ERR_FAIL_COND(!first && !(format & Mesh::ARRAY_FORMAT_TANGENT)); @@ -188,7 +192,6 @@ void SurfaceTool::add_tangent(const Plane &p_tangent) { } void SurfaceTool::add_uv(const Vector2 &p_uv) { - ERR_FAIL_COND(!begun); ERR_FAIL_COND(!first && !(format & Mesh::ARRAY_FORMAT_TEX_UV)); @@ -197,7 +200,6 @@ void SurfaceTool::add_uv(const Vector2 &p_uv) { } void SurfaceTool::add_uv2(const Vector2 &p_uv2) { - ERR_FAIL_COND(!begun); ERR_FAIL_COND(!first && !(format & Mesh::ARRAY_FORMAT_TEX_UV2)); @@ -206,7 +208,6 @@ void SurfaceTool::add_uv2(const Vector2 &p_uv2) { } void SurfaceTool::add_bones(const Vector<int> &p_bones) { - ERR_FAIL_COND(!begun); ERR_FAIL_COND(!first && !(format & Mesh::ARRAY_FORMAT_BONES)); @@ -215,7 +216,6 @@ void SurfaceTool::add_bones(const Vector<int> &p_bones) { } void SurfaceTool::add_weights(const Vector<float> &p_weights) { - ERR_FAIL_COND(!begun); ERR_FAIL_COND(!first && !(format & Mesh::ARRAY_FORMAT_WEIGHTS)); @@ -224,12 +224,10 @@ void SurfaceTool::add_weights(const Vector<float> &p_weights) { } void SurfaceTool::add_smooth_group(bool p_smooth) { - ERR_FAIL_COND(!begun); if (index_array.size()) { smooth_groups[index_array.size()] = p_smooth; } else { - smooth_groups[vertex_array.size()] = p_smooth; } } @@ -264,7 +262,6 @@ void SurfaceTool::add_triangle_fan(const Vector<Vector3> &p_vertices, const Vect } void SurfaceTool::add_index(int p_index) { - ERR_FAIL_COND(!begun); format |= Mesh::ARRAY_FORMAT_INDEX; @@ -272,29 +269,25 @@ void SurfaceTool::add_index(int p_index) { } Array SurfaceTool::commit_to_arrays() { - int varr_len = vertex_array.size(); Array a; a.resize(Mesh::ARRAY_MAX); for (int i = 0; i < Mesh::ARRAY_MAX; i++) { - - if (!(format & (1 << i))) + if (!(format & (1 << i))) { continue; //not in format + } switch (i) { - case Mesh::ARRAY_VERTEX: case Mesh::ARRAY_NORMAL: { - Vector<Vector3> array; array.resize(varr_len); Vector3 *w = array.ptrw(); int idx = 0; for (List<Vertex>::Element *E = vertex_array.front(); E; E = E->next(), idx++) { - const Vertex &v = E->get(); switch (i) { @@ -313,18 +306,15 @@ Array SurfaceTool::commit_to_arrays() { case Mesh::ARRAY_TEX_UV: case Mesh::ARRAY_TEX_UV2: { - Vector<Vector2> array; array.resize(varr_len); Vector2 *w = array.ptrw(); int idx = 0; for (List<Vertex>::Element *E = vertex_array.front(); E; E = E->next(), idx++) { - const Vertex &v = E->get(); switch (i) { - case Mesh::ARRAY_TEX_UV: { w[idx] = v.uv; } break; @@ -337,14 +327,12 @@ Array SurfaceTool::commit_to_arrays() { a[i] = array; } break; case Mesh::ARRAY_TANGENT: { - Vector<float> array; array.resize(varr_len * 4); float *w = array.ptrw(); int idx = 0; for (List<Vertex>::Element *E = vertex_array.front(); E; E = E->next(), idx += 4) { - const Vertex &v = E->get(); w[idx + 0] = v.tangent.x; @@ -360,14 +348,12 @@ Array SurfaceTool::commit_to_arrays() { } break; case Mesh::ARRAY_COLOR: { - Vector<Color> array; array.resize(varr_len); Color *w = array.ptrw(); int idx = 0; for (List<Vertex>::Element *E = vertex_array.front(); E; E = E->next(), idx++) { - const Vertex &v = E->get(); w[idx] = v.color; } @@ -375,14 +361,12 @@ Array SurfaceTool::commit_to_arrays() { a[i] = array; } break; case Mesh::ARRAY_BONES: { - Vector<int> array; array.resize(varr_len * 4); int *w = array.ptrw(); int idx = 0; for (List<Vertex>::Element *E = vertex_array.front(); E; E = E->next(), idx += 4) { - const Vertex &v = E->get(); ERR_CONTINUE(v.bones.size() != 4); @@ -396,19 +380,16 @@ Array SurfaceTool::commit_to_arrays() { } break; case Mesh::ARRAY_WEIGHTS: { - Vector<float> array; array.resize(varr_len * 4); float *w = array.ptrw(); int idx = 0; for (List<Vertex>::Element *E = vertex_array.front(); E; E = E->next(), idx += 4) { - const Vertex &v = E->get(); ERR_CONTINUE(v.weights.size() != 4); for (int j = 0; j < 4; j++) { - w[idx + j] = v.weights[j]; } } @@ -417,7 +398,6 @@ Array SurfaceTool::commit_to_arrays() { } break; case Mesh::ARRAY_INDEX: { - ERR_CONTINUE(index_array.size() == 0); Vector<int> array; @@ -426,7 +406,6 @@ Array SurfaceTool::commit_to_arrays() { int idx = 0; for (List<int>::Element *E = index_array.front(); E; E = E->next(), idx++) { - w[idx] = E->get(); } @@ -442,17 +421,18 @@ Array SurfaceTool::commit_to_arrays() { } Ref<ArrayMesh> SurfaceTool::commit(const Ref<ArrayMesh> &p_existing, uint32_t p_flags) { - Ref<ArrayMesh> mesh; - if (p_existing.is_valid()) + if (p_existing.is_valid()) { mesh = p_existing; - else + } else { mesh.instance(); + } int varr_len = vertex_array.size(); - if (varr_len == 0) + if (varr_len == 0) { return mesh; + } int surface = mesh->get_surface_count(); @@ -460,22 +440,22 @@ Ref<ArrayMesh> SurfaceTool::commit(const Ref<ArrayMesh> &p_existing, uint32_t p_ mesh->add_surface_from_arrays(primitive, a, Array(), Dictionary(), p_flags); - if (material.is_valid()) + if (material.is_valid()) { mesh->surface_set_material(surface, material); + } return mesh; } void SurfaceTool::index() { - - if (index_array.size()) + if (index_array.size()) { return; //already indexed + } HashMap<Vertex, int, VertexHasher> indices; List<Vertex> new_vertices; for (List<Vertex>::Element *E = vertex_array.front(); E; E = E->next()) { - int *idxptr = indices.getptr(E->get()); int idx; if (!idxptr) { @@ -496,19 +476,17 @@ void SurfaceTool::index() { } void SurfaceTool::deindex() { - - if (index_array.size() == 0) + if (index_array.size() == 0) { return; //nothing to deindex + } Vector<Vertex> varr; varr.resize(vertex_array.size()); int idx = 0; for (List<Vertex>::Element *E = vertex_array.front(); E; E = E->next()) { - varr.write[idx++] = E->get(); } vertex_array.clear(); for (List<int>::Element *E = index_array.front(); E; E = E->next()) { - ERR_FAIL_INDEX(E->get(), varr.size()); vertex_array.push_back(varr[E->get()]); } @@ -517,14 +495,12 @@ void SurfaceTool::deindex() { } void SurfaceTool::_create_list(const Ref<Mesh> &p_existing, int p_surface, List<Vertex> *r_vertex, List<int> *r_index, int &lformat) { - Array arr = p_existing->surface_get_arrays(p_surface); ERR_FAIL_COND(arr.size() != RS::ARRAY_MAX); _create_list_from_arrays(arr, r_vertex, r_index, lformat); } Vector<SurfaceTool::Vertex> SurfaceTool::create_vertex_array_from_triangle_arrays(const Array &p_arrays) { - Vector<SurfaceTool::Vertex> ret; Vector<Vector3> varr = p_arrays[RS::ARRAY_VERTEX]; @@ -537,8 +513,9 @@ Vector<SurfaceTool::Vertex> SurfaceTool::create_vertex_array_from_triangle_array Vector<float> warr = p_arrays[RS::ARRAY_WEIGHTS]; int vc = varr.size(); - if (vc == 0) + if (vc == 0) { return ret; + } int lformat = 0; if (varr.size()) { @@ -568,21 +545,26 @@ Vector<SurfaceTool::Vertex> SurfaceTool::create_vertex_array_from_triangle_array for (int i = 0; i < vc; i++) { Vertex v; - if (lformat & RS::ARRAY_FORMAT_VERTEX) + if (lformat & RS::ARRAY_FORMAT_VERTEX) { v.vertex = varr[i]; - if (lformat & RS::ARRAY_FORMAT_NORMAL) + } + if (lformat & RS::ARRAY_FORMAT_NORMAL) { v.normal = narr[i]; + } if (lformat & RS::ARRAY_FORMAT_TANGENT) { Plane p(tarr[i * 4 + 0], tarr[i * 4 + 1], tarr[i * 4 + 2], tarr[i * 4 + 3]); v.tangent = p.normal; v.binormal = p.normal.cross(v.tangent).normalized() * p.d; } - if (lformat & RS::ARRAY_FORMAT_COLOR) + if (lformat & RS::ARRAY_FORMAT_COLOR) { v.color = carr[i]; - if (lformat & RS::ARRAY_FORMAT_TEX_UV) + } + if (lformat & RS::ARRAY_FORMAT_TEX_UV) { v.uv = uvarr[i]; - if (lformat & RS::ARRAY_FORMAT_TEX_UV2) + } + if (lformat & RS::ARRAY_FORMAT_TEX_UV2) { v.uv2 = uv2arr[i]; + } if (lformat & RS::ARRAY_FORMAT_BONES) { Vector<int> b; b.resize(4); @@ -609,7 +591,6 @@ Vector<SurfaceTool::Vertex> SurfaceTool::create_vertex_array_from_triangle_array } void SurfaceTool::_create_list_from_arrays(Array arr, List<Vertex> *r_vertex, List<int> *r_index, int &lformat) { - Vector<Vector3> varr = arr[RS::ARRAY_VERTEX]; Vector<Vector3> narr = arr[RS::ARRAY_NORMAL]; Vector<float> tarr = arr[RS::ARRAY_TANGENT]; @@ -620,8 +601,9 @@ void SurfaceTool::_create_list_from_arrays(Array arr, List<Vertex> *r_vertex, Li Vector<float> warr = arr[RS::ARRAY_WEIGHTS]; int vc = varr.size(); - if (vc == 0) + if (vc == 0) { return; + } lformat = 0; if (varr.size()) { @@ -651,21 +633,26 @@ void SurfaceTool::_create_list_from_arrays(Array arr, List<Vertex> *r_vertex, Li for (int i = 0; i < vc; i++) { Vertex v; - if (lformat & RS::ARRAY_FORMAT_VERTEX) + if (lformat & RS::ARRAY_FORMAT_VERTEX) { v.vertex = varr[i]; - if (lformat & RS::ARRAY_FORMAT_NORMAL) + } + if (lformat & RS::ARRAY_FORMAT_NORMAL) { v.normal = narr[i]; + } if (lformat & RS::ARRAY_FORMAT_TANGENT) { Plane p(tarr[i * 4 + 0], tarr[i * 4 + 1], tarr[i * 4 + 2], tarr[i * 4 + 3]); v.tangent = p.normal; v.binormal = p.normal.cross(v.tangent).normalized() * p.d; } - if (lformat & RS::ARRAY_FORMAT_COLOR) + if (lformat & RS::ARRAY_FORMAT_COLOR) { v.color = carr[i]; - if (lformat & RS::ARRAY_FORMAT_TEX_UV) + } + if (lformat & RS::ARRAY_FORMAT_TEX_UV) { v.uv = uvarr[i]; - if (lformat & RS::ARRAY_FORMAT_TEX_UV2) + } + if (lformat & RS::ARRAY_FORMAT_TEX_UV2) { v.uv2 = uv2arr[i]; + } if (lformat & RS::ARRAY_FORMAT_BONES) { Vector<int> b; b.resize(4); @@ -693,7 +680,6 @@ void SurfaceTool::_create_list_from_arrays(Array arr, List<Vertex> *r_vertex, Li Vector<int> idx = arr[RS::ARRAY_INDEX]; int is = idx.size(); if (is) { - lformat |= RS::ARRAY_FORMAT_INDEX; const int *iarr = idx.ptr(); for (int i = 0; i < is; i++) { @@ -703,14 +689,12 @@ void SurfaceTool::_create_list_from_arrays(Array arr, List<Vertex> *r_vertex, Li } void SurfaceTool::create_from_triangle_arrays(const Array &p_arrays) { - clear(); primitive = Mesh::PRIMITIVE_TRIANGLES; _create_list_from_arrays(p_arrays, &vertex_array, &index_array, format); } void SurfaceTool::create_from(const Ref<Mesh> &p_existing, int p_surface) { - clear(); primitive = p_existing->surface_get_primitive_type(p_surface); _create_list(p_existing, p_surface, &vertex_array, &index_array, format); @@ -738,7 +722,6 @@ void SurfaceTool::create_from_blend_shape(const Ref<Mesh> &p_existing, int p_sur } void SurfaceTool::append_from(const Ref<Mesh> &p_existing, int p_surface, const Transform &p_xform) { - if (vertex_array.size() == 0) { primitive = p_existing->surface_get_primitive_type(p_surface); format = 0; @@ -752,7 +735,6 @@ void SurfaceTool::append_from(const Ref<Mesh> &p_existing, int p_surface, const int vfrom = vertex_array.size(); for (List<Vertex>::Element *E = nvertices.front(); E; E = E->next()) { - Vertex v = E->get(); v.vertex = p_xform.xform(v.vertex); if (nformat & RS::ARRAY_FORMAT_NORMAL) { @@ -767,7 +749,6 @@ void SurfaceTool::append_from(const Ref<Mesh> &p_existing, int p_surface, const } for (List<int>::Element *E = nindices.front(); E; E = E->next()) { - int dst_index = E->get() + vfrom; index_array.push_back(dst_index); } @@ -785,7 +766,6 @@ struct TangentGenerationContextUserData { } // namespace int SurfaceTool::mikktGetNumFaces(const SMikkTSpaceContext *pContext) { - TangentGenerationContextUserData &triangle_data = *reinterpret_cast<TangentGenerationContextUserData *>(pContext->m_pUserData); if (triangle_data.indices.size() > 0) { @@ -794,12 +774,12 @@ int SurfaceTool::mikktGetNumFaces(const SMikkTSpaceContext *pContext) { return triangle_data.vertices.size() / 3; } } -int SurfaceTool::mikktGetNumVerticesOfFace(const SMikkTSpaceContext *pContext, const int iFace) { +int SurfaceTool::mikktGetNumVerticesOfFace(const SMikkTSpaceContext *pContext, const int iFace) { return 3; //always 3 } -void SurfaceTool::mikktGetPosition(const SMikkTSpaceContext *pContext, float fvPosOut[], const int iFace, const int iVert) { +void SurfaceTool::mikktGetPosition(const SMikkTSpaceContext *pContext, float fvPosOut[], const int iFace, const int iVert) { TangentGenerationContextUserData &triangle_data = *reinterpret_cast<TangentGenerationContextUserData *>(pContext->m_pUserData); Vector3 v; if (triangle_data.indices.size() > 0) { @@ -817,7 +797,6 @@ void SurfaceTool::mikktGetPosition(const SMikkTSpaceContext *pContext, float fvP } void SurfaceTool::mikktGetNormal(const SMikkTSpaceContext *pContext, float fvNormOut[], const int iFace, const int iVert) { - TangentGenerationContextUserData &triangle_data = *reinterpret_cast<TangentGenerationContextUserData *>(pContext->m_pUserData); Vector3 v; if (triangle_data.indices.size() > 0) { @@ -833,8 +812,8 @@ void SurfaceTool::mikktGetNormal(const SMikkTSpaceContext *pContext, float fvNor fvNormOut[1] = v.y; fvNormOut[2] = v.z; } -void SurfaceTool::mikktGetTexCoord(const SMikkTSpaceContext *pContext, float fvTexcOut[], const int iFace, const int iVert) { +void SurfaceTool::mikktGetTexCoord(const SMikkTSpaceContext *pContext, float fvTexcOut[], const int iFace, const int iVert) { TangentGenerationContextUserData &triangle_data = *reinterpret_cast<TangentGenerationContextUserData *>(pContext->m_pUserData); Vector2 v; if (triangle_data.indices.size() > 0) { @@ -852,7 +831,6 @@ void SurfaceTool::mikktGetTexCoord(const SMikkTSpaceContext *pContext, float fvT void SurfaceTool::mikktSetTSpaceDefault(const SMikkTSpaceContext *pContext, const float fvTangent[], const float fvBiTangent[], const float fMagS, const float fMagT, const tbool bIsOrientationPreserving, const int iFace, const int iVert) { - TangentGenerationContextUserData &triangle_data = *reinterpret_cast<TangentGenerationContextUserData *>(pContext->m_pUserData); Vertex *vtx = nullptr; if (triangle_data.indices.size() > 0) { @@ -871,7 +849,6 @@ void SurfaceTool::mikktSetTSpaceDefault(const SMikkTSpaceContext *pContext, cons } void SurfaceTool::generate_tangents() { - ERR_FAIL_COND(!(format & Mesh::ARRAY_FORMAT_TEX_UV)); ERR_FAIL_COND(!(format & Mesh::ARRAY_FORMAT_NORMAL)); @@ -909,7 +886,6 @@ void SurfaceTool::generate_tangents() { } void SurfaceTool::generate_normals(bool p_flip) { - ERR_FAIL_COND(primitive != Mesh::PRIMITIVE_TRIANGLES); bool was_indexed = index_array.size(); @@ -920,12 +896,12 @@ void SurfaceTool::generate_normals(bool p_flip) { int count = 0; bool smooth = false; - if (smooth_groups.has(0)) + if (smooth_groups.has(0)) { smooth = smooth_groups[0]; + } List<Vertex>::Element *B = vertex_array.front(); for (List<Vertex>::Element *E = B; E;) { - List<Vertex>::Element *v[3]; v[0] = E; v[1] = v[0]->next(); @@ -935,15 +911,14 @@ void SurfaceTool::generate_normals(bool p_flip) { E = v[2]->next(); Vector3 normal; - if (!p_flip) + if (!p_flip) { normal = Plane(v[0]->get().vertex, v[1]->get().vertex, v[2]->get().vertex).normal; - else + } else { normal = Plane(v[2]->get().vertex, v[1]->get().vertex, v[0]->get().vertex).normal; + } if (smooth) { - for (int i = 0; i < 3; i++) { - Vector3 *lv = vertex_hash.getptr(v[i]->get()); if (!lv) { vertex_hash.set(v[i]->get(), normal); @@ -952,20 +927,15 @@ void SurfaceTool::generate_normals(bool p_flip) { } } } else { - for (int i = 0; i < 3; i++) { - v[i]->get().normal = normal; } } count += 3; if (smooth_groups.has(count) || !E) { - if (vertex_hash.size()) { - while (B != E) { - Vector3 *lv = vertex_hash.getptr(B->get()); if (lv) { B->get().normal = lv->normalized(); @@ -994,12 +964,10 @@ void SurfaceTool::generate_normals(bool p_flip) { } void SurfaceTool::set_material(const Ref<Material> &p_material) { - material = p_material; } void SurfaceTool::clear() { - begun = false; primitive = Mesh::PRIMITIVE_LINES; format = 0; @@ -1012,7 +980,6 @@ void SurfaceTool::clear() { } void SurfaceTool::_bind_methods() { - ClassDB::bind_method(D_METHOD("begin", "primitive"), &SurfaceTool::begin); ClassDB::bind_method(D_METHOD("add_vertex", "vertex"), &SurfaceTool::add_vertex); @@ -1046,7 +1013,6 @@ void SurfaceTool::_bind_methods() { } SurfaceTool::SurfaceTool() { - first = false; begun = false; primitive = Mesh::PRIMITIVE_LINES; |