git-svn-id: svn://db.shs.com.ru/libs@668 a8b55f48-bf90-11e4-a774-851b48703e85
This commit is contained in:
@@ -51,6 +51,7 @@ ObjectBase::~ObjectBase() {
|
|||||||
if (scene_) {
|
if (scene_) {
|
||||||
scene_->__objectDeleted(this);
|
scene_->__objectDeleted(this);
|
||||||
scene_->setTreeChanged();
|
scene_->setTreeChanged();
|
||||||
|
scene_->setTreeStructChanged();
|
||||||
}
|
}
|
||||||
foreach (ObjectBase * c, children_) {
|
foreach (ObjectBase * c, children_) {
|
||||||
c->parent_ = nullptr;
|
c->parent_ = nullptr;
|
||||||
@@ -364,6 +365,8 @@ void ObjectBase::setColor(QColor c, bool with_children) {
|
|||||||
|
|
||||||
|
|
||||||
void ObjectBase::setMesh(Mesh * v) {
|
void ObjectBase::setMesh(Mesh * v) {
|
||||||
|
if (scene_)
|
||||||
|
v = scene_->attachMesh(v);
|
||||||
mesh_ = v;
|
mesh_ = v;
|
||||||
setSceneTreeChanged();
|
setSceneTreeChanged();
|
||||||
setObjectsChanged();
|
setObjectsChanged();
|
||||||
|
|||||||
@@ -171,6 +171,7 @@ void Scene::removeObject(ObjectBase & o, bool inChildren) {
|
|||||||
|
|
||||||
void Scene::clearObjects(bool deleteAll) {
|
void Scene::clearObjects(bool deleteAll) {
|
||||||
root_->clearChildren(deleteAll);
|
root_->clearChildren(deleteAll);
|
||||||
|
cleanUnused();
|
||||||
setTreeStructChanged();
|
setTreeStructChanged();
|
||||||
emitSelectionChanged();
|
emitSelectionChanged();
|
||||||
}
|
}
|
||||||
@@ -253,6 +254,20 @@ ObjectBase * Scene::selectedObject() const {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void Scene::cleanUnused() {
|
||||||
|
QSet<Mesh*> ums;
|
||||||
|
QMapIterator<int, QMap<Mesh*, ObjectBaseList>> it(geometries_used);
|
||||||
|
while (it.hasNext())
|
||||||
|
ums |= it.next().value().keys().toSet();
|
||||||
|
for (int i = 0; i < geometries.size(); ++i) {
|
||||||
|
if (ums.contains(geometries[i])) continue;
|
||||||
|
td_geometries << geometries[i];
|
||||||
|
geometries.removeAt(i);
|
||||||
|
--i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
const Box3D & Scene::boundingBox() const {
|
const Box3D & Scene::boundingBox() const {
|
||||||
root_->calculateBoundingBox();
|
root_->calculateBoundingBox();
|
||||||
return root_->boundingBox();
|
return root_->boundingBox();
|
||||||
@@ -319,25 +334,8 @@ void Scene::attachObject(ObjectBase * o) {
|
|||||||
if (!o) return;
|
if (!o) return;
|
||||||
o->setScene(this);
|
o->setScene(this);
|
||||||
if (o->mesh()) { // search suitable mesh in this scene
|
if (o->mesh()) { // search suitable mesh in this scene
|
||||||
uint ohash = o->mesh()->hash();
|
o->mesh_ = attachMesh(o->mesh());
|
||||||
bool need_new = true;
|
setObjectMeshChanged(o);
|
||||||
foreach (Mesh * m, geometries) {
|
|
||||||
if (m == o->mesh()) { // already exists by ptr
|
|
||||||
need_new = false;
|
|
||||||
setObjectMeshChanged(o);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (m->hash() == ohash) { // already exists by hash
|
|
||||||
need_new = false;
|
|
||||||
o->setMesh(m);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (need_new) { // need to clone mesh and add to scene
|
|
||||||
Mesh * nmesh = o->mesh()->clone();
|
|
||||||
o->setMesh(nmesh);
|
|
||||||
geometries << nmesh;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if (o->material()) { // search suitable material in this scene
|
if (o->material()) { // search suitable material in this scene
|
||||||
uint ohash = o->material()->hash();
|
uint ohash = o->material()->hash();
|
||||||
@@ -361,6 +359,25 @@ void Scene::attachObject(ObjectBase * o) {
|
|||||||
materials << nmat;
|
materials << nmat;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
setTreeStructChanged();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Mesh * Scene::attachMesh(Mesh * mesh) {
|
||||||
|
if (!mesh) return 0;
|
||||||
|
uint mhash = mesh->hash();
|
||||||
|
foreach (Mesh * m, geometries) {
|
||||||
|
if (m == mesh) { // already exists by ptr
|
||||||
|
return m;
|
||||||
|
}
|
||||||
|
if (m->hash() == mhash) { // already exists by hash
|
||||||
|
return m;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// need to clone mesh and add to scene
|
||||||
|
Mesh * nmesh = mesh->clone();
|
||||||
|
geometries << nmesh;
|
||||||
|
return nmesh;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -421,14 +438,15 @@ bool Scene::prepare() {
|
|||||||
if (tree_changed) {
|
if (tree_changed) {
|
||||||
tree_changed = false;
|
tree_changed = false;
|
||||||
lights_changed = true;
|
lights_changed = true;
|
||||||
if (tree_struct_changed) {
|
|
||||||
tree_struct_changed = false;
|
|
||||||
QMetaObject::invokeMethod(this, "treeChanged", Qt::QueuedConnection);
|
|
||||||
}
|
|
||||||
geometries_used[rpSolid ].clear();
|
geometries_used[rpSolid ].clear();
|
||||||
geometries_used[rpTransparent].clear();
|
geometries_used[rpTransparent].clear();
|
||||||
lights_used.clear();
|
lights_used.clear();
|
||||||
prepareTree(root_);
|
prepareTree(root_);
|
||||||
|
if (tree_struct_changed) {
|
||||||
|
tree_struct_changed = false;
|
||||||
|
cleanUnused();
|
||||||
|
QMetaObject::invokeMethod(this, "treeChanged", Qt::QueuedConnection);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
mat_changed = false;
|
mat_changed = false;
|
||||||
return true;
|
return true;
|
||||||
@@ -440,7 +458,7 @@ void Scene::destroy() {
|
|||||||
selected_top.clear();
|
selected_top.clear();
|
||||||
emitSelectionChanged();
|
emitSelectionChanged();
|
||||||
root_->clearChildren(true);
|
root_->clearChildren(true);
|
||||||
qDeleteAll(geometries);
|
td_geometries << geometries;
|
||||||
qDeleteAll(materials);
|
qDeleteAll(materials);
|
||||||
geometries.clear();
|
geometries.clear();
|
||||||
materials.clear();
|
materials.clear();
|
||||||
@@ -449,6 +467,15 @@ void Scene::destroy() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void Scene::destroyUnused(QOpenGLExtraFunctions * f) {
|
||||||
|
if (!td_geometries.isEmpty()) qDebug() << "destroyUnused" << td_geometries.size();
|
||||||
|
foreach (Mesh * i, td_geometries)
|
||||||
|
i->destroy(f);
|
||||||
|
qDeleteAll(td_geometries);
|
||||||
|
td_geometries.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
QDataStream & operator <<(QDataStream & s, const Scene * p) {
|
QDataStream & operator <<(QDataStream & s, const Scene * p) {
|
||||||
ChunkStream cs;
|
ChunkStream cs;
|
||||||
//qDebug() << "place" << p->name() << "...";
|
//qDebug() << "place" << p->name() << "...";
|
||||||
|
|||||||
@@ -77,6 +77,7 @@ public:
|
|||||||
void clearSelection();
|
void clearSelection();
|
||||||
ObjectBaseList selectedObjects(bool top_only = false) const;
|
ObjectBaseList selectedObjects(bool top_only = false) const;
|
||||||
ObjectBase * selectedObject() const;
|
ObjectBase * selectedObject() const;
|
||||||
|
void cleanUnused();
|
||||||
|
|
||||||
const Box3D & boundingBox() const;
|
const Box3D & boundingBox() const;
|
||||||
|
|
||||||
@@ -89,6 +90,7 @@ public:
|
|||||||
|
|
||||||
void dump();
|
void dump();
|
||||||
void destroy();
|
void destroy();
|
||||||
|
void destroyUnused(QOpenGLExtraFunctions * f);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
void prepareTree(ObjectBase * o);
|
void prepareTree(ObjectBase * o);
|
||||||
@@ -99,6 +101,7 @@ protected:
|
|||||||
QString uniqueName(QString n, const QSet<QString> & names);
|
QString uniqueName(QString n, const QSet<QString> & names);
|
||||||
|
|
||||||
void attachObject(ObjectBase * o);
|
void attachObject(ObjectBase * o);
|
||||||
|
Mesh * attachMesh(Mesh * mesh);
|
||||||
void setTreeChanged();
|
void setTreeChanged();
|
||||||
void setTreeStructChanged();
|
void setTreeStructChanged();
|
||||||
void setMaterialsChanged() {mat_changed = true;}
|
void setMaterialsChanged() {mat_changed = true;}
|
||||||
@@ -112,7 +115,7 @@ protected:
|
|||||||
bool need_reload_materials, tree_struct_changed;
|
bool need_reload_materials, tree_struct_changed;
|
||||||
QVector<bool> mat_map_changed;
|
QVector<bool> mat_map_changed;
|
||||||
|
|
||||||
QVector<Mesh*> geometries;
|
QVector<Mesh*> geometries, td_geometries;
|
||||||
QVector<Material*> materials;
|
QVector<Material*> materials;
|
||||||
|
|
||||||
QMap<int, QMap<Mesh*, ObjectBaseList>> geometries_used; // [pass][mesh] = ObjectBaseList
|
QMap<int, QMap<Mesh*, ObjectBaseList>> geometries_used; // [pass][mesh] = ObjectBaseList
|
||||||
|
|||||||
@@ -255,6 +255,7 @@ void Renderer::renderScene() {
|
|||||||
Camera * cam = view->camera();
|
Camera * cam = view->camera();
|
||||||
QOpenGLShaderProgram * prog = 0;
|
QOpenGLShaderProgram * prog = 0;
|
||||||
bool scene_changed = scene.prepare();
|
bool scene_changed = scene.prepare();
|
||||||
|
scene.destroyUnused(f);
|
||||||
|
|
||||||
/// reload materials on change
|
/// reload materials on change
|
||||||
if (scene_changed || scene.need_reload_materials) {
|
if (scene_changed || scene.need_reload_materials) {
|
||||||
@@ -332,7 +333,6 @@ void Renderer::renderScene() {
|
|||||||
if (bindShader(srTonemapPass, &prog)) {
|
if (bindShader(srTonemapPass, &prog)) {
|
||||||
prog->setUniformValue("gamma", gamma_);
|
prog->setUniformValue("gamma", gamma_);
|
||||||
prog->setUniformValue("frame_max", tone_proc.frameMax());
|
prog->setUniformValue("frame_max", tone_proc.frameMax());
|
||||||
//fbo_1x1.bindColorTexture(0, 1);
|
|
||||||
fbo_out.bindColorTexture(obrSum, 0);
|
fbo_out.bindColorTexture(obrSum, 0);
|
||||||
fbo_out.setWriteBuffer(obrTonemap);
|
fbo_out.setWriteBuffer(obrTonemap);
|
||||||
renderQuad(prog, quad);
|
renderQuad(prog, quad);
|
||||||
|
|||||||
Reference in New Issue
Block a user