mirror of
https://github.com/overte-org/overte.git
synced 2025-08-10 02:31:13 +02:00
Merge pull request #11028 from sethalves/script-getmeshes-for-models
Script getmeshes for models
This commit is contained in:
commit
a21da8613c
14 changed files with 187 additions and 24 deletions
|
@ -23,6 +23,7 @@
|
||||||
#include <PerfStat.h>
|
#include <PerfStat.h>
|
||||||
#include <render/Scene.h>
|
#include <render/Scene.h>
|
||||||
#include <DependencyManager.h>
|
#include <DependencyManager.h>
|
||||||
|
#include <shared/QtHelpers.h>
|
||||||
|
|
||||||
#include "EntityTreeRenderer.h"
|
#include "EntityTreeRenderer.h"
|
||||||
#include "EntitiesRendererLogging.h"
|
#include "EntitiesRendererLogging.h"
|
||||||
|
@ -1282,3 +1283,11 @@ void RenderableModelEntityItem::mapJoints(const QStringList& modelJointNames) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool RenderableModelEntityItem::getMeshes(MeshProxyList& result) {
|
||||||
|
if (!_model || !_model->isLoaded()) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
BLOCKING_INVOKE_METHOD(_model.get(), "getMeshes", Q_RETURN_ARG(MeshProxyList, result));
|
||||||
|
return !result.isEmpty();
|
||||||
|
}
|
||||||
|
|
|
@ -116,6 +116,8 @@ public:
|
||||||
return _animation;
|
return _animation;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool getMeshes(MeshProxyList& result) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
QVariantMap parseTexturesToMap(QString textures);
|
QVariantMap parseTexturesToMap(QString textures);
|
||||||
void remapTextures();
|
void remapTextures();
|
||||||
|
|
|
@ -1663,6 +1663,7 @@ bool RenderablePolyVoxEntityItem::getMeshes(MeshProxyList& result) {
|
||||||
// the mesh will be in voxel-space. transform it into object-space
|
// the mesh will be in voxel-space. transform it into object-space
|
||||||
meshProxy = new SimpleMeshProxy(
|
meshProxy = new SimpleMeshProxy(
|
||||||
_mesh->map([=](glm::vec3 position){ return glm::vec3(transform * glm::vec4(position, 1.0f)); },
|
_mesh->map([=](glm::vec3 position){ return glm::vec3(transform * glm::vec4(position, 1.0f)); },
|
||||||
|
[=](glm::vec3 color){ return color; },
|
||||||
[=](glm::vec3 normal){ return glm::normalize(glm::vec3(transform * glm::vec4(normal, 0.0f))); },
|
[=](glm::vec3 normal){ return glm::normalize(glm::vec3(transform * glm::vec4(normal, 0.0f))); },
|
||||||
[&](uint32_t index){ return index; }));
|
[&](uint32_t index){ return index; }));
|
||||||
result << meshProxy;
|
result << meshProxy;
|
||||||
|
|
|
@ -1736,9 +1736,7 @@ glm::mat4 EntityScriptingInterface::getEntityTransform(const QUuid& entityID) {
|
||||||
if (entity) {
|
if (entity) {
|
||||||
glm::mat4 translation = glm::translate(entity->getPosition());
|
glm::mat4 translation = glm::translate(entity->getPosition());
|
||||||
glm::mat4 rotation = glm::mat4_cast(entity->getRotation());
|
glm::mat4 rotation = glm::mat4_cast(entity->getRotation());
|
||||||
glm::mat4 registration = glm::translate(ENTITY_ITEM_DEFAULT_REGISTRATION_POINT -
|
result = translation * rotation;
|
||||||
entity->getRegistrationPoint());
|
|
||||||
result = translation * rotation * registration;
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -1753,9 +1751,7 @@ glm::mat4 EntityScriptingInterface::getEntityLocalTransform(const QUuid& entityI
|
||||||
if (entity) {
|
if (entity) {
|
||||||
glm::mat4 translation = glm::translate(entity->getLocalPosition());
|
glm::mat4 translation = glm::translate(entity->getLocalPosition());
|
||||||
glm::mat4 rotation = glm::mat4_cast(entity->getLocalOrientation());
|
glm::mat4 rotation = glm::mat4_cast(entity->getLocalOrientation());
|
||||||
glm::mat4 registration = glm::translate(ENTITY_ITEM_DEFAULT_REGISTRATION_POINT -
|
result = translation * rotation;
|
||||||
entity->getRegistrationPoint());
|
|
||||||
result = translation * rotation * registration;
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
@ -118,7 +118,7 @@ glm::vec3 OBJTokenizer::getVec3() {
|
||||||
auto z = getFloat();
|
auto z = getFloat();
|
||||||
auto v = glm::vec3(x, y, z);
|
auto v = glm::vec3(x, y, z);
|
||||||
while (isNextTokenFloat()) {
|
while (isNextTokenFloat()) {
|
||||||
// the spec(s) get(s) vague here. might be w, might be a color... chop it off.
|
// ignore any following floats
|
||||||
nextToken();
|
nextToken();
|
||||||
}
|
}
|
||||||
return v;
|
return v;
|
||||||
|
@ -139,7 +139,7 @@ bool OBJTokenizer::getVertex(glm::vec3& vertex, glm::vec3& vertexColor) {
|
||||||
// only a single value) that it's a vertex color.
|
// only a single value) that it's a vertex color.
|
||||||
r = getFloat();
|
r = getFloat();
|
||||||
if (isNextTokenFloat()) {
|
if (isNextTokenFloat()) {
|
||||||
// Safe to assume the following values are the green/blue components.
|
// Safe to assume the following values are the green/blue components.
|
||||||
g = getFloat();
|
g = getFloat();
|
||||||
b = getFloat();
|
b = getFloat();
|
||||||
|
|
||||||
|
@ -351,6 +351,8 @@ bool OBJReader::parseOBJGroup(OBJTokenizer& tokenizer, const QVariantHash& mappi
|
||||||
bool result = true;
|
bool result = true;
|
||||||
int originalFaceCountForDebugging = 0;
|
int originalFaceCountForDebugging = 0;
|
||||||
QString currentGroup;
|
QString currentGroup;
|
||||||
|
bool anyVertexColor { false };
|
||||||
|
int vertexCount { 0 };
|
||||||
|
|
||||||
setMeshPartDefaults(meshPart, QString("dontknow") + QString::number(mesh.parts.count()));
|
setMeshPartDefaults(meshPart, QString("dontknow") + QString::number(mesh.parts.count()));
|
||||||
|
|
||||||
|
@ -412,14 +414,25 @@ bool OBJReader::parseOBJGroup(OBJTokenizer& tokenizer, const QVariantHash& mappi
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
} else if (token == "v") {
|
} else if (token == "v") {
|
||||||
glm::vec3 vertex, vertexColor;
|
glm::vec3 vertex;
|
||||||
|
glm::vec3 vertexColor { glm::vec3(1.0f) };
|
||||||
|
|
||||||
bool hasVertexColor = tokenizer.getVertex(vertex, vertexColor);
|
bool hasVertexColor = tokenizer.getVertex(vertex, vertexColor);
|
||||||
vertices.append(vertex);
|
vertices.append(vertex);
|
||||||
|
|
||||||
if(hasVertexColor) {
|
// if any vertex has color, they all need to.
|
||||||
|
if (hasVertexColor && !anyVertexColor) {
|
||||||
|
// we've had a gap of zero or more vertices without color, followed
|
||||||
|
// by one that has color. catch up:
|
||||||
|
for (int i = 0; i < vertexCount; i++) {
|
||||||
|
vertexColors.append(glm::vec3(1.0f));
|
||||||
|
}
|
||||||
|
anyVertexColor = true;
|
||||||
|
}
|
||||||
|
if (anyVertexColor) {
|
||||||
vertexColors.append(vertexColor);
|
vertexColors.append(vertexColor);
|
||||||
}
|
}
|
||||||
|
vertexCount++;
|
||||||
} else if (token == "vn") {
|
} else if (token == "vn") {
|
||||||
normals.append(tokenizer.getVec3());
|
normals.append(tokenizer.getVec3());
|
||||||
} else if (token == "vt") {
|
} else if (token == "vt") {
|
||||||
|
|
|
@ -40,8 +40,6 @@ static QString formatFloat(double n) {
|
||||||
}
|
}
|
||||||
|
|
||||||
bool writeOBJToTextStream(QTextStream& out, QList<MeshPointer> meshes) {
|
bool writeOBJToTextStream(QTextStream& out, QList<MeshPointer> meshes) {
|
||||||
int attributeTypeNormal = gpu::Stream::InputSlot::NORMAL; // libraries/gpu/src/gpu/Stream.h
|
|
||||||
|
|
||||||
// each mesh's vertices are numbered from zero. We're combining all their vertices into one list here,
|
// each mesh's vertices are numbered from zero. We're combining all their vertices into one list here,
|
||||||
// so keep track of the start index for each mesh.
|
// so keep track of the start index for each mesh.
|
||||||
QList<int> meshVertexStartOffset;
|
QList<int> meshVertexStartOffset;
|
||||||
|
@ -49,10 +47,15 @@ bool writeOBJToTextStream(QTextStream& out, QList<MeshPointer> meshes) {
|
||||||
int currentVertexStartOffset = 0;
|
int currentVertexStartOffset = 0;
|
||||||
int currentNormalStartOffset = 0;
|
int currentNormalStartOffset = 0;
|
||||||
|
|
||||||
// write out vertices
|
// write out vertices (and maybe colors)
|
||||||
foreach (const MeshPointer& mesh, meshes) {
|
foreach (const MeshPointer& mesh, meshes) {
|
||||||
meshVertexStartOffset.append(currentVertexStartOffset);
|
meshVertexStartOffset.append(currentVertexStartOffset);
|
||||||
const gpu::BufferView& vertexBuffer = mesh->getVertexBuffer();
|
const gpu::BufferView& vertexBuffer = mesh->getVertexBuffer();
|
||||||
|
|
||||||
|
const gpu::BufferView& colorsBufferView = mesh->getAttributeBuffer(gpu::Stream::COLOR);
|
||||||
|
gpu::BufferView::Index numColors = (gpu::BufferView::Index)colorsBufferView.getNumElements();
|
||||||
|
gpu::BufferView::Index colorIndex = 0;
|
||||||
|
|
||||||
int vertexCount = 0;
|
int vertexCount = 0;
|
||||||
gpu::BufferView::Iterator<const glm::vec3> vertexItr = vertexBuffer.cbegin<const glm::vec3>();
|
gpu::BufferView::Iterator<const glm::vec3> vertexItr = vertexBuffer.cbegin<const glm::vec3>();
|
||||||
while (vertexItr != vertexBuffer.cend<const glm::vec3>()) {
|
while (vertexItr != vertexBuffer.cend<const glm::vec3>()) {
|
||||||
|
@ -60,7 +63,15 @@ bool writeOBJToTextStream(QTextStream& out, QList<MeshPointer> meshes) {
|
||||||
out << "v ";
|
out << "v ";
|
||||||
out << formatFloat(v[0]) << " ";
|
out << formatFloat(v[0]) << " ";
|
||||||
out << formatFloat(v[1]) << " ";
|
out << formatFloat(v[1]) << " ";
|
||||||
out << formatFloat(v[2]) << "\n";
|
out << formatFloat(v[2]);
|
||||||
|
if (colorIndex < numColors) {
|
||||||
|
glm::vec3 color = colorsBufferView.get<glm::vec3>(colorIndex);
|
||||||
|
out << " " << formatFloat(color[0]);
|
||||||
|
out << " " << formatFloat(color[1]);
|
||||||
|
out << " " << formatFloat(color[2]);
|
||||||
|
colorIndex++;
|
||||||
|
}
|
||||||
|
out << "\n";
|
||||||
vertexItr++;
|
vertexItr++;
|
||||||
vertexCount++;
|
vertexCount++;
|
||||||
}
|
}
|
||||||
|
@ -72,7 +83,7 @@ bool writeOBJToTextStream(QTextStream& out, QList<MeshPointer> meshes) {
|
||||||
bool haveNormals = true;
|
bool haveNormals = true;
|
||||||
foreach (const MeshPointer& mesh, meshes) {
|
foreach (const MeshPointer& mesh, meshes) {
|
||||||
meshNormalStartOffset.append(currentNormalStartOffset);
|
meshNormalStartOffset.append(currentNormalStartOffset);
|
||||||
const gpu::BufferView& normalsBufferView = mesh->getAttributeBuffer(attributeTypeNormal);
|
const gpu::BufferView& normalsBufferView = mesh->getAttributeBuffer(gpu::Stream::InputSlot::NORMAL);
|
||||||
gpu::BufferView::Index numNormals = (gpu::BufferView::Index)normalsBufferView.getNumElements();
|
gpu::BufferView::Index numNormals = (gpu::BufferView::Index)normalsBufferView.getNumElements();
|
||||||
for (gpu::BufferView::Index i = 0; i < numNormals; i++) {
|
for (gpu::BufferView::Index i = 0; i < numNormals; i++) {
|
||||||
glm::vec3 normal = normalsBufferView.get<glm::vec3>(i);
|
glm::vec3 normal = normalsBufferView.get<glm::vec3>(i);
|
||||||
|
|
|
@ -192,7 +192,7 @@ public:
|
||||||
BufferView(const BufferPointer& buffer, Size offset, Size size, const Element& element = DEFAULT_ELEMENT);
|
BufferView(const BufferPointer& buffer, Size offset, Size size, const Element& element = DEFAULT_ELEMENT);
|
||||||
BufferView(const BufferPointer& buffer, Size offset, Size size, uint16 stride, const Element& element = DEFAULT_ELEMENT);
|
BufferView(const BufferPointer& buffer, Size offset, Size size, uint16 stride, const Element& element = DEFAULT_ELEMENT);
|
||||||
|
|
||||||
Size getNumElements() const { return (_size - _offset) / _stride; }
|
Size getNumElements() const { return _size / _stride; }
|
||||||
|
|
||||||
//Template iterator with random access on the buffer sysmem
|
//Template iterator with random access on the buffer sysmem
|
||||||
template<typename T>
|
template<typename T>
|
||||||
|
|
|
@ -11,8 +11,6 @@
|
||||||
|
|
||||||
#include "Geometry.h"
|
#include "Geometry.h"
|
||||||
|
|
||||||
#include <QDebug>
|
|
||||||
|
|
||||||
using namespace model;
|
using namespace model;
|
||||||
|
|
||||||
Mesh::Mesh() :
|
Mesh::Mesh() :
|
||||||
|
@ -136,11 +134,13 @@ Box Mesh::evalPartsBound(int partStart, int partEnd) const {
|
||||||
|
|
||||||
|
|
||||||
model::MeshPointer Mesh::map(std::function<glm::vec3(glm::vec3)> vertexFunc,
|
model::MeshPointer Mesh::map(std::function<glm::vec3(glm::vec3)> vertexFunc,
|
||||||
|
std::function<glm::vec3(glm::vec3)> colorFunc,
|
||||||
std::function<glm::vec3(glm::vec3)> normalFunc,
|
std::function<glm::vec3(glm::vec3)> normalFunc,
|
||||||
std::function<uint32_t(uint32_t)> indexFunc) {
|
std::function<uint32_t(uint32_t)> indexFunc) const {
|
||||||
// vertex data
|
// vertex data
|
||||||
const gpu::BufferView& vertexBufferView = getVertexBuffer();
|
const gpu::BufferView& vertexBufferView = getVertexBuffer();
|
||||||
gpu::BufferView::Index numVertices = (gpu::BufferView::Index)getNumVertices();
|
gpu::BufferView::Index numVertices = (gpu::BufferView::Index)getNumVertices();
|
||||||
|
|
||||||
gpu::Resource::Size vertexSize = numVertices * sizeof(glm::vec3);
|
gpu::Resource::Size vertexSize = numVertices * sizeof(glm::vec3);
|
||||||
unsigned char* resultVertexData = new unsigned char[vertexSize];
|
unsigned char* resultVertexData = new unsigned char[vertexSize];
|
||||||
unsigned char* vertexDataCursor = resultVertexData;
|
unsigned char* vertexDataCursor = resultVertexData;
|
||||||
|
@ -151,6 +151,21 @@ model::MeshPointer Mesh::map(std::function<glm::vec3(glm::vec3)> vertexFunc,
|
||||||
vertexDataCursor += sizeof(pos);
|
vertexDataCursor += sizeof(pos);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// color data
|
||||||
|
int attributeTypeColor = gpu::Stream::COLOR;
|
||||||
|
const gpu::BufferView& colorsBufferView = getAttributeBuffer(attributeTypeColor);
|
||||||
|
gpu::BufferView::Index numColors = (gpu::BufferView::Index)colorsBufferView.getNumElements();
|
||||||
|
|
||||||
|
gpu::Resource::Size colorSize = numColors * sizeof(glm::vec3);
|
||||||
|
unsigned char* resultColorData = new unsigned char[colorSize];
|
||||||
|
unsigned char* colorDataCursor = resultColorData;
|
||||||
|
|
||||||
|
for (gpu::BufferView::Index i = 0; i < numColors; i++) {
|
||||||
|
glm::vec3 color = colorFunc(colorsBufferView.get<glm::vec3>(i));
|
||||||
|
memcpy(colorDataCursor, &color, sizeof(color));
|
||||||
|
colorDataCursor += sizeof(color);
|
||||||
|
}
|
||||||
|
|
||||||
// normal data
|
// normal data
|
||||||
int attributeTypeNormal = gpu::Stream::InputSlot::NORMAL; // libraries/gpu/src/gpu/Stream.h
|
int attributeTypeNormal = gpu::Stream::InputSlot::NORMAL; // libraries/gpu/src/gpu/Stream.h
|
||||||
const gpu::BufferView& normalsBufferView = getAttributeBuffer(attributeTypeNormal);
|
const gpu::BufferView& normalsBufferView = getAttributeBuffer(attributeTypeNormal);
|
||||||
|
@ -187,6 +202,12 @@ model::MeshPointer Mesh::map(std::function<glm::vec3(glm::vec3)> vertexFunc,
|
||||||
gpu::BufferView resultVertexBufferView(resultVertexBufferPointer, vertexElement);
|
gpu::BufferView resultVertexBufferView(resultVertexBufferPointer, vertexElement);
|
||||||
result->setVertexBuffer(resultVertexBufferView);
|
result->setVertexBuffer(resultVertexBufferView);
|
||||||
|
|
||||||
|
gpu::Element colorElement = gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ);
|
||||||
|
gpu::Buffer* resultColorsBuffer = new gpu::Buffer(colorSize, resultColorData);
|
||||||
|
gpu::BufferPointer resultColorsBufferPointer(resultColorsBuffer);
|
||||||
|
gpu::BufferView resultColorsBufferView(resultColorsBufferPointer, colorElement);
|
||||||
|
result->addAttribute(attributeTypeColor, resultColorsBufferView);
|
||||||
|
|
||||||
gpu::Element normalElement = gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ);
|
gpu::Element normalElement = gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ);
|
||||||
gpu::Buffer* resultNormalsBuffer = new gpu::Buffer(normalSize, resultNormalData);
|
gpu::Buffer* resultNormalsBuffer = new gpu::Buffer(normalSize, resultNormalData);
|
||||||
gpu::BufferPointer resultNormalsBufferPointer(resultNormalsBuffer);
|
gpu::BufferPointer resultNormalsBufferPointer(resultNormalsBuffer);
|
||||||
|
@ -215,6 +236,7 @@ model::MeshPointer Mesh::map(std::function<glm::vec3(glm::vec3)> vertexFunc,
|
||||||
|
|
||||||
|
|
||||||
void Mesh::forEach(std::function<void(glm::vec3)> vertexFunc,
|
void Mesh::forEach(std::function<void(glm::vec3)> vertexFunc,
|
||||||
|
std::function<void(glm::vec3)> colorFunc,
|
||||||
std::function<void(glm::vec3)> normalFunc,
|
std::function<void(glm::vec3)> normalFunc,
|
||||||
std::function<void(uint32_t)> indexFunc) {
|
std::function<void(uint32_t)> indexFunc) {
|
||||||
// vertex data
|
// vertex data
|
||||||
|
@ -224,6 +246,14 @@ void Mesh::forEach(std::function<void(glm::vec3)> vertexFunc,
|
||||||
vertexFunc(vertexBufferView.get<glm::vec3>(i));
|
vertexFunc(vertexBufferView.get<glm::vec3>(i));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// color data
|
||||||
|
int attributeTypeColor = gpu::Stream::InputSlot::COLOR; // libraries/gpu/src/gpu/Stream.h
|
||||||
|
const gpu::BufferView& colorsBufferView = getAttributeBuffer(attributeTypeColor);
|
||||||
|
gpu::BufferView::Index numColors = (gpu::BufferView::Index)colorsBufferView.getNumElements();
|
||||||
|
for (gpu::BufferView::Index i = 0; i < numColors; i++) {
|
||||||
|
colorFunc(colorsBufferView.get<glm::vec3>(i));
|
||||||
|
}
|
||||||
|
|
||||||
// normal data
|
// normal data
|
||||||
int attributeTypeNormal = gpu::Stream::InputSlot::NORMAL; // libraries/gpu/src/gpu/Stream.h
|
int attributeTypeNormal = gpu::Stream::InputSlot::NORMAL; // libraries/gpu/src/gpu/Stream.h
|
||||||
const gpu::BufferView& normalsBufferView = getAttributeBuffer(attributeTypeNormal);
|
const gpu::BufferView& normalsBufferView = getAttributeBuffer(attributeTypeNormal);
|
||||||
|
|
|
@ -123,10 +123,12 @@ public:
|
||||||
|
|
||||||
// create a copy of this mesh after passing its vertices, normals, and indexes though the provided functions
|
// create a copy of this mesh after passing its vertices, normals, and indexes though the provided functions
|
||||||
MeshPointer map(std::function<glm::vec3(glm::vec3)> vertexFunc,
|
MeshPointer map(std::function<glm::vec3(glm::vec3)> vertexFunc,
|
||||||
|
std::function<glm::vec3(glm::vec3)> colorFunc,
|
||||||
std::function<glm::vec3(glm::vec3)> normalFunc,
|
std::function<glm::vec3(glm::vec3)> normalFunc,
|
||||||
std::function<uint32_t(uint32_t)> indexFunc);
|
std::function<uint32_t(uint32_t)> indexFunc) const;
|
||||||
|
|
||||||
void forEach(std::function<void(glm::vec3)> vertexFunc,
|
void forEach(std::function<void(glm::vec3)> vertexFunc,
|
||||||
|
std::function<void(glm::vec3)> colorFunc,
|
||||||
std::function<void(glm::vec3)> normalFunc,
|
std::function<void(glm::vec3)> normalFunc,
|
||||||
std::function<void(uint32_t)> indexFunc);
|
std::function<void(uint32_t)> indexFunc);
|
||||||
|
|
||||||
|
|
|
@ -24,6 +24,7 @@
|
||||||
#include <PerfStat.h>
|
#include <PerfStat.h>
|
||||||
#include <ViewFrustum.h>
|
#include <ViewFrustum.h>
|
||||||
#include <GLMHelpers.h>
|
#include <GLMHelpers.h>
|
||||||
|
#include <model-networking/SimpleMeshProxy.h>
|
||||||
|
|
||||||
#include "AbstractViewStateInterface.h"
|
#include "AbstractViewStateInterface.h"
|
||||||
#include "MeshPartPayload.h"
|
#include "MeshPartPayload.h"
|
||||||
|
@ -462,6 +463,41 @@ bool Model::convexHullContains(glm::vec3 point) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MeshProxyList Model::getMeshes() const {
|
||||||
|
MeshProxyList result;
|
||||||
|
const Geometry::Pointer& renderGeometry = getGeometry();
|
||||||
|
const Geometry::GeometryMeshes& meshes = renderGeometry->getMeshes();
|
||||||
|
|
||||||
|
if (!isLoaded()) {
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
Transform offset;
|
||||||
|
offset.setScale(_scale);
|
||||||
|
offset.postTranslate(_offset);
|
||||||
|
glm::mat4 offsetMat = offset.getMatrix();
|
||||||
|
|
||||||
|
for (std::shared_ptr<const model::Mesh> mesh : meshes) {
|
||||||
|
if (!mesh) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
MeshProxy* meshProxy = new SimpleMeshProxy(
|
||||||
|
mesh->map(
|
||||||
|
[=](glm::vec3 position) {
|
||||||
|
return glm::vec3(offsetMat * glm::vec4(position, 1.0f));
|
||||||
|
},
|
||||||
|
[=](glm::vec3 color) { return color; },
|
||||||
|
[=](glm::vec3 normal) {
|
||||||
|
return glm::normalize(glm::vec3(offsetMat * glm::vec4(normal, 0.0f)));
|
||||||
|
},
|
||||||
|
[&](uint32_t index) { return index; }));
|
||||||
|
result << meshProxy;
|
||||||
|
}
|
||||||
|
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
void Model::calculateTriangleSets() {
|
void Model::calculateTriangleSets() {
|
||||||
PROFILE_RANGE(render, __FUNCTION__);
|
PROFILE_RANGE(render, __FUNCTION__);
|
||||||
|
|
||||||
|
|
|
@ -257,6 +257,8 @@ public:
|
||||||
int getResourceDownloadAttempts() { return _renderWatcher.getResourceDownloadAttempts(); }
|
int getResourceDownloadAttempts() { return _renderWatcher.getResourceDownloadAttempts(); }
|
||||||
int getResourceDownloadAttemptsRemaining() { return _renderWatcher.getResourceDownloadAttemptsRemaining(); }
|
int getResourceDownloadAttemptsRemaining() { return _renderWatcher.getResourceDownloadAttemptsRemaining(); }
|
||||||
|
|
||||||
|
Q_INVOKABLE MeshProxyList getMeshes() const;
|
||||||
|
|
||||||
public slots:
|
public slots:
|
||||||
void loadURLFinished(bool success);
|
void loadURLFinished(bool success);
|
||||||
|
|
||||||
|
|
|
@ -38,16 +38,22 @@ QString ModelScriptingInterface::meshToOBJ(MeshProxyList in) {
|
||||||
QScriptValue ModelScriptingInterface::appendMeshes(MeshProxyList in) {
|
QScriptValue ModelScriptingInterface::appendMeshes(MeshProxyList in) {
|
||||||
// figure out the size of the resulting mesh
|
// figure out the size of the resulting mesh
|
||||||
size_t totalVertexCount { 0 };
|
size_t totalVertexCount { 0 };
|
||||||
size_t totalAttributeCount { 0 };
|
size_t totalColorCount { 0 };
|
||||||
|
size_t totalNormalCount { 0 };
|
||||||
size_t totalIndexCount { 0 };
|
size_t totalIndexCount { 0 };
|
||||||
foreach (const MeshProxy* meshProxy, in) {
|
foreach (const MeshProxy* meshProxy, in) {
|
||||||
MeshPointer mesh = meshProxy->getMeshPointer();
|
MeshPointer mesh = meshProxy->getMeshPointer();
|
||||||
totalVertexCount += mesh->getNumVertices();
|
totalVertexCount += mesh->getNumVertices();
|
||||||
|
|
||||||
|
int attributeTypeColor = gpu::Stream::InputSlot::COLOR; // libraries/gpu/src/gpu/Stream.h
|
||||||
|
const gpu::BufferView& colorsBufferView = mesh->getAttributeBuffer(attributeTypeColor);
|
||||||
|
gpu::BufferView::Index numColors = (gpu::BufferView::Index)colorsBufferView.getNumElements();
|
||||||
|
totalColorCount += numColors;
|
||||||
|
|
||||||
int attributeTypeNormal = gpu::Stream::InputSlot::NORMAL; // libraries/gpu/src/gpu/Stream.h
|
int attributeTypeNormal = gpu::Stream::InputSlot::NORMAL; // libraries/gpu/src/gpu/Stream.h
|
||||||
const gpu::BufferView& normalsBufferView = mesh->getAttributeBuffer(attributeTypeNormal);
|
const gpu::BufferView& normalsBufferView = mesh->getAttributeBuffer(attributeTypeNormal);
|
||||||
gpu::BufferView::Index numNormals = (gpu::BufferView::Index)normalsBufferView.getNumElements();
|
gpu::BufferView::Index numNormals = (gpu::BufferView::Index)normalsBufferView.getNumElements();
|
||||||
totalAttributeCount += numNormals;
|
totalNormalCount += numNormals;
|
||||||
|
|
||||||
totalIndexCount += mesh->getNumIndices();
|
totalIndexCount += mesh->getNumIndices();
|
||||||
}
|
}
|
||||||
|
@ -57,7 +63,11 @@ QScriptValue ModelScriptingInterface::appendMeshes(MeshProxyList in) {
|
||||||
unsigned char* combinedVertexData = new unsigned char[combinedVertexSize];
|
unsigned char* combinedVertexData = new unsigned char[combinedVertexSize];
|
||||||
unsigned char* combinedVertexDataCursor = combinedVertexData;
|
unsigned char* combinedVertexDataCursor = combinedVertexData;
|
||||||
|
|
||||||
gpu::Resource::Size combinedNormalSize = totalAttributeCount * sizeof(glm::vec3);
|
gpu::Resource::Size combinedColorSize = totalColorCount * sizeof(glm::vec3);
|
||||||
|
unsigned char* combinedColorData = new unsigned char[combinedColorSize];
|
||||||
|
unsigned char* combinedColorDataCursor = combinedColorData;
|
||||||
|
|
||||||
|
gpu::Resource::Size combinedNormalSize = totalNormalCount * sizeof(glm::vec3);
|
||||||
unsigned char* combinedNormalData = new unsigned char[combinedNormalSize];
|
unsigned char* combinedNormalData = new unsigned char[combinedNormalSize];
|
||||||
unsigned char* combinedNormalDataCursor = combinedNormalData;
|
unsigned char* combinedNormalDataCursor = combinedNormalData;
|
||||||
|
|
||||||
|
@ -74,6 +84,10 @@ QScriptValue ModelScriptingInterface::appendMeshes(MeshProxyList in) {
|
||||||
memcpy(combinedVertexDataCursor, &position, sizeof(position));
|
memcpy(combinedVertexDataCursor, &position, sizeof(position));
|
||||||
combinedVertexDataCursor += sizeof(position);
|
combinedVertexDataCursor += sizeof(position);
|
||||||
},
|
},
|
||||||
|
[&](glm::vec3 color){
|
||||||
|
memcpy(combinedColorDataCursor, &color, sizeof(color));
|
||||||
|
combinedColorDataCursor += sizeof(color);
|
||||||
|
},
|
||||||
[&](glm::vec3 normal){
|
[&](glm::vec3 normal){
|
||||||
memcpy(combinedNormalDataCursor, &normal, sizeof(normal));
|
memcpy(combinedNormalDataCursor, &normal, sizeof(normal));
|
||||||
combinedNormalDataCursor += sizeof(normal);
|
combinedNormalDataCursor += sizeof(normal);
|
||||||
|
@ -96,6 +110,13 @@ QScriptValue ModelScriptingInterface::appendMeshes(MeshProxyList in) {
|
||||||
gpu::BufferView combinedVertexBufferView(combinedVertexBufferPointer, vertexElement);
|
gpu::BufferView combinedVertexBufferView(combinedVertexBufferPointer, vertexElement);
|
||||||
result->setVertexBuffer(combinedVertexBufferView);
|
result->setVertexBuffer(combinedVertexBufferView);
|
||||||
|
|
||||||
|
int attributeTypeColor = gpu::Stream::InputSlot::COLOR; // libraries/gpu/src/gpu/Stream.h
|
||||||
|
gpu::Element colorElement = gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ);
|
||||||
|
gpu::Buffer* combinedColorsBuffer = new gpu::Buffer(combinedColorSize, combinedColorData);
|
||||||
|
gpu::BufferPointer combinedColorsBufferPointer(combinedColorsBuffer);
|
||||||
|
gpu::BufferView combinedColorsBufferView(combinedColorsBufferPointer, colorElement);
|
||||||
|
result->addAttribute(attributeTypeColor, combinedColorsBufferView);
|
||||||
|
|
||||||
int attributeTypeNormal = gpu::Stream::InputSlot::NORMAL; // libraries/gpu/src/gpu/Stream.h
|
int attributeTypeNormal = gpu::Stream::InputSlot::NORMAL; // libraries/gpu/src/gpu/Stream.h
|
||||||
gpu::Element normalElement = gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ);
|
gpu::Element normalElement = gpu::Element(gpu::VEC3, gpu::FLOAT, gpu::XYZ);
|
||||||
gpu::Buffer* combinedNormalsBuffer = new gpu::Buffer(combinedNormalSize, combinedNormalData);
|
gpu::Buffer* combinedNormalsBuffer = new gpu::Buffer(combinedNormalSize, combinedNormalData);
|
||||||
|
@ -132,12 +153,48 @@ QScriptValue ModelScriptingInterface::transformMesh(glm::mat4 transform, MeshPro
|
||||||
}
|
}
|
||||||
|
|
||||||
model::MeshPointer result = mesh->map([&](glm::vec3 position){ return glm::vec3(transform * glm::vec4(position, 1.0f)); },
|
model::MeshPointer result = mesh->map([&](glm::vec3 position){ return glm::vec3(transform * glm::vec4(position, 1.0f)); },
|
||||||
|
[&](glm::vec3 color){ return color; },
|
||||||
[&](glm::vec3 normal){ return glm::vec3(transform * glm::vec4(normal, 0.0f)); },
|
[&](glm::vec3 normal){ return glm::vec3(transform * glm::vec4(normal, 0.0f)); },
|
||||||
[&](uint32_t index){ return index; });
|
[&](uint32_t index){ return index; });
|
||||||
MeshProxy* resultProxy = new SimpleMeshProxy(result);
|
MeshProxy* resultProxy = new SimpleMeshProxy(result);
|
||||||
return meshToScriptValue(_modelScriptEngine, resultProxy);
|
return meshToScriptValue(_modelScriptEngine, resultProxy);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QScriptValue ModelScriptingInterface::getVertexCount(MeshProxy* meshProxy) {
|
||||||
|
if (!meshProxy) {
|
||||||
|
return QScriptValue(false);
|
||||||
|
}
|
||||||
|
MeshPointer mesh = meshProxy->getMeshPointer();
|
||||||
|
if (!mesh) {
|
||||||
|
return QScriptValue(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
gpu::BufferView::Index numVertices = (gpu::BufferView::Index)mesh->getNumVertices();
|
||||||
|
|
||||||
|
return numVertices;
|
||||||
|
}
|
||||||
|
|
||||||
|
QScriptValue ModelScriptingInterface::getVertex(MeshProxy* meshProxy, int vertexIndex) {
|
||||||
|
if (!meshProxy) {
|
||||||
|
return QScriptValue(false);
|
||||||
|
}
|
||||||
|
MeshPointer mesh = meshProxy->getMeshPointer();
|
||||||
|
if (!mesh) {
|
||||||
|
return QScriptValue(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
const gpu::BufferView& vertexBufferView = mesh->getVertexBuffer();
|
||||||
|
gpu::BufferView::Index numVertices = (gpu::BufferView::Index)mesh->getNumVertices();
|
||||||
|
|
||||||
|
if (vertexIndex < 0 || vertexIndex >= numVertices) {
|
||||||
|
return QScriptValue(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
glm::vec3 pos = vertexBufferView.get<glm::vec3>(vertexIndex);
|
||||||
|
return vec3toScriptValue(_modelScriptEngine, pos);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
QScriptValue ModelScriptingInterface::newMesh(const QVector<glm::vec3>& vertices,
|
QScriptValue ModelScriptingInterface::newMesh(const QVector<glm::vec3>& vertices,
|
||||||
const QVector<glm::vec3>& normals,
|
const QVector<glm::vec3>& normals,
|
||||||
const QVector<MeshFace>& faces) {
|
const QVector<MeshFace>& faces) {
|
||||||
|
|
|
@ -29,6 +29,8 @@ public:
|
||||||
Q_INVOKABLE QScriptValue newMesh(const QVector<glm::vec3>& vertices,
|
Q_INVOKABLE QScriptValue newMesh(const QVector<glm::vec3>& vertices,
|
||||||
const QVector<glm::vec3>& normals,
|
const QVector<glm::vec3>& normals,
|
||||||
const QVector<MeshFace>& faces);
|
const QVector<MeshFace>& faces);
|
||||||
|
Q_INVOKABLE QScriptValue getVertexCount(MeshProxy* meshProxy);
|
||||||
|
Q_INVOKABLE QScriptValue getVertex(MeshProxy* meshProxy, int vertexIndex);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
QScriptEngine* _modelScriptEngine { nullptr };
|
QScriptEngine* _modelScriptEngine { nullptr };
|
||||||
|
|
|
@ -23,6 +23,7 @@
|
||||||
#include <DependencyManager.h>
|
#include <DependencyManager.h>
|
||||||
#include <SettingHandle.h>
|
#include <SettingHandle.h>
|
||||||
#include <AssetUpload.h>
|
#include <AssetUpload.h>
|
||||||
|
#include <StatTracker.h>
|
||||||
|
|
||||||
#include "ATPClientApp.h"
|
#include "ATPClientApp.h"
|
||||||
|
|
||||||
|
@ -137,6 +138,7 @@ ATPClientApp::ATPClientApp(int argc, char* argv[]) :
|
||||||
Setting::init();
|
Setting::init();
|
||||||
DependencyManager::registerInheritance<LimitedNodeList, NodeList>();
|
DependencyManager::registerInheritance<LimitedNodeList, NodeList>();
|
||||||
|
|
||||||
|
DependencyManager::set<StatTracker>();
|
||||||
DependencyManager::set<AccountManager>([&]{ return QString(HIGH_FIDELITY_ATP_CLIENT_USER_AGENT); });
|
DependencyManager::set<AccountManager>([&]{ return QString(HIGH_FIDELITY_ATP_CLIENT_USER_AGENT); });
|
||||||
DependencyManager::set<AddressManager>();
|
DependencyManager::set<AddressManager>();
|
||||||
DependencyManager::set<NodeList>(NodeType::Agent, _listenPort);
|
DependencyManager::set<NodeList>(NodeType::Agent, _listenPort);
|
||||||
|
|
Loading…
Reference in a new issue