mirror of
https://github.com/Armored-Dragon/overte.git
synced 2025-03-11 16:13:16 +01:00
cleanup Model::renderPart()
This commit is contained in:
parent
1b8572640b
commit
4b46fc3ad9
3 changed files with 123 additions and 262 deletions
|
@ -3180,12 +3180,12 @@ namespace render {
|
||||||
if (args->_renderMode != CAMERA_MODE_MIRROR && Menu::getInstance()->isOptionChecked(MenuOption::Stats)) {
|
if (args->_renderMode != CAMERA_MODE_MIRROR && Menu::getInstance()->isOptionChecked(MenuOption::Stats)) {
|
||||||
PerformanceTimer perfTimer("worldBox");
|
PerformanceTimer perfTimer("worldBox");
|
||||||
renderWorldBox();
|
renderWorldBox();
|
||||||
|
|
||||||
|
// FIXME: there's currently a bug in the new render engine, if this origin dot is rendered out of view it will
|
||||||
|
// screw up the state of textures on models so they all end up rendering in the incorrect tint/color/texture
|
||||||
|
float originSphereRadius = 0.05f;
|
||||||
|
DependencyManager::get<GeometryCache>()->renderSphere(originSphereRadius, 15, 15, glm::vec4(1.0f, 0.0f, 0.0f, 1.0f));
|
||||||
}
|
}
|
||||||
|
|
||||||
// never the less
|
|
||||||
float originSphereRadius = 0.05f;
|
|
||||||
DependencyManager::get<GeometryCache>()->renderSphere(originSphereRadius, 15, 15, glm::vec4(1.0f, 0.0f, 0.0f, 1.0f));
|
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -115,12 +115,9 @@ bool RenderableModelEntityItem::readyToAddToScene(RenderArgs* renderArgs) {
|
||||||
// TODO: this getModel() appears to be about 3% of model render time. We should optimize
|
// TODO: this getModel() appears to be about 3% of model render time. We should optimize
|
||||||
PerformanceTimer perfTimer("getModel");
|
PerformanceTimer perfTimer("getModel");
|
||||||
EntityTreeRenderer* renderer = static_cast<EntityTreeRenderer*>(renderArgs->_renderer);
|
EntityTreeRenderer* renderer = static_cast<EntityTreeRenderer*>(renderArgs->_renderer);
|
||||||
qDebug() << "RenderableModelEntityItem::readyToAddToScene().... renderer:" << renderer;
|
|
||||||
getModel(renderer);
|
getModel(renderer);
|
||||||
}
|
}
|
||||||
if (renderArgs && _model && _needsInitialSimulation && _model->isActive() && _model->isLoadedWithTextures()) {
|
if (renderArgs && _model && _needsInitialSimulation && _model->isActive() && _model->isLoadedWithTextures()) {
|
||||||
qDebug() << "RenderableModelEntityItem::readyToAddToScene().... doing initial simulation";
|
|
||||||
|
|
||||||
_model->setScaleToFit(true, getDimensions());
|
_model->setScaleToFit(true, getDimensions());
|
||||||
_model->setSnapModelToRegistrationPoint(true, getRegistrationPoint());
|
_model->setSnapModelToRegistrationPoint(true, getRegistrationPoint());
|
||||||
_model->setRotation(getRotation());
|
_model->setRotation(getRotation());
|
||||||
|
@ -136,18 +133,11 @@ bool RenderableModelEntityItem::readyToAddToScene(RenderArgs* renderArgs) {
|
||||||
_model->renderSetup(renderArgs);
|
_model->renderSetup(renderArgs);
|
||||||
}
|
}
|
||||||
bool ready = !_needsInitialSimulation && _model && _model->readyToAddToScene(renderArgs);
|
bool ready = !_needsInitialSimulation && _model && _model->readyToAddToScene(renderArgs);
|
||||||
|
|
||||||
/*
|
|
||||||
qDebug() << "RenderableModelEntityItem::readyToAddToScene().... id:" << getEntityItemID()
|
|
||||||
<< "ready:" << ready << "renderArgs:" << renderArgs
|
|
||||||
<< "areMeshGroupsKnown():" << (_model ? _model->areMeshGroupsKnown() : false);
|
|
||||||
*/
|
|
||||||
return ready;
|
return ready;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool RenderableModelEntityItem::addToScene(EntityItemPointer self, std::shared_ptr<render::Scene> scene,
|
bool RenderableModelEntityItem::addToScene(EntityItemPointer self, std::shared_ptr<render::Scene> scene,
|
||||||
render::PendingChanges& pendingChanges) {
|
render::PendingChanges& pendingChanges) {
|
||||||
qDebug() << "RenderableModelEntityItem::addToScene().... id:" << getEntityItemID();
|
|
||||||
if (_model) {
|
if (_model) {
|
||||||
return _model->addToScene(scene, pendingChanges);
|
return _model->addToScene(scene, pendingChanges);
|
||||||
}
|
}
|
||||||
|
@ -156,14 +146,12 @@ bool RenderableModelEntityItem::addToScene(EntityItemPointer self, std::shared_p
|
||||||
|
|
||||||
void RenderableModelEntityItem::removeFromScene(EntityItemPointer self, std::shared_ptr<render::Scene> scene,
|
void RenderableModelEntityItem::removeFromScene(EntityItemPointer self, std::shared_ptr<render::Scene> scene,
|
||||||
render::PendingChanges& pendingChanges) {
|
render::PendingChanges& pendingChanges) {
|
||||||
qDebug() << "RenderableModelEntityItem::removeFromScene().... id:" << getEntityItemID();
|
|
||||||
if (_model) {
|
if (_model) {
|
||||||
_model->removeFromScene(scene, pendingChanges);
|
_model->removeFromScene(scene, pendingChanges);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void RenderableModelEntityItem::render(RenderArgs* args) {
|
void RenderableModelEntityItem::render(RenderArgs* args) {
|
||||||
qDebug() << "RenderableModelEntityItem::render().... id:" << getEntityItemID();
|
|
||||||
PerformanceTimer perfTimer("RMEIrender");
|
PerformanceTimer perfTimer("RMEIrender");
|
||||||
assert(getType() == EntityTypes::Model);
|
assert(getType() == EntityTypes::Model);
|
||||||
|
|
||||||
|
|
|
@ -783,7 +783,6 @@ namespace render {
|
||||||
}
|
}
|
||||||
|
|
||||||
template <> const Item::Bound payloadGetBound(const TransparentMeshPart::Pointer& payload) {
|
template <> const Item::Bound payloadGetBound(const TransparentMeshPart::Pointer& payload) {
|
||||||
//qDebug() << "payloadGetBound(TransparentMeshPart) url:" << payload->model->getURL();
|
|
||||||
if (payload) {
|
if (payload) {
|
||||||
//return payload->model->getPartBounds(payload->meshIndex, payload->partIndex);
|
//return payload->model->getPartBounds(payload->meshIndex, payload->partIndex);
|
||||||
}
|
}
|
||||||
|
@ -791,7 +790,6 @@ namespace render {
|
||||||
}
|
}
|
||||||
template <> void payloadRender(const TransparentMeshPart::Pointer& payload, RenderArgs* args) {
|
template <> void payloadRender(const TransparentMeshPart::Pointer& payload, RenderArgs* args) {
|
||||||
if (args) {
|
if (args) {
|
||||||
// qDebug() << "payloadRender(TransparentMeshPart) url:" << payload->model->getURL();
|
|
||||||
args->_elementsTouched++;
|
args->_elementsTouched++;
|
||||||
return payload->model->renderPart(args, payload->meshIndex, payload->partIndex, true);
|
return payload->model->renderPart(args, payload->meshIndex, payload->partIndex, true);
|
||||||
}
|
}
|
||||||
|
@ -815,7 +813,6 @@ namespace render {
|
||||||
}
|
}
|
||||||
|
|
||||||
template <> const Item::Bound payloadGetBound(const OpaqueMeshPart::Pointer& payload) {
|
template <> const Item::Bound payloadGetBound(const OpaqueMeshPart::Pointer& payload) {
|
||||||
// qDebug() << "payloadGetBound(OpaqueMeshPart) url:" << payload->model->getURL();
|
|
||||||
if (payload) {
|
if (payload) {
|
||||||
//return payload->model->getPartBounds(payload->meshIndex, payload->partIndex);
|
//return payload->model->getPartBounds(payload->meshIndex, payload->partIndex);
|
||||||
}
|
}
|
||||||
|
@ -823,7 +820,6 @@ namespace render {
|
||||||
}
|
}
|
||||||
template <> void payloadRender(const OpaqueMeshPart::Pointer& payload, RenderArgs* args) {
|
template <> void payloadRender(const OpaqueMeshPart::Pointer& payload, RenderArgs* args) {
|
||||||
if (args) {
|
if (args) {
|
||||||
// qDebug() << "payloadRender(OpaqueMeshPart) url:" << payload->model->getURL();
|
|
||||||
args->_elementsTouched++;
|
args->_elementsTouched++;
|
||||||
return payload->model->renderPart(args, payload->meshIndex, payload->partIndex, false);
|
return payload->model->renderPart(args, payload->meshIndex, payload->partIndex, false);
|
||||||
}
|
}
|
||||||
|
@ -832,7 +828,6 @@ namespace render {
|
||||||
|
|
||||||
|
|
||||||
bool Model::addToScene(std::shared_ptr<render::Scene> scene, render::PendingChanges& pendingChanges) {
|
bool Model::addToScene(std::shared_ptr<render::Scene> scene, render::PendingChanges& pendingChanges) {
|
||||||
qDebug() << "Model::addToScene() url:" << getURL();
|
|
||||||
bool somethingAdded = false;
|
bool somethingAdded = false;
|
||||||
// allow the attachments to add to scene
|
// allow the attachments to add to scene
|
||||||
foreach (Model* attachment, _attachments) {
|
foreach (Model* attachment, _attachments) {
|
||||||
|
@ -846,7 +841,6 @@ bool Model::addToScene(std::shared_ptr<render::Scene> scene, render::PendingChan
|
||||||
auto renderPayload = render::PayloadPointer(new TransparentMeshPart::Payload(renderData));
|
auto renderPayload = render::PayloadPointer(new TransparentMeshPart::Payload(renderData));
|
||||||
pendingChanges.resetItem(item, renderPayload);
|
pendingChanges.resetItem(item, renderPayload);
|
||||||
_renderItems << item;
|
_renderItems << item;
|
||||||
qDebug() << "Model::addToScene() added transparent item:" << item << "url:" << getURL();
|
|
||||||
somethingAdded = true;
|
somethingAdded = true;
|
||||||
}
|
}
|
||||||
foreach (auto renderItem, _opaqueRenderItems) {
|
foreach (auto renderItem, _opaqueRenderItems) {
|
||||||
|
@ -855,7 +849,6 @@ bool Model::addToScene(std::shared_ptr<render::Scene> scene, render::PendingChan
|
||||||
auto renderPayload = render::PayloadPointer(new OpaqueMeshPart::Payload(renderData));
|
auto renderPayload = render::PayloadPointer(new OpaqueMeshPart::Payload(renderData));
|
||||||
pendingChanges.resetItem(item, renderPayload);
|
pendingChanges.resetItem(item, renderPayload);
|
||||||
_renderItems << item;
|
_renderItems << item;
|
||||||
qDebug() << "Model::addToScene() added opaque item:" << item << "url:" << getURL();
|
|
||||||
somethingAdded = true;
|
somethingAdded = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -863,7 +856,6 @@ bool Model::addToScene(std::shared_ptr<render::Scene> scene, render::PendingChan
|
||||||
}
|
}
|
||||||
|
|
||||||
void Model::removeFromScene(std::shared_ptr<render::Scene> scene, render::PendingChanges& pendingChanges) {
|
void Model::removeFromScene(std::shared_ptr<render::Scene> scene, render::PendingChanges& pendingChanges) {
|
||||||
qDebug() << "Model::removeFromScene() url:" << getURL();
|
|
||||||
// allow the attachments to remove to scene
|
// allow the attachments to remove to scene
|
||||||
foreach (Model* attachment, _attachments) {
|
foreach (Model* attachment, _attachments) {
|
||||||
attachment->removeFromScene(scene, pendingChanges);
|
attachment->removeFromScene(scene, pendingChanges);
|
||||||
|
@ -2188,37 +2180,20 @@ AABox Model::getPartBounds(int meshIndex, int partIndex) {
|
||||||
AABox partBox = mesh._mesh.evalPartBound(partIndex);
|
AABox partBox = mesh._mesh.evalPartBound(partIndex);
|
||||||
|
|
||||||
// FIX ME!
|
// FIX ME!
|
||||||
// TODO: needs to translate to world space, these values are in model space
|
// 1) needs to translate to world space, these values are in model space
|
||||||
|
// 2) mesh._mesh.parts doesn't always have the correct values in it... so we
|
||||||
|
// need to just use mesh.parts or find/fix whatever is causing mesh._mesh
|
||||||
|
// to not contain data
|
||||||
return partBox;
|
return partBox;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Model::renderPart(RenderArgs* args, int meshIndex, int partIndex, bool translucent) {
|
void Model::renderPart(RenderArgs* args, int meshIndex, int partIndex, bool translucent) {
|
||||||
//renderCore(args, 1.0f);
|
|
||||||
//return;
|
|
||||||
//qDebug() << "Model::renderPart()... meshIndex:" << meshIndex << "partIndex:" << partIndex << "url:" << _url;
|
|
||||||
renderSetup(args);
|
renderSetup(args);
|
||||||
auto textureCache = DependencyManager::get<TextureCache>();
|
auto textureCache = DependencyManager::get<TextureCache>();
|
||||||
|
|
||||||
|
|
||||||
int i = meshIndex;
|
|
||||||
int j = partIndex;
|
|
||||||
gpu::Batch& batch = *(args->_batch);
|
gpu::Batch& batch = *(args->_batch);
|
||||||
auto mode = args->_renderMode;
|
auto mode = args->_renderMode;
|
||||||
|
|
||||||
// Setup the projection matrix
|
|
||||||
/*
|
|
||||||
if (args && args->_viewFrustum) {
|
|
||||||
glm::mat4 proj;
|
|
||||||
// If for easier debug depending on the pass
|
|
||||||
if (mode == RenderArgs::SHADOW_RENDER_MODE) {
|
|
||||||
args->_viewFrustum->evalProjectionMatrix(proj);
|
|
||||||
} else {
|
|
||||||
args->_viewFrustum->evalProjectionMatrix(proj);
|
|
||||||
}
|
|
||||||
batch.setProjectionTransform(proj);
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
|
|
||||||
// Capture the view matrix once for the rendering of this model
|
// Capture the view matrix once for the rendering of this model
|
||||||
if (_transforms.empty()) {
|
if (_transforms.empty()) {
|
||||||
_transforms.push_back(Transform());
|
_transforms.push_back(Transform());
|
||||||
|
@ -2232,23 +2207,6 @@ void Model::renderPart(RenderArgs* args, int meshIndex, int partIndex, bool tran
|
||||||
batch.setViewTransform(_transforms[0]);
|
batch.setViewTransform(_transforms[0]);
|
||||||
|
|
||||||
|
|
||||||
// FIXME: Do I need this? it doesn't seem to do anything.
|
|
||||||
/* {
|
|
||||||
GLenum buffers[3];
|
|
||||||
int bufferCount = 0;
|
|
||||||
|
|
||||||
if (mode != RenderArgs::SHADOW_RENDER_MODE) {
|
|
||||||
buffers[bufferCount++] = GL_COLOR_ATTACHMENT0;
|
|
||||||
}
|
|
||||||
if (mode != RenderArgs::SHADOW_RENDER_MODE) {
|
|
||||||
buffers[bufferCount++] = GL_COLOR_ATTACHMENT1;
|
|
||||||
}
|
|
||||||
if (mode != RenderArgs::SHADOW_RENDER_MODE) {
|
|
||||||
buffers[bufferCount++] = GL_COLOR_ATTACHMENT2;
|
|
||||||
}
|
|
||||||
GLBATCH(glDrawBuffers)(bufferCount, buffers);
|
|
||||||
}*/
|
|
||||||
|
|
||||||
const float DEFAULT_ALPHA_THRESHOLD = 0.5f; //
|
const float DEFAULT_ALPHA_THRESHOLD = 0.5f; //
|
||||||
auto alphaThreshold = DEFAULT_ALPHA_THRESHOLD; // FIX ME
|
auto alphaThreshold = DEFAULT_ALPHA_THRESHOLD; // FIX ME
|
||||||
const FBXGeometry& geometry = _geometry->getFBXGeometry();
|
const FBXGeometry& geometry = _geometry->getFBXGeometry();
|
||||||
|
@ -2258,9 +2216,6 @@ void Model::renderPart(RenderArgs* args, int meshIndex, int partIndex, bool tran
|
||||||
const FBXMesh& mesh = geometry.meshes.at(meshIndex);
|
const FBXMesh& mesh = geometry.meshes.at(meshIndex);
|
||||||
const MeshState& state = _meshStates.at(meshIndex);
|
const MeshState& state = _meshStates.at(meshIndex);
|
||||||
|
|
||||||
int vertexCount = mesh.vertices.size(); // NOTE: This seems wrong, shouldn't it be the part's vertex count?
|
|
||||||
|
|
||||||
|
|
||||||
bool translucentMesh = networkMesh.getTranslucentPartCount(mesh) == networkMesh.parts.size();
|
bool translucentMesh = networkMesh.getTranslucentPartCount(mesh) == networkMesh.parts.size();
|
||||||
bool hasTangents = !mesh.tangents.isEmpty();
|
bool hasTangents = !mesh.tangents.isEmpty();
|
||||||
bool hasSpecular = mesh.hasSpecularTexture();
|
bool hasSpecular = mesh.hasSpecularTexture();
|
||||||
|
@ -2277,226 +2232,147 @@ void Model::renderPart(RenderArgs* args, int meshIndex, int partIndex, bool tran
|
||||||
args, locations);
|
args, locations);
|
||||||
|
|
||||||
|
|
||||||
QString lastMaterialID;
|
|
||||||
int meshPartsRendered = 0;
|
int meshPartsRendered = 0;
|
||||||
updateVisibleJointStates();
|
updateVisibleJointStates();
|
||||||
|
|
||||||
// i is the "index" from the original networkMeshes QVector...
|
// if our index is ever out of range for either meshes or networkMeshes, then skip it, and set our _meshGroupsKnown
|
||||||
{
|
// to false to rebuild out mesh groups.
|
||||||
|
|
||||||
// if our index is ever out of range for either meshes or networkMeshes, then skip it, and set our _meshGroupsKnown
|
if (meshIndex < 0 || meshIndex >= networkMeshes.size() || meshIndex > geometry.meshes.size()) {
|
||||||
// to false to rebuild out mesh groups.
|
_meshGroupsKnown = false; // regenerate these lists next time around.
|
||||||
|
return; // FIXME!
|
||||||
if (i < 0 || i >= networkMeshes.size() || i > geometry.meshes.size()) {
|
}
|
||||||
_meshGroupsKnown = false; // regenerate these lists next time around.
|
|
||||||
// qDebug() << "if (i < 0 || i >= networkMeshes.size() || i > geometry.meshes.size()) {.... BAIL!!!";
|
batch.setIndexBuffer(gpu::UINT32, (networkMesh._indexBuffer), 0);
|
||||||
return; // FIXME!
|
int vertexCount = mesh.vertices.size();
|
||||||
}
|
if (vertexCount == 0) {
|
||||||
|
// sanity check
|
||||||
// exit early if the translucency doesn't match what we're drawing
|
return; // FIXME!
|
||||||
const NetworkMesh& networkMesh = networkMeshes.at(i);
|
}
|
||||||
const FBXMesh& mesh = geometry.meshes.at(i);
|
|
||||||
|
if (state.clusterMatrices.size() > 1) {
|
||||||
|
GLBATCH(glUniformMatrix4fv)(locations->clusterMatrices, state.clusterMatrices.size(), false,
|
||||||
|
(const float*)state.clusterMatrices.constData());
|
||||||
|
batch.setModelTransform(Transform());
|
||||||
|
} else {
|
||||||
|
batch.setModelTransform(Transform(state.clusterMatrices[0]));
|
||||||
|
}
|
||||||
|
|
||||||
batch.setIndexBuffer(gpu::UINT32, (networkMesh._indexBuffer), 0);
|
if (mesh.blendshapes.isEmpty()) {
|
||||||
int vertexCount = mesh.vertices.size();
|
batch.setInputFormat(networkMesh._vertexFormat);
|
||||||
if (vertexCount == 0) {
|
batch.setInputStream(0, *networkMesh._vertexStream);
|
||||||
// sanity check
|
} else {
|
||||||
// qDebug() << "if (vertexCount == 0) {.... BAIL!!!";
|
batch.setInputFormat(networkMesh._vertexFormat);
|
||||||
return; // FIXME!
|
batch.setInputBuffer(0, _blendedVertexBuffers[meshIndex], 0, sizeof(glm::vec3));
|
||||||
}
|
batch.setInputBuffer(1, _blendedVertexBuffers[meshIndex], vertexCount * sizeof(glm::vec3), sizeof(glm::vec3));
|
||||||
|
batch.setInputStream(2, *networkMesh._vertexStream);
|
||||||
const MeshState& state = _meshStates.at(i);
|
}
|
||||||
if (state.clusterMatrices.size() > 1) {
|
|
||||||
GLBATCH(glUniformMatrix4fv)(locations->clusterMatrices, state.clusterMatrices.size(), false,
|
|
||||||
(const float*)state.clusterMatrices.constData());
|
|
||||||
batch.setModelTransform(Transform());
|
|
||||||
} else {
|
|
||||||
batch.setModelTransform(Transform(state.clusterMatrices[0]));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mesh.blendshapes.isEmpty()) {
|
if (mesh.colors.isEmpty()) {
|
||||||
batch.setInputFormat(networkMesh._vertexFormat);
|
GLBATCH(glColor4f)(1.0f, 1.0f, 1.0f, 1.0f);
|
||||||
batch.setInputStream(0, *networkMesh._vertexStream);
|
}
|
||||||
} else {
|
|
||||||
batch.setInputFormat(networkMesh._vertexFormat);
|
|
||||||
batch.setInputBuffer(0, _blendedVertexBuffers[i], 0, sizeof(glm::vec3));
|
|
||||||
batch.setInputBuffer(1, _blendedVertexBuffers[i], vertexCount * sizeof(glm::vec3), sizeof(glm::vec3));
|
|
||||||
batch.setInputStream(2, *networkMesh._vertexStream);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (mesh.colors.isEmpty()) {
|
qint64 offset = 0;
|
||||||
// qDebug() << " colors empty ... meshIndex:" << meshIndex << "partIndex:" << partIndex << "url:" << _url;
|
|
||||||
GLBATCH(glColor4f)(1.0f, 1.0f, 1.0f, 1.0f);
|
|
||||||
} else {
|
|
||||||
// qDebug() << " colors size:" << mesh.colors.size() << " ... meshIndex:" << meshIndex << "partIndex:" << partIndex << "url:" << _url;
|
|
||||||
}
|
|
||||||
|
|
||||||
qint64 offset = 0;
|
const NetworkMeshPart& networkPart = networkMesh.parts.at(partIndex);
|
||||||
{ // j
|
const FBXMeshPart& part = mesh.parts.at(partIndex);
|
||||||
const NetworkMeshPart& networkPart = networkMesh.parts.at(j);
|
model::MaterialPointer material = part._material;
|
||||||
const FBXMeshPart& part = mesh.parts.at(j);
|
|
||||||
model::MaterialPointer material = part._material;
|
if (material == nullptr) {
|
||||||
|
qCDebug(renderutils) << "WARNING: material == nullptr!!!";
|
||||||
if (material != nullptr) {
|
}
|
||||||
/*
|
|
||||||
if ((networkPart.isTranslucent() || part.opacity != 1.0f) != translucent) {
|
if (material != nullptr) {
|
||||||
offset += (part.quadIndices.size() + part.triangleIndices.size()) * sizeof(int);
|
|
||||||
return; // FIXME!
|
// apply material properties
|
||||||
|
if (mode != RenderArgs::SHADOW_RENDER_MODE) {
|
||||||
|
#ifdef WANT_DEBUG
|
||||||
|
qCDebug(renderutils) << "Material Changed ---------------------------------------------";
|
||||||
|
qCDebug(renderutils) << "part INDEX:" << partIndex;
|
||||||
|
qCDebug(renderutils) << "NEW part.materialID:" << part.materialID;
|
||||||
|
#endif //def WANT_DEBUG
|
||||||
|
|
||||||
|
if (locations->materialBufferUnit >= 0) {
|
||||||
|
batch.setUniformBuffer(locations->materialBufferUnit, material->getSchemaBuffer());
|
||||||
}
|
}
|
||||||
*/
|
|
||||||
|
|
||||||
// apply material properties
|
Texture* diffuseMap = networkPart.diffuseTexture.data();
|
||||||
if (mode == RenderArgs::SHADOW_RENDER_MODE) {
|
if (mesh.isEye && diffuseMap) {
|
||||||
/// GLBATCH(glBindTexture)(GL_TEXTURE_2D, 0);
|
diffuseMap = (_dilatedTextures[meshIndex][partIndex] =
|
||||||
|
static_cast<DilatableNetworkTexture*>(diffuseMap)->getDilatedTexture(_pupilDilation)).data();
|
||||||
} else {
|
}
|
||||||
if (true) { //lastMaterialID != part.materialID) {
|
static bool showDiffuse = true;
|
||||||
const bool wantDebug = false;
|
if (showDiffuse && diffuseMap) {
|
||||||
if (wantDebug) {
|
batch.setUniformTexture(0, diffuseMap->getGPUTexture());
|
||||||
qCDebug(renderutils) << "Material Changed ---------------------------------------------";
|
|
||||||
qCDebug(renderutils) << "part INDEX:" << j;
|
} else {
|
||||||
qCDebug(renderutils) << "NEW part.materialID:" << part.materialID;
|
batch.setUniformTexture(0, textureCache->getWhiteTexture());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (locations->materialBufferUnit >= 0) {
|
if (locations->texcoordMatrices >= 0) {
|
||||||
batch.setUniformBuffer(locations->materialBufferUnit, material->getSchemaBuffer());
|
glm::mat4 texcoordTransform[2];
|
||||||
}
|
if (!part.diffuseTexture.transform.isIdentity()) {
|
||||||
|
part.diffuseTexture.transform.getMatrix(texcoordTransform[0]);
|
||||||
Texture* diffuseMap = networkPart.diffuseTexture.data();
|
|
||||||
if (mesh.isEye && diffuseMap) {
|
|
||||||
diffuseMap = (_dilatedTextures[i][j] =
|
|
||||||
static_cast<DilatableNetworkTexture*>(diffuseMap)->getDilatedTexture(_pupilDilation)).data();
|
|
||||||
}
|
|
||||||
static bool showDiffuse = true;
|
|
||||||
if (showDiffuse && diffuseMap) {
|
|
||||||
// qCDebug(renderutils) << " batch.setUniformTexture(0, diffuseMap->getGPUTexture());";
|
|
||||||
batch.setUniformTexture(0, diffuseMap->getGPUTexture());
|
|
||||||
|
|
||||||
} else {
|
|
||||||
// qCDebug(renderutils) << " batch.setUniformTexture(0, textureCache->getWhiteTexture());";
|
|
||||||
batch.setUniformTexture(0, textureCache->getWhiteTexture());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (locations->texcoordMatrices >= 0) {
|
|
||||||
glm::mat4 texcoordTransform[2];
|
|
||||||
if (!part.diffuseTexture.transform.isIdentity()) {
|
|
||||||
// qCDebug(renderutils) << " part.diffuseTexture.transform.getMatrix(texcoordTransform[0]);";
|
|
||||||
part.diffuseTexture.transform.getMatrix(texcoordTransform[0]);
|
|
||||||
}
|
|
||||||
if (!part.emissiveTexture.transform.isIdentity()) {
|
|
||||||
// qCDebug(renderutils) << " part.emissiveTexture.transform.getMatrix(texcoordTransform[1]);";
|
|
||||||
part.emissiveTexture.transform.getMatrix(texcoordTransform[1]);
|
|
||||||
}
|
|
||||||
// qCDebug(renderutils) << " GLBATCH(glUniformMatrix4fv)(locations->texcoordMatrices, 2, false, (const float*) &texcoordTransform);";
|
|
||||||
GLBATCH(glUniformMatrix4fv)(locations->texcoordMatrices, 2, false, (const float*) &texcoordTransform);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!mesh.tangents.isEmpty()) {
|
|
||||||
Texture* normalMap = networkPart.normalTexture.data();
|
|
||||||
// qCDebug(renderutils) << " batch.setUniformTexture(1, !normalMap ? textureCache->getBlueTexture() : normalMap->getGPUTexture());";
|
|
||||||
batch.setUniformTexture(1, !normalMap ?
|
|
||||||
textureCache->getBlueTexture() : normalMap->getGPUTexture());
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
if (locations->specularTextureUnit >= 0) {
|
|
||||||
Texture* specularMap = networkPart.specularTexture.data();
|
|
||||||
// qCDebug(renderutils) << " batch.setUniformTexture(locations->specularTextureUnit, !specularMap ? textureCache->getWhiteTexture() : specularMap->getGPUTexture());";
|
|
||||||
batch.setUniformTexture(locations->specularTextureUnit, !specularMap ?
|
|
||||||
textureCache->getWhiteTexture() : specularMap->getGPUTexture());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (args) {
|
|
||||||
args->_materialSwitches++;
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
// HACK: For unkwon reason (yet!) this code that should be assigned only if the material changes need to be called for every
|
|
||||||
// drawcall with an emissive, so let's do it for now.
|
|
||||||
if (locations->emissiveTextureUnit >= 0) {
|
|
||||||
// assert(locations->emissiveParams >= 0); // we should have the emissiveParams defined in the shader
|
|
||||||
float emissiveOffset = part.emissiveParams.x;
|
|
||||||
float emissiveScale = part.emissiveParams.y;
|
|
||||||
GLBATCH(glUniform2f)(locations->emissiveParams, emissiveOffset, emissiveScale);
|
|
||||||
|
|
||||||
Texture* emissiveMap = networkPart.emissiveTexture.data();
|
|
||||||
// qCDebug(renderutils) << " batch.setUniformTexture(locations->emissiveTextureUnit, !emissiveMap ? textureCache->getWhiteTexture() : emissiveMap->getGPUTexture());";
|
|
||||||
batch.setUniformTexture(locations->emissiveTextureUnit, !emissiveMap ?
|
|
||||||
textureCache->getWhiteTexture() : emissiveMap->getGPUTexture());
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
if (!part.emissiveTexture.transform.isIdentity()) {
|
||||||
|
part.emissiveTexture.transform.getMatrix(texcoordTransform[1]);
|
||||||
lastMaterialID = part.materialID;
|
}
|
||||||
}
|
GLBATCH(glUniformMatrix4fv)(locations->texcoordMatrices, 2, false, (const float*) &texcoordTransform);
|
||||||
|
|
||||||
meshPartsRendered++;
|
|
||||||
|
|
||||||
if (part.quadIndices.size() > 0) {
|
|
||||||
// qDebug() << "batch.drawIndexed(gpu::QUADS) size:" << part.quadIndices.size();
|
|
||||||
batch.drawIndexed(gpu::QUADS, part.quadIndices.size(), offset);
|
|
||||||
offset += part.quadIndices.size() * sizeof(int);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (part.triangleIndices.size() > 0) {
|
if (!mesh.tangents.isEmpty()) {
|
||||||
// qDebug() << "batch.drawIndexed(gpu::TRIANGLES) size:" << part.triangleIndices.size();
|
Texture* normalMap = networkPart.normalTexture.data();
|
||||||
batch.drawIndexed(gpu::TRIANGLES, part.triangleIndices.size(), offset);
|
batch.setUniformTexture(1, !normalMap ?
|
||||||
offset += part.triangleIndices.size() * sizeof(int);
|
textureCache->getBlueTexture() : normalMap->getGPUTexture());
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
if (locations->specularTextureUnit >= 0) {
|
||||||
|
Texture* specularMap = networkPart.specularTexture.data();
|
||||||
|
batch.setUniformTexture(locations->specularTextureUnit, !specularMap ?
|
||||||
|
textureCache->getWhiteTexture() : specularMap->getGPUTexture());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (args) {
|
if (args) {
|
||||||
const int INDICES_PER_TRIANGLE = 3;
|
args->_materialSwitches++;
|
||||||
const int INDICES_PER_QUAD = 4;
|
}
|
||||||
args->_trianglesRendered += part.triangleIndices.size() / INDICES_PER_TRIANGLE;
|
|
||||||
args->_quadsRendered += part.quadIndices.size() / INDICES_PER_QUAD;
|
// HACK: For unknown reason (yet!) this code that should be assigned only if the material changes need to be called for every
|
||||||
|
// drawcall with an emissive, so let's do it for now.
|
||||||
|
if (locations->emissiveTextureUnit >= 0) {
|
||||||
|
// assert(locations->emissiveParams >= 0); // we should have the emissiveParams defined in the shader
|
||||||
|
float emissiveOffset = part.emissiveParams.x;
|
||||||
|
float emissiveScale = part.emissiveParams.y;
|
||||||
|
GLBATCH(glUniform2f)(locations->emissiveParams, emissiveOffset, emissiveScale);
|
||||||
|
|
||||||
|
Texture* emissiveMap = networkPart.emissiveTexture.data();
|
||||||
|
batch.setUniformTexture(locations->emissiveTextureUnit, !emissiveMap ?
|
||||||
|
textureCache->getWhiteTexture() : emissiveMap->getGPUTexture());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
meshPartsRendered++;
|
||||||
|
|
||||||
// NOTE: these don't seem to do anything
|
if (part.quadIndices.size() > 0) {
|
||||||
/*
|
batch.drawIndexed(gpu::QUADS, part.quadIndices.size(), offset);
|
||||||
GLBATCH(glDepthMask)(true);
|
offset += part.quadIndices.size() * sizeof(int);
|
||||||
GLBATCH(glDepthFunc)(GL_LESS);
|
|
||||||
GLBATCH(glDisable)(GL_CULL_FACE);
|
|
||||||
|
|
||||||
if (mode == RenderArgs::SHADOW_RENDER_MODE) {
|
|
||||||
GLBATCH(glCullFace)(GL_BACK);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
GLBATCH(glActiveTexture)(GL_TEXTURE0 + 1);
|
if (part.triangleIndices.size() > 0) {
|
||||||
GLBATCH(glBindTexture)(GL_TEXTURE_2D, 0);
|
batch.drawIndexed(gpu::TRIANGLES, part.triangleIndices.size(), offset);
|
||||||
GLBATCH(glActiveTexture)(GL_TEXTURE0 + 2);
|
offset += part.triangleIndices.size() * sizeof(int);
|
||||||
GLBATCH(glBindTexture)(GL_TEXTURE_2D, 0);
|
}
|
||||||
GLBATCH(glActiveTexture)(GL_TEXTURE0 + 3);
|
|
||||||
GLBATCH(glBindTexture)(GL_TEXTURE_2D, 0);
|
if (args) {
|
||||||
GLBATCH(glActiveTexture)(GL_TEXTURE0);
|
const int INDICES_PER_TRIANGLE = 3;
|
||||||
GLBATCH(glBindTexture)(GL_TEXTURE_2D, 0);
|
const int INDICES_PER_QUAD = 4;
|
||||||
|
args->_trianglesRendered += part.triangleIndices.size() / INDICES_PER_TRIANGLE;
|
||||||
// deactivate vertex arrays after drawing
|
args->_quadsRendered += part.quadIndices.size() / INDICES_PER_QUAD;
|
||||||
GLBATCH(glDisableClientState)(GL_NORMAL_ARRAY);
|
}
|
||||||
GLBATCH(glDisableClientState)(GL_VERTEX_ARRAY);
|
|
||||||
GLBATCH(glDisableClientState)(GL_TEXTURE_COORD_ARRAY);
|
|
||||||
GLBATCH(glDisableClientState)(GL_COLOR_ARRAY);
|
|
||||||
GLBATCH(glDisableVertexAttribArray)(gpu::Stream::TANGENT);
|
|
||||||
GLBATCH(glDisableVertexAttribArray)(gpu::Stream::SKIN_CLUSTER_INDEX);
|
|
||||||
GLBATCH(glDisableVertexAttribArray)(gpu::Stream::SKIN_CLUSTER_WEIGHT);
|
|
||||||
|
|
||||||
// bind with 0 to switch back to normal operation
|
|
||||||
GLBATCH(glBindBuffer)(GL_ARRAY_BUFFER, 0);
|
|
||||||
GLBATCH(glBindBuffer)(GL_ELEMENT_ARRAY_BUFFER, 0);
|
|
||||||
GLBATCH(glBindTexture)(GL_TEXTURE_2D, 0);
|
|
||||||
*/
|
|
||||||
|
|
||||||
// Back to no program
|
|
||||||
// GLBATCH(glUseProgram)(0); // NOTE: We need this or else the avatar will end up with the texture of the last entity
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Model::segregateMeshGroups() {
|
void Model::segregateMeshGroups() {
|
||||||
|
|
||||||
//qDebug() << "Model::segregateMeshGroups() ------------------------------------------------";
|
|
||||||
|
|
||||||
_renderBuckets.clear();
|
_renderBuckets.clear();
|
||||||
|
|
||||||
const FBXGeometry& geometry = _geometry->getFBXGeometry();
|
const FBXGeometry& geometry = _geometry->getFBXGeometry();
|
||||||
|
@ -2528,15 +2404,12 @@ void Model::segregateMeshGroups() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Debug...
|
// Debug...
|
||||||
qDebug() << "Mesh parts... for " << _url << " count:" << mesh.parts.size();
|
|
||||||
int totalParts = mesh.parts.size();
|
int totalParts = mesh.parts.size();
|
||||||
for (int partIndex = 0; partIndex < totalParts; partIndex++) {
|
for (int partIndex = 0; partIndex < totalParts; partIndex++) {
|
||||||
// this is a good place to create our renderPayloads
|
// this is a good place to create our renderPayloads
|
||||||
if (translucentMesh) {
|
if (translucentMesh) {
|
||||||
qDebug() << "Transparent Mesh parts[" << partIndex << "]";
|
|
||||||
_transparentRenderItems << std::shared_ptr<TransparentMeshPart>(new TransparentMeshPart(this, i, partIndex));
|
_transparentRenderItems << std::shared_ptr<TransparentMeshPart>(new TransparentMeshPart(this, i, partIndex));
|
||||||
} else {
|
} else {
|
||||||
qDebug() << "Opaque Mesh parts[" << partIndex << "]";
|
|
||||||
_opaqueRenderItems << std::shared_ptr<OpaqueMeshPart>(new OpaqueMeshPart(this, i, partIndex));
|
_opaqueRenderItems << std::shared_ptr<OpaqueMeshPart>(new OpaqueMeshPart(this, i, partIndex));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue