git-svn-id: svn://db.shs.com.ru/libs@637 a8b55f48-bf90-11e4-a774-851b48703e85
This commit is contained in:
@@ -22,11 +22,13 @@ if (MINGW)
|
||||
find_package(MinGW REQUIRED)
|
||||
endif()
|
||||
find_package(OpenGL REQUIRED)
|
||||
include_directories(${QAD_INCLUDES} {CMAKE_CURRENT_SOURCE_DIR})
|
||||
include_directories(${QAD_INCLUDES} "${CMAKE_CURRENT_SOURCE_DIR}" "${CMAKE_CURRENT_SOURCE_DIR}/core")
|
||||
find_qt(Qt5 Core Gui OpenGL Xml)
|
||||
qt_sources(SRC)
|
||||
qt_sources(FSRC DIR "formats")
|
||||
list(APPEND SRC ${FSRC})
|
||||
qt_sources(FSRC DIR "core")
|
||||
list(APPEND SRC ${FSRC})
|
||||
qt_wrap(${SRC} HDRS out_HDR CPPS out_CPP QMS out_QM)
|
||||
qt_add_library(qglengine_core SHARED out_CPP)
|
||||
qt_target_link_libraries(qglengine_core qad_utils qad_widgets assimp ${OPENGL_LIBRARIES})
|
||||
|
||||
@@ -24,8 +24,8 @@
|
||||
Framebuffer::Framebuffer(QOpenGLExtraFunctions * f_, int colorAttachments_, bool withDepth, GLenum colorFormat_, GLenum _target): f(f_),
|
||||
pbo(GL_PIXEL_PACK_BUFFER, GL_STREAM_DRAW) {
|
||||
is_depth = withDepth;
|
||||
color_format = colorFormat_;
|
||||
target_ = _target;
|
||||
color_formats.fill(colorFormat_, colorAttachments_);
|
||||
colors.fill(0, colorAttachments_);
|
||||
fbo = drbo = 0;
|
||||
tex_d = 0;
|
||||
@@ -35,6 +35,20 @@ Framebuffer::Framebuffer(QOpenGLExtraFunctions * f_, int colorAttachments_, bool
|
||||
}
|
||||
|
||||
|
||||
Framebuffer::Framebuffer(QOpenGLExtraFunctions * f_, QVector<GLenum> colors_, bool withDepth, GLenum _target): f(f_),
|
||||
pbo(GL_PIXEL_PACK_BUFFER, GL_STREAM_DRAW) {
|
||||
is_depth = withDepth;
|
||||
target_ = _target;
|
||||
color_formats = colors_;
|
||||
colors.fill(0, colors_.size());
|
||||
fbo = drbo = 0;
|
||||
tex_d = 0;
|
||||
wid = hei = 0;
|
||||
pbo_queried = 0;
|
||||
is_changed = false;
|
||||
}
|
||||
|
||||
|
||||
Framebuffer::~Framebuffer() {
|
||||
deleteGLFramebuffer(fbo);
|
||||
deleteGLRenderbuffer(drbo);
|
||||
@@ -53,7 +67,7 @@ void Framebuffer::resize(int width, int height, bool force) {
|
||||
f->glBindFramebuffer(GL_FRAMEBUFFER, fbo);
|
||||
for (int i = 0; i < colors.size(); ++i) {
|
||||
deleteGLTexture(f, colors[i]);
|
||||
createGLTexture(f, colors[i], width, height, color_format, target_);
|
||||
createGLTexture(f, colors[i], width, height, color_formats[i], target_);
|
||||
f->glTexParameteri(target_, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
|
||||
f->glTexParameteri(target_, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
|
||||
f->glTexParameteri(target_, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
|
||||
@@ -26,11 +26,12 @@ class Framebuffer
|
||||
{
|
||||
public:
|
||||
Framebuffer(QOpenGLExtraFunctions * f_, int colorAttachments = 1, bool withDepth = true, GLenum colorFormat = GL_RGBA8, GLenum _target = GL_TEXTURE_2D);
|
||||
Framebuffer(QOpenGLExtraFunctions * f_, QVector<GLenum> colors_, bool withDepth = true, GLenum _target = GL_TEXTURE_2D);
|
||||
virtual ~Framebuffer();
|
||||
|
||||
GLuint id() const {return fbo;}
|
||||
GLuint colorTexture(int index = 0) const {return colors[index];}
|
||||
GLenum colorFormat() const {return color_format;}
|
||||
//GLenum colorFormat() const {return color_format;}
|
||||
GLuint depthTexture() const {return tex_d;}
|
||||
GLenum target() const {return target_;}
|
||||
int width() const {return wid;}
|
||||
@@ -55,7 +56,7 @@ public:
|
||||
void setWriteBuffer(int index);
|
||||
void setWriteBuffers(int * indeces, int count);
|
||||
void setWriteBuffers();
|
||||
void setColorFormat(GLenum format) {color_format = format; is_changed = true;}
|
||||
//void setColorFormat(GLenum format) {color_format = format; is_changed = true;}
|
||||
void enablePixelBuffer();
|
||||
|
||||
void copyDepthFrom(GLuint tex) {;}
|
||||
@@ -72,7 +73,8 @@ private:
|
||||
QOpenGLExtraFunctions * f;
|
||||
mutable Buffer pbo;
|
||||
QVector<GLuint> colors;
|
||||
GLenum color_format, target_;
|
||||
QVector<GLenum> color_formats;
|
||||
GLenum target_;
|
||||
GLuint fbo, drbo, tex_d;
|
||||
GLint prev_view[4], wid, hei;
|
||||
|
||||
@@ -153,7 +153,7 @@ void QGLEngineShaders::setUniformLight(QOpenGLShaderProgram * prog, Light * ligh
|
||||
if (!prog) return;
|
||||
if (!prog->isLinked()) return;
|
||||
QMatrix4x4 m = mat * light->worldTransform();
|
||||
QVector4D pos(0, 0, 0, 1.), dir(light->direction, 1);//, dir0(light->dir0), dir1(light->dir1);
|
||||
QVector4D pos(0, 0, 0, 1.), dir(light->direction(), 1);//, dir0(light->dir0), dir1(light->dir1);
|
||||
pos = m * pos;
|
||||
dir = ((m * dir) - pos).normalized();
|
||||
float ang_start = light->angle_start / 2.f, ang_end = light->angle_end / 2.f;
|
||||
@@ -165,6 +165,7 @@ inline QImage rotateQImage180(const QImage & im) {return im.mirrored(true, true)
|
||||
class QGLView;
|
||||
class MouseController;
|
||||
class ObjectBase;
|
||||
class AimedObject;
|
||||
class Light;
|
||||
class Camera;
|
||||
class Texture;
|
||||
@@ -86,7 +86,7 @@ Light * assimpLight(const aiLight * l) {
|
||||
Light * ret = new Light();
|
||||
ret->setName(l->mName.C_Str());
|
||||
ret->setPos(fromAiVector3D(l->mPosition));
|
||||
ret->direction = fromAiVector3D(l->mDirection);
|
||||
ret->setDirection(fromAiVector3D(l->mDirection));
|
||||
ret->decay_const = l->mAttenuationConstant ;
|
||||
ret->decay_linear = l->mAttenuationLinear ;
|
||||
ret->decay_quadratic = l->mAttenuationQuadratic;
|
||||
@@ -102,14 +102,15 @@ Light * assimpLight(const aiLight * l) {
|
||||
}
|
||||
|
||||
|
||||
ObjectBase * assimpObject(const aiNode * n, const QVector<Mesh * > & meshes, const QMap<QString, Light * > & light_by_name) {
|
||||
ObjectBase * assimpObject(const aiNode * n, const QVector<Mesh * > & meshes, const QMap<QString, Light * > & light_by_name, QVector<Light*> & out_lights) {
|
||||
if (!n) return 0;
|
||||
ObjectBase * ret = 0;
|
||||
QString name = n->mName.C_Str();
|
||||
Light * light = light_by_name.value(name, 0);
|
||||
if (light)
|
||||
if (light) {
|
||||
ret = light->clone();
|
||||
else
|
||||
out_lights << (Light*)ret;
|
||||
} else
|
||||
ret = new ObjectBase();
|
||||
ret->setName(name);
|
||||
ret->setTransform(fromAiMatrix4D(n->mTransformation));
|
||||
@@ -125,7 +126,7 @@ ObjectBase * assimpObject(const aiNode * n, const QVector<Mesh * > & meshes, con
|
||||
}
|
||||
}
|
||||
for (uint i = 0; i < n->mNumChildren; ++i) {
|
||||
ObjectBase * co = assimpObject(n->mChildren[i], meshes, light_by_name);
|
||||
ObjectBase * co = assimpObject(n->mChildren[i], meshes, light_by_name, out_lights);
|
||||
if (co) ret->addChild(co);
|
||||
}
|
||||
|
||||
@@ -138,9 +139,9 @@ Scene * loadScene(const QString & filepath) {
|
||||
qDebug() << "[Loader Assimp] Import" << filepath << "...";
|
||||
Assimp::Importer importer;
|
||||
const aiScene * ais = importer.ReadFile(filepath.toUtf8(), aiProcess_Triangulate |
|
||||
aiProcess_SortByPType |
|
||||
aiProcess_GenUVCoords |
|
||||
aiProcess_TransformUVCoords);
|
||||
aiProcess_SortByPType |
|
||||
aiProcess_GenUVCoords |
|
||||
aiProcess_TransformUVCoords);
|
||||
if (!ais) {
|
||||
qDebug() << "[Loader Assimp] Error: \"" + QString(importer.GetErrorString()) + "\"";
|
||||
return 0;
|
||||
@@ -156,15 +157,25 @@ Scene * loadScene(const QString & filepath) {
|
||||
foreach (Light * l, lights)
|
||||
light_by_name[l->name()] = l;
|
||||
|
||||
ObjectBase * root = assimpObject(ais->mRootNode, meshes, light_by_name);
|
||||
QVector<Light*> out_lights;
|
||||
ObjectBase * root = assimpObject(ais->mRootNode, meshes, light_by_name, out_lights);
|
||||
if (!root) return 0;
|
||||
|
||||
QList<ObjectBase*> rcl = root->children(true);
|
||||
foreach (ObjectBase * c, rcl) {
|
||||
foreach (Light * l, out_lights) {
|
||||
if (c->name() == (l->name() + ".Target")) {
|
||||
l->setAim((l->worldTransform().inverted() * QVector4D(c->worldPos(), 1)).toVector3D());
|
||||
delete c;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Scene * scene = new Scene();
|
||||
scene->setName(root->name());
|
||||
foreach (ObjectBase * o, root->children())
|
||||
scene->addObject(o);
|
||||
//foreach (ObjectBase * o, lights)
|
||||
// scene->addObject(o);
|
||||
qDeleteAll(lights);
|
||||
|
||||
return scene;
|
||||
|
||||
@@ -24,7 +24,7 @@
|
||||
//extern QMatrix4x4 globCameraMatrix;
|
||||
//extern Camera * currentCamera;
|
||||
|
||||
class Camera: public ObjectBase
|
||||
class Camera: public AimedObject
|
||||
{
|
||||
friend class QGLView;
|
||||
friend class GLParticlesSystem;
|
||||
@@ -34,7 +34,7 @@ public:
|
||||
Camera();
|
||||
|
||||
void setPos(const QVector3D & p) {pos_ = p; anglesFromPoints(); buildTransform();}
|
||||
void setAim(const QVector3D & p) {aim_ = p; anglesFromPoints(); buildTransform();}
|
||||
void setAim(const QVector3D & p) {AimedObject::setAim(p); anglesFromPoints(); buildTransform();}
|
||||
void move(const QVector3D & p) {pos_ += p; aim_ += p; buildTransform();}
|
||||
void move(const float & x, const float & y = 0., const float & z = 0.) {pos_ += QVector3D(x, y, z); aim_ += QVector3D(x, y, z); buildTransform();}
|
||||
void moveForward(const float & x, bool withZ = true);
|
||||
@@ -66,7 +66,6 @@ public:
|
||||
void flyFarer(const float & s);
|
||||
void flyToDistance(const float & d);
|
||||
|
||||
QVector3D aim() const {return aim_;}
|
||||
QVector3D angles() const {return rotation();}
|
||||
QVector3D direction() const {return (aim_ - pos_).normalized();}
|
||||
QVector3D directionXY() const {QVector3D tv = aim_ - pos_; return QVector3D(tv.x(), tv.y(), 0.).normalized();}
|
||||
@@ -94,7 +93,6 @@ public:
|
||||
QMatrix4x4 fullViewMatrix() const {return viewMatrix() * offsetMatrix();}
|
||||
|
||||
private:
|
||||
QVector3D aim_;
|
||||
mutable QVector3D offset_;
|
||||
GLfloat fov_;
|
||||
GLfloat depth_start;
|
||||
|
||||
@@ -465,18 +465,41 @@ QMatrix4x4 ObjectBase::worldMatrix(QMatrix4x4 parent) const {
|
||||
|
||||
|
||||
|
||||
Light::Light(): ObjectBase(), shadow_map(0, true, GL_R16F) {
|
||||
AimedObject::AimedObject() {
|
||||
|
||||
}
|
||||
|
||||
|
||||
void AimedObject::setAim(const QVector3D & p) {
|
||||
aim_ = p;
|
||||
}
|
||||
|
||||
|
||||
QVector3D AimedObject::direction() const {
|
||||
return (aim_ - pos_).normalized();
|
||||
}
|
||||
|
||||
|
||||
void AimedObject::setDirection(const QVector3D & d) {
|
||||
double len = qMax(direction().length(), 0.001f);
|
||||
aim_ = pos_ + (d.normalized() * len);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
Light::Light(): AimedObject(), shadow_map(0, true, GL_R16F) {
|
||||
type_ = glLight;
|
||||
light_type = Omni;
|
||||
intensity = 1.;
|
||||
angle_start = angle_end = 180.;
|
||||
decay_linear = decay_quadratic = decay_start = 0.;
|
||||
decay_const = decay_end = 1.;
|
||||
direction.setZ(1.);
|
||||
setDirection(0, 0, -1.);
|
||||
}
|
||||
|
||||
|
||||
Light::Light(const QVector3D & p, const QColor & c, float i): ObjectBase(), shadow_map(0, true, GL_R16F) {
|
||||
Light::Light(const QVector3D & p, const QColor & c, float i): AimedObject(), shadow_map(0, true, GL_R16F) {
|
||||
type_ = glLight;
|
||||
light_type = Omni;
|
||||
pos_ = p;
|
||||
@@ -485,7 +508,7 @@ Light::Light(const QVector3D & p, const QColor & c, float i): ObjectBase(), shad
|
||||
angle_start = angle_end = 180.;
|
||||
decay_linear = decay_quadratic = decay_start = 0.;
|
||||
decay_const = decay_end = 1.;
|
||||
direction.setZ(1.);
|
||||
setDirection(0, 0, -1.);
|
||||
}
|
||||
|
||||
|
||||
@@ -502,7 +525,8 @@ ObjectBase * Light::clone(bool withChildren) {
|
||||
}
|
||||
o->color_ = color_;
|
||||
o->light_type = light_type;
|
||||
o->direction = direction;
|
||||
o->pos_ = pos_;
|
||||
o->aim_ = aim_;
|
||||
o->angle_start = angle_start;
|
||||
o->angle_end = angle_end;
|
||||
o->intensity = intensity;
|
||||
@@ -531,9 +555,9 @@ QDataStream & operator <<(QDataStream & s, const ObjectBase * p) {
|
||||
if (p->type_ == ObjectBase::glLight) {
|
||||
//qDebug() << "place light ...";
|
||||
const Light * l = (const Light*)p;
|
||||
cs.add(100, l->direction).add(101, l->angle_start).add(102, l->angle_end).add(103, l->intensity)
|
||||
cs.add(100, l->direction()).add(101, l->angle_start).add(102, l->angle_end).add(103, l->intensity)
|
||||
.add(104, l->decay_const).add(105, l->decay_linear).add(106, l->decay_quadratic)
|
||||
.add(107, l->decay_start).add(108, l->decay_end).add(109, int(l->light_type));
|
||||
.add(107, l->decay_start).add(108, l->decay_end).add(109, int(l->light_type)).add(110, l->aim());
|
||||
}
|
||||
if (p->type_ == ObjectBase::glCamera) {
|
||||
//qDebug() << "place camera ...";
|
||||
@@ -592,7 +616,7 @@ QDataStream & operator >>(QDataStream & s, ObjectBase *& p) {
|
||||
case 17: if (p) p->name_ = cs.getData<QString>(); break;
|
||||
case 18: if (p) p->meta = cs.getData<QVariantMap>(); break;
|
||||
case 19: if (p) p->color_ = cs.getData<QColor>(); break;
|
||||
case 100: if (l) l->direction = cs.getData<QVector3D>(); break;
|
||||
case 100: if (l) l->setDirection(cs.getData<QVector3D>());break;
|
||||
case 101: if (l) l->angle_start = cs.getData<GLfloat>(); break;
|
||||
case 102: if (l) l->angle_end = cs.getData<GLfloat>(); break;
|
||||
case 103: if (l) l->intensity = cs.getData<GLfloat>(); break;
|
||||
@@ -602,6 +626,7 @@ QDataStream & operator >>(QDataStream & s, ObjectBase *& p) {
|
||||
case 107: if (l) l->decay_start = cs.getData<GLfloat>(); break;
|
||||
case 108: if (l) l->decay_end = cs.getData<GLfloat>(); break;
|
||||
case 109: if (l) l->light_type = (Light::Type)cs.getData<int>(); break;
|
||||
case 110: if (l) l->setAim(cs.getData<QVector3D>()); if (l->aim().isNull()) l->setAim(l->direction()); break;
|
||||
case 200: if (c) c->setAim(cs.getData<QVector3D>()); break;
|
||||
case 201: if (c) c->setFOV(cs.getData<GLfloat>()); break;
|
||||
case 202: if (c) c->setDepthStart(cs.getData<GLfloat>()); break;
|
||||
|
||||
@@ -229,13 +229,23 @@ inline bool operator <(const ObjectBase & f, const ObjectBase & s) {return f.pos
|
||||
class AimedObject: public ObjectBase {
|
||||
friend class QGLView;
|
||||
friend class GLRendererBase;
|
||||
friend class Light;
|
||||
friend class Camera;
|
||||
public:
|
||||
AimedObject();
|
||||
~AimedObject();
|
||||
~AimedObject() {}
|
||||
QVector3D aim() const {return aim_;}
|
||||
QVector3D worldAim() const {return (itransform_ * QVector4D(aim_, 1.)).toVector3D();}
|
||||
void setAim(const QVector3D & p);
|
||||
QVector3D direction() const;
|
||||
void setDirection(const QVector3D & d);
|
||||
void setDirection(double x, double y, double z) {setDirection(QVector3D(x, y, z));}
|
||||
protected:
|
||||
QVector3D aim_;
|
||||
};
|
||||
|
||||
|
||||
class Light: public ObjectBase {
|
||||
class Light: public AimedObject {
|
||||
friend class QGLView;
|
||||
friend class RendererBase;
|
||||
public:
|
||||
@@ -247,7 +257,6 @@ public:
|
||||
virtual void init() {shadow_map.resize(512, 512); is_init = true;}
|
||||
void apply();
|
||||
|
||||
QVector3D direction, dir0, dir1;
|
||||
float angle_start;
|
||||
float angle_end;
|
||||
float intensity;
|
||||
|
||||
@@ -36,9 +36,9 @@ void GLRendererBase::setupLight(const Light & l, int inpass_index, int gl_index)
|
||||
GLfloat pos[] = {0.f, 0.f, 0.f, 0.f};
|
||||
GLfloat dir[] = {0.f, 0.f, 0.f};
|
||||
GLfloat col[] = {0.f, 0.f, 0.f};
|
||||
pos[0] = l.light_type == Light::Directional ? -l.direction.x() : lp.x();
|
||||
pos[1] = l.light_type == Light::Directional ? -l.direction.y() : lp.y();
|
||||
pos[2] = l.light_type == Light::Directional ? -l.direction.z() : lp.z();
|
||||
pos[0] = l.light_type == Light::Directional ? -l.direction().x() : lp.x();
|
||||
pos[1] = l.light_type == Light::Directional ? -l.direction().y() : lp.y();
|
||||
pos[2] = l.light_type == Light::Directional ? -l.direction().z() : lp.z();
|
||||
pos[3] = l.light_type == Light::Directional ? 0. : 1.;
|
||||
dir[0] = ld.x();
|
||||
dir[1] = ld.y();
|
||||
@@ -209,7 +209,7 @@ void GLRendererBase::renderShadow(Light * l, QOpenGLShaderProgram * prog, QMatri
|
||||
Camera cam;
|
||||
QVector3D wp = l->worldPos();
|
||||
cam.setPos(wp);
|
||||
cam.setAim(wp + (l->worldTransform() * QVector4D(l->direction)).toVector3D());
|
||||
cam.setAim(wp + (l->worldTransform() * QVector4D(l->direction())).toVector3D());
|
||||
cam.setDepthStart(view->camera()->depthStart());
|
||||
cam.setDepthEnd(view->camera()->depthEnd());
|
||||
cam.setFOV(l->angle_end);
|
||||
|
||||
@@ -28,7 +28,7 @@ using namespace QGLEngineShaders;
|
||||
|
||||
|
||||
Renderer::Renderer(QGLView * view_): RendererBase(view_),
|
||||
fbo_ds (view_, 5, true , GL_RGBA16F),
|
||||
fbo_ds (view_, QVector<GLenum>() << GL_RGBA16F << GL_RGBA32F << GL_RGBA16F << GL_RGBA16F << GL_RGBA16F),
|
||||
fbo_out (view_, 3, false, GL_RGBA16F),
|
||||
fbo_hsmall (view_, 1, false, GL_RGB16F ),
|
||||
rend_mat(this), rend_service(this), rend_selection(this) {
|
||||
@@ -125,13 +125,22 @@ bool Renderer::bindShader(Renderer::ShaderRole role, QOpenGLShaderProgram ** ret
|
||||
void Renderer::initShaders() {
|
||||
if (!need_init_shaders) return;
|
||||
need_init_shaders = false;
|
||||
initUniformBuffer(shaders.value(srGeometryPass), &buffer_materials , bpMaterials , "QGLMaterialData" );
|
||||
initUniformBuffer(shaders.value(srGeometryPass ), &buffer_materials , bpMaterials , "QGLMaterialData" );
|
||||
initUniformBuffer(shaders.value(srLightOmniPass), &buffer_materials , bpMaterials , "QGLMaterialData" );
|
||||
initUniformBuffer(shaders.value(srLightOmniPass), &buffer_lights , bpLightParameters, "QGLLightParameterData");
|
||||
initUniformBuffer(shaders.value(srLightOmniPass), &buffer_lights_pos, bpLightPositions , "QGLLightPositionData" );
|
||||
initUniformBuffer(shaders.value(srLightSpotPass), &buffer_materials , bpMaterials , "QGLMaterialData" );
|
||||
initUniformBuffer(shaders.value(srLightSpotPass), &buffer_lights , bpLightParameters, "QGLLightParameterData");
|
||||
initUniformBuffer(shaders.value(srLightSpotPass), &buffer_lights_pos, bpLightPositions , "QGLLightPositionData" );
|
||||
ShaderRole roles[] = {srLightOmniPass, srLightSpotPass};
|
||||
for (int p = 0; p < 2; ++p) {
|
||||
QOpenGLShaderProgram * prog = 0;
|
||||
if (!bindShader(roles[p], &prog)) continue;
|
||||
for (int i = 0; i < 5; ++i)
|
||||
prog->setUniformValue(QString("tex_%1").arg(i).toLatin1().constData(), i);
|
||||
prog->setUniformValue("tex_d", 5);
|
||||
prog->setUniformValue("tex_sum", 7);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -236,7 +245,7 @@ void Renderer::renderScene() {
|
||||
}
|
||||
fbo_ds.release();
|
||||
|
||||
/// lighting pass
|
||||
/// lighting passes
|
||||
fbo_ds.bindColorTextures();
|
||||
fbo_ds.bindDepthTexture(5);
|
||||
fbo_out.bind();
|
||||
@@ -248,12 +257,8 @@ void Renderer::renderScene() {
|
||||
if (bindShader(pass.first, &prog)) {
|
||||
setUniformCamera(prog, cam);
|
||||
setUniformViewCorners(prog, cam);
|
||||
for (int i = 0; i < 5; ++i)
|
||||
prog->setUniformValue(QString("tex_%1").arg(i).toLatin1().constData(), i);
|
||||
prog->setUniformValue("tex_d", 5);
|
||||
prog->setUniformValue("lights_start", lights_start[pass.second]);
|
||||
prog->setUniformValue("lights_count", ll[pass.second].size());
|
||||
prog->setUniformValue("tex_sum", 7);
|
||||
fbo_out.setWriteBuffer(wi);
|
||||
fbo_out.bindColorTexture(ri, 7);
|
||||
glClearFramebuffer(Qt::black, false);
|
||||
|
||||
@@ -258,7 +258,7 @@ void RendererBase::reloadLightsPositions(Camera * cam) {
|
||||
QGLLightPosition & so(cur_lights_pos_[i]);
|
||||
Light * l = current_lights[i];
|
||||
QMatrix4x4 m = mat * l->worldTransform();
|
||||
QVector4D pos(0, 0, 0, 1.), dir(l->direction, 1);//, dir0(light->dir0), dir1(light->dir1);
|
||||
QVector4D pos(0, 0, 0, 1.), dir(l->direction(), 1);//, dir0(light->dir0), dir1(light->dir1);
|
||||
pos = m * pos;
|
||||
dir = ((m * dir) - pos).normalized();
|
||||
so.position = pos;
|
||||
|
||||
@@ -54,8 +54,8 @@ RendererService::RendererService(Renderer * r_): r(r_) {
|
||||
axis_camera->setFOV(45.);
|
||||
axis_mesh = Primitive::arrow(12);
|
||||
size_vp_scale = size_full_scale = 1.;
|
||||
box_mesh = Primitive::cube();
|
||||
box_mesh_f = Primitive::cubeFrame();
|
||||
box_mesh = Primitive::cube(0.8, 0.8, 0.8);
|
||||
box_mesh_f = Primitive::cubeFrame(0.8, 0.8, 0.8);
|
||||
omni_mesh = Primitive::ellipsoid(2, 1);
|
||||
omni_mesh_f = Primitive::ellipsoidFrame(2, 1);
|
||||
omni_mesh ->scalePoints(1.5);
|
||||
@@ -63,14 +63,18 @@ RendererService::RendererService(Renderer * r_): r(r_) {
|
||||
cone_mesh = Primitive::cone(8, 1., 1., 1.);
|
||||
cone_mesh_f = Primitive::coneFrame(8, 1., 1., 1.);
|
||||
QMatrix4x4 mat;
|
||||
mat.rotate(90, 0,1,0);
|
||||
mat.translate(0,0,2);
|
||||
mat.translate(0,0,1);
|
||||
mat.rotate(180, 1,0,0);
|
||||
cone_mesh ->transformPoints(mat);
|
||||
cone_mesh_f->transformPoints(mat);
|
||||
cone_mesh_f->scalePoints(1.5);
|
||||
|
||||
box_mesh ->scalePoints(1.3);
|
||||
omni_mesh ->scalePoints(1.3);
|
||||
cone_mesh ->translatePoints(0,0,-1);
|
||||
cone_mesh ->scalePoints(1.4);
|
||||
cone_mesh ->translatePoints(0,0,1);
|
||||
cone_mesh ->scalePoints(1.5);
|
||||
|
||||
handle_move_mesh = Primitive::arrow(12, 0.06);
|
||||
handle_ms_2_mesh = Primitive::torus(8, 12, 0.5, 0.02, 90);
|
||||
@@ -144,6 +148,26 @@ QMatrix4x4 RendererService::invariantSizeMatrix(QVector3D p) {
|
||||
}
|
||||
|
||||
|
||||
QMatrix4x4 RendererService::parentRotationMatrix(ObjectBase * o, bool self_rotation) {
|
||||
QMatrix4x4 ret;
|
||||
if (!o) return ret;
|
||||
QMatrix4x4 pmat;
|
||||
if (o->parent()) {
|
||||
pmat = o->parent()->worldTransform();
|
||||
pmat.setColumn(3, QVector4D(0,0,0,1));
|
||||
double det = pmat.determinant();
|
||||
if (det > 0.) pmat /= sqrt(det);
|
||||
}
|
||||
if (self_rotation) {
|
||||
ret.rotate(o->angles_.z(), 0., 0., 1.);
|
||||
ret.rotate(o->angles_.y(), 0., 1., 0.);
|
||||
ret.rotate(o->angles_.x(), 1., 0., 0.);
|
||||
}
|
||||
ret = pmat * ret;
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
void RendererService::fillXYZObjects() {
|
||||
cur_objects.resize(3);
|
||||
for (int i = 0; i < 3; ++i) {
|
||||
@@ -166,6 +190,32 @@ void RendererService::fillOmniObjects() {
|
||||
}
|
||||
|
||||
|
||||
void RendererService::fillSpotObjects() {
|
||||
QList<Light*> ll = r->view->scene()->lights_used.value(Light::Cone);
|
||||
Object o;
|
||||
cur_objects.clear();
|
||||
cur_aims.clear();
|
||||
foreach (Light * l, ll) {
|
||||
QMatrix4x4 m, lm;
|
||||
//QVector3D up = QVector3D::crossProduct(l->direction, QVector3D(0,0,1)).normalized();
|
||||
//if (up.isNull())
|
||||
// up = QVector3D::crossProduct(l->direction, QVector3D(0,0,1)).normalized();
|
||||
//lm.lookAt(QVector3D(), l->direction, up);
|
||||
//lm.lookAt(QVector3D(), l->direction, (QVector3D(0,0,1)));
|
||||
lm.rotate(QQuaternion::fromDirection(l->direction(), QVector3D()));
|
||||
m = invariantSizeMatrix(l->worldPos()) * parentRotationMatrix(l) * lm;
|
||||
m.transposed().copyDataTo(o.modelmatrix);
|
||||
o.object_id = l->id_;
|
||||
cur_objects << o;
|
||||
|
||||
m = invariantSizeMatrix(l->worldAim());
|
||||
m.transposed().copyDataTo(o.modelmatrix);
|
||||
o.object_id = l->id_ + 1;
|
||||
cur_aims << o;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void RendererService::fillHandleObjects(QVector3D center, HandleMesh ids[], const QVector<QMatrix4x4> & mats, const QVector<QVector4D> & colors, QMatrix4x4 add_mat, int count) {
|
||||
QMatrix4x4 m = invariantSizeMatrix(center) * add_mat;
|
||||
cur_objects.resize(count);
|
||||
@@ -196,18 +246,7 @@ bool RendererService::calculateCenter() {
|
||||
}
|
||||
axis_mat = QMatrix4x4();
|
||||
if ((sol.size() == 1) && (current_action != haMove)) {
|
||||
ObjectBase * o = sol[0];
|
||||
QMatrix4x4 pmat;
|
||||
if (o->parent()) {
|
||||
pmat = o->parent()->worldTransform();
|
||||
pmat.setColumn(3, QVector4D(0,0,0,1));
|
||||
double det = pmat.determinant();
|
||||
if (det > 0.) pmat /= sqrt(det);
|
||||
}
|
||||
axis_mat.rotate(o->angles_.z(), 0., 0., 1.);
|
||||
axis_mat.rotate(o->angles_.y(), 0., 1., 0.);
|
||||
axis_mat.rotate(o->angles_.x(), 1., 0., 0.);
|
||||
axis_mat = pmat * axis_mat;
|
||||
axis_mat = parentRotationMatrix(sol[0]);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -259,11 +298,50 @@ void RendererService::drawCurrentHandleObjects() {
|
||||
|
||||
|
||||
void RendererService::drawLights() {
|
||||
QGLView * v = r->view;
|
||||
RendererSelection & rs(r->rend_selection);
|
||||
|
||||
fillOmniObjects();
|
||||
omni_mesh->loadObjects(r->view, cur_objects);
|
||||
r->fillSelectionsBuffer(r->rend_selection.cur_selections_, light2objectList(r->view->scene_->lights_used.value(Light::Omni)));
|
||||
omni_mesh->loadSelections(r->view, r->rend_selection.cur_selections_);
|
||||
omni_mesh->draw(r->view, cur_objects.size());
|
||||
omni_mesh->loadObjects(v, cur_objects);
|
||||
r->fillSelectionsBuffer(rs.cur_selections_, light2objectList(v->scene_->lights_used.value(Light::Omni)));
|
||||
omni_mesh->loadSelections(v, rs.cur_selections_);
|
||||
omni_mesh->draw(v, cur_objects.size());
|
||||
|
||||
fillSpotObjects();
|
||||
cone_mesh->loadObjects(v, cur_objects);
|
||||
r->fillSelectionsBuffer(rs.cur_selections_, light2objectList(v->scene_->lights_used.value(Light::Cone)));
|
||||
cone_mesh->loadSelections(v, rs.cur_selections_);
|
||||
cone_mesh->draw(v, cur_objects.size());
|
||||
box_mesh->loadObjects(v, cur_aims);
|
||||
box_mesh->loadSelections(v, rs.cur_selections_);
|
||||
box_mesh->draw(v, cur_aims.size());
|
||||
|
||||
}
|
||||
|
||||
|
||||
void RendererService::drawLightsFrame(QColor color) {
|
||||
QGLView * v = r->view;
|
||||
RendererSelection & rs(r->rend_selection);
|
||||
|
||||
fillOmniObjects();
|
||||
setObjectsColor(cur_objects, color);
|
||||
omni_mesh_f->loadObjects(v, cur_objects);
|
||||
r->fillSelectionsBuffer(rs.cur_selections_, light2objectList(v->scene_->lights_used.value(Light::Omni)));
|
||||
omni_mesh_f->loadSelections(v, rs.cur_selections_);
|
||||
omni_mesh_f->draw(v, cur_objects.size());
|
||||
|
||||
fillSpotObjects();
|
||||
setObjectsColor(cur_objects, color);
|
||||
cone_mesh_f->loadObjects(v, cur_objects);
|
||||
r->fillSelectionsBuffer(rs.cur_selections_, light2objectList(v->scene_->lights_used.value(Light::Cone)));
|
||||
cone_mesh_f->loadSelections(v, rs.cur_selections_);
|
||||
cone_mesh_f->draw(v, cur_objects.size());
|
||||
setObjectsColor(cur_aims, color);
|
||||
box_mesh_f->loadObjects(v, cur_aims);
|
||||
box_mesh_f->loadSelections(v, rs.cur_selections_);
|
||||
box_mesh_f->draw(v, cur_aims.size());
|
||||
|
||||
setObjectsColor(cur_aims, color);
|
||||
}
|
||||
|
||||
|
||||
@@ -289,19 +367,13 @@ void RendererService::renderService() {
|
||||
//glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDisable(GL_CULL_FACE);
|
||||
r->setUniformCamera(prog, r->view->camera());
|
||||
fillOmniObjects();
|
||||
|
||||
setObjectsColor(cur_objects, Qt::white);
|
||||
prog->setUniformValue("line_width", 2.f);
|
||||
prog->setUniformValue("z_offset", 0.f);
|
||||
omni_mesh_f->loadObjects(f, cur_objects);
|
||||
omni_mesh_f->draw(f, cur_objects.size());
|
||||
|
||||
setObjectsColor(cur_objects, Qt::black);
|
||||
drawLightsFrame(Qt::white);
|
||||
prog->setUniformValue("line_width", 1.f);
|
||||
prog->setUniformValue("z_offset", -1.E-2f);
|
||||
omni_mesh_f->loadObjects(f, cur_objects);
|
||||
omni_mesh_f->draw(f, cur_objects.size());
|
||||
drawLightsFrame(Qt::black);
|
||||
|
||||
glEnable(GL_CULL_FACE);
|
||||
//glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
|
||||
@@ -66,12 +66,15 @@ public:
|
||||
void resize(int width, int height);
|
||||
|
||||
QMatrix4x4 invariantSizeMatrix(QVector3D p);
|
||||
QMatrix4x4 parentRotationMatrix(ObjectBase * o, bool self_rotation = true);
|
||||
void fillXYZObjects();
|
||||
void fillOmniObjects();
|
||||
void fillSpotObjects();
|
||||
void fillHandleObjects(QVector3D center, HandleMesh ids[], const QVector<QMatrix4x4> & mats, const QVector<QVector4D> & colors, QMatrix4x4 add_mat, int count = 3);
|
||||
bool calculateCenter();
|
||||
void drawCurrentHandleObjects();
|
||||
void drawLights();
|
||||
void drawLightsFrame(QColor color);
|
||||
void setObjectsColor(QVector<QGLEngineShaders::Object> & ol, QColor col);
|
||||
void renderService();
|
||||
void setCurrentAction(HandleAction ha) {current_action = ha;}
|
||||
@@ -87,7 +90,7 @@ private:
|
||||
QVector3D selection_center;
|
||||
QVector<QMatrix4x4> mat_xyz, mat_ms2;
|
||||
QVector<QVector4D> color_xyz, color_ms2;
|
||||
QVector<QGLEngineShaders::Object> cur_objects;
|
||||
QVector<QGLEngineShaders::Object> cur_objects, cur_aims;
|
||||
Camera * axis_camera;
|
||||
QSize axis_viewport;
|
||||
HandleAction current_action;
|
||||
|
||||
@@ -52,8 +52,8 @@ void main(void) {
|
||||
|
||||
float height = dot(qgl_materialTexture(QGL_MAP_RELIEF, tc, vec4(0)).rgb, luma);
|
||||
|
||||
qgl_FragData[0] = vec4(diffuse .rgb, roughness );
|
||||
qgl_FragData[1] = vec4(normal .xyz, reflectivity);
|
||||
qgl_FragData[0] = vec4(diffuse .rgb, reflectivity);
|
||||
qgl_FragData[1] = vec4(normal .xyz, roughness );
|
||||
qgl_FragData[2] = vec4(specular.rgb, height );
|
||||
qgl_FragData[3] = vec4(emission.rgb, 0/*bn.x*/);
|
||||
//qgl_FragData[4] = vec4(speed.xy, bn.yz);
|
||||
|
||||
@@ -113,8 +113,8 @@ void main(void) {
|
||||
vec3 normal = v1.xyz;
|
||||
vec3 specular = v2.rgb;
|
||||
vec3 emission = v3.rgb;
|
||||
float roughness = v0.w;
|
||||
float reflectivity = v1.w;
|
||||
float reflectivity = v0.w;
|
||||
float roughness = v1.w;
|
||||
float height = v2.w;
|
||||
//bn = normalize(vec3(v3.w, v4.zw));
|
||||
//bn2 = normalize(cross(n, bn));
|
||||
|
||||
@@ -6,7 +6,8 @@ out float mat_scale;
|
||||
void main(void) {
|
||||
gl_Position = qgl_ftransform();
|
||||
object_color_g = qgl_ObjectColor;
|
||||
mat_scale = pow(qgl_ModelMatrix[0][0] * qgl_ModelMatrix[1][1] * qgl_ModelMatrix[2][2], 0.3333);
|
||||
//mat_scale = pow(qgl_ModelMatrix[0][0] * qgl_ModelMatrix[1][1] * qgl_ModelMatrix[2][2], 0.3333);
|
||||
mat_scale = pow(determinant(mat3(qgl_ModelMatrix)), 0.333);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -86,9 +86,9 @@ void ObjectEditor::setObject(ObjectBase * o) {
|
||||
ui->spinLightDecayQuadratic->setValue(l->decay_quadratic);
|
||||
ui->spinLightAngleStart->setValue(l->angle_start);
|
||||
ui->spinLightAngleEnd->setValue(l->angle_end);
|
||||
ui->spinLightDirectionX->setValue(l->direction.x());
|
||||
ui->spinLightDirectionY->setValue(l->direction.y());
|
||||
ui->spinLightDirectionZ->setValue(l->direction.z());
|
||||
ui->spinLightDirectionX->setValue(l->direction().x());
|
||||
ui->spinLightDirectionY->setValue(l->direction().y());
|
||||
ui->spinLightDirectionZ->setValue(l->direction().z());
|
||||
}
|
||||
ui->groupCamera->setEnabled(object->type() == ObjectBase::glCamera);
|
||||
ui->groupCamera->setVisible(object->type() == ObjectBase::glCamera);
|
||||
@@ -135,7 +135,7 @@ void ObjectEditor::objectChanged() {
|
||||
l->decay_quadratic = ui->spinLightDecayQuadratic->value();
|
||||
l->angle_start = ui->spinLightAngleStart->value();
|
||||
l->angle_end = ui->spinLightAngleEnd->value();
|
||||
l->direction = QVector3D(ui->spinLightDirectionX->value(), ui->spinLightDirectionY->value(), ui->spinLightDirectionZ->value()).normalized();
|
||||
l->setDirection(QVector3D(ui->spinLightDirectionX->value(), ui->spinLightDirectionY->value(), ui->spinLightDirectionZ->value()).normalized());
|
||||
l->apply();
|
||||
}
|
||||
if (object->type() == ObjectBase::glCamera) {
|
||||
|
||||
Reference in New Issue
Block a user