载入中...
搜索中...
未找到
SoftBody3DGraphics.cpp
浏览该文件的文档.
2
3#include "graphics/Graphics.h"
4#include "graphics/Mesh.h"
6
7#include <glm/glm.hpp>
8
9#include <algorithm>
10#include <cstdint>
11#include <vector>
12
13namespace eve::physics {
14
16 body_ = body;
17 mesh_ = nullptr;
18 meshVertexCount_ = 0;
19 meshIndexCount_ = 0;
20}
21
22void SoftBody3DRenderer::setColor(float r, float g, float b, float a) {
23 colorR_ = std::clamp(r, 0.f, 1.f);
24 colorG_ = std::clamp(g, 0.f, 1.f);
25 colorB_ = std::clamp(b, 0.f, 1.f);
26 colorA_ = std::clamp(a, 0.f, 1.f);
27}
28
30 if (!graphics || !body_ || body_->isDestroyed()) return;
31 std::vector<float> positions;
32 std::vector<float> normals;
33 std::vector<float> uv;
34 std::vector<uint32_t> indices;
35 positions.reserve(static_cast<size_t>(body_->getParticleCount()) * 18);
36 normals.reserve(static_cast<size_t>(body_->getParticleCount()) * 18);
37 uv.reserve(static_cast<size_t>(body_->getParticleCount()) * 12);
38 auto addQuad = [&](int a, int b, int c, int d) {
39 const glm::vec3 pa(body_->getParticleX(a), body_->getParticleY(a), body_->getParticleZ(a));
40 const glm::vec3 pb(body_->getParticleX(b), body_->getParticleY(b), body_->getParticleZ(b));
41 const glm::vec3 pc(body_->getParticleX(c), body_->getParticleY(c), body_->getParticleZ(c));
42 const glm::vec3 normal = glm::normalize(glm::cross(pb - pa, pc - pa));
43 const uint32_t base = static_cast<uint32_t>(positions.size() / 3);
44 const int vertices[4] = {a, b, c, d};
45 const float tex[8] = {0.f, 0.f, 1.f, 0.f, 1.f, 1.f, 0.f, 1.f};
46 for (int i = 0; i < 4; ++i) {
47 const int p = vertices[i];
48 positions.insert(positions.end(),
49 {body_->getParticleX(p), body_->getParticleY(p), body_->getParticleZ(p)});
50 normals.insert(normals.end(), {normal.x, normal.y, normal.z});
51 uv.insert(uv.end(), {tex[i * 2], tex[i * 2 + 1]});
52 }
53 indices.insert(indices.end(), {base, base + 1, base + 2, base, base + 2, base + 3});
54 };
55 const int cols = body_->getCols(), rows = body_->getRows(), layers = body_->getLayers();
56 auto indexOf = [=](int x, int y, int z) { return (z * rows + y) * cols + x; };
57 for (int z = 0; z + 1 < layers; ++z)
58 for (int y = 0; y + 1 < rows; ++y) {
59 addQuad(indexOf(0, y, z), indexOf(0, y, z + 1), indexOf(0, y + 1, z + 1), indexOf(0, y + 1, z));
60 addQuad(indexOf(cols - 1, y, z + 1), indexOf(cols - 1, y, z), indexOf(cols - 1, y + 1, z),
61 indexOf(cols - 1, y + 1, z + 1));
62 }
63 for (int z = 0; z + 1 < layers; ++z)
64 for (int x = 0; x + 1 < cols; ++x) {
65 addQuad(indexOf(x, 0, z + 1), indexOf(x, 0, z), indexOf(x + 1, 0, z), indexOf(x + 1, 0, z + 1));
66 addQuad(indexOf(x, rows - 1, z), indexOf(x, rows - 1, z + 1), indexOf(x + 1, rows - 1, z + 1),
67 indexOf(x + 1, rows - 1, z));
68 }
69 for (int y = 0; y + 1 < rows; ++y)
70 for (int x = 0; x + 1 < cols; ++x) {
71 addQuad(indexOf(x + 1, y, 0), indexOf(x, y, 0), indexOf(x, y + 1, 0), indexOf(x + 1, y + 1, 0));
72 addQuad(indexOf(x, y, layers - 1), indexOf(x + 1, y, layers - 1),
73 indexOf(x + 1, y + 1, layers - 1), indexOf(x, y + 1, layers - 1));
74 }
75 const int vertexCount = static_cast<int>(positions.size() / 3);
76 const int indexCount = static_cast<int>(indices.size());
77 if (!mesh_ || meshVertexCount_ != vertexCount || meshIndexCount_ != indexCount) {
78 mesh_ = graphics->newMeshFromArrays(positions.data(), normals.data(), uv.data(), vertexCount, indices.data(),
80 meshVertexCount_ = vertexCount;
81 meshIndexCount_ = indexCount;
82 } else {
83 graphics->updateMeshVertices(mesh_, positions.data(), normals.data(), uv.data(), vertexCount, nullptr, 0);
84 }
85 if (mesh_) graphics->drawMesh(mesh_, glm::mat4(1.f), nullptr, graphics::Color(colorR_, colorG_, colorB_, colorA_));
86}
87
88} // namespace eve::physics
float y
Definition AnimClip.cpp:738
float x
Definition AnimClip.cpp:738
float z
Definition AnimClip.cpp:738
float uv
glm::vec4 p[6]
int rows
int cols
std::uint32_t vertexCount
std::uint32_t indexCount
tensor::Graph g
Definition GpuGraph.cpp:7
double r
std::vector< std::uint32_t > indices
std::vector< float > normals
std::vector< float > positions
std::int32_t c
MeleePoint3 b
Definition MeleeHit.cpp:41
MeleePoint3 a
Definition MeleeHit.cpp:40
Texture * normal
std::vector< Point > vertices
float d
std::string body
virtual void drawMesh(Mesh *mesh, const glm::mat4 &model, Texture *texture, const Color &tint)=0
Draw one mesh with model matrix. Requires begin3DFrame() (or an open swapchain pass).
virtual bool updateMeshVertices(Mesh *mesh, const float *posXYZ, const float *nrmXYZ, const float *uvST, int vertexCount, const uint32_t *indices, int indexCount)=0
In-place update of a mesh's vertex/index data (CPU -> host-visible VBO). Mirrors bakeMeshMorph: the u...
virtual Mesh * newMeshFromArrays(const float *posXYZ, const float *nrmXYZ, const float *uvST, int vertexCount, const uint32_t *indices, int indexCount)=0
Upload a triangle mesh from packed CPU arrays. Owned by Graphics. posXYZ required (vertexCount*3)....
void draw(graphics::Graphics *graphics)
Update the surface cache and draw it in the current 3D frame.
void setBody(SoftBody3D *body)
Replace the borrowed runtime; null disables drawing.
void setColor(float r, float g, float b, float a)
Set the clamped RGBA presentation color.
Volumetric particle soft body using overlapping shape-matching clusters.
Definition SoftBody3D.h:27
bool isDestroyed() const noexcept
Whether destroy() has disabled this runtime instance.
Definition SoftBody3D.h:169
int getParticleCount() const
Definition SoftBody3D.h:174
float getParticleZ(int index) const
float getParticleX(int index) const
float getParticleY(int index) const
eve::Color Color
RGBA color used by every graphics draw call. Lives inside eve::graphics so including a graphics heade...
Definition Color.h:13
Optional physics backend for vehicle mobility and body attach.
Definition Climbing.h:36