diff options
Diffstat (limited to 'examples/quick/scenegraph/openglunderqml/squircle.cpp')
-rw-r--r-- | examples/quick/scenegraph/openglunderqml/squircle.cpp | 160 |
1 files changed, 160 insertions, 0 deletions
diff --git a/examples/quick/scenegraph/openglunderqml/squircle.cpp b/examples/quick/scenegraph/openglunderqml/squircle.cpp new file mode 100644 index 0000000000..f7bbeb9f14 --- /dev/null +++ b/examples/quick/scenegraph/openglunderqml/squircle.cpp @@ -0,0 +1,160 @@ +/**************************************************************************** +** +** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies). +** Contact: http://www.qt-project.org/ +** +** This file is part of the demonstration applications of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** GNU Lesser General Public License Usage +** This file may be used under the terms of the GNU Lesser General Public +** License version 2.1 as published by the Free Software Foundation and +** appearing in the file LICENSE.LGPL included in the packaging of this +** file. Please review the following information to ensure the GNU Lesser +** General Public License version 2.1 requirements will be met: +** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU General +** Public License version 3.0 as published by the Free Software Foundation +** and appearing in the file LICENSE.GPL included in the packaging of this +** file. Please review the following information to ensure the GNU General +** Public License version 3.0 requirements will be met: +** http://www.gnu.org/copyleft/gpl.html. +** +** Other Usage +** Alternatively, this file may be used in accordance with the terms and +** conditions contained in a signed written agreement between you and Nokia. +** +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#include "squircle.h" + +#include <QtQuick/qquickwindow.h> +#include <QtGui/QOpenGLShaderProgram> +#include <QtGui/QOpenGLContext> + +//! [7] +Squircle::Squircle() + : m_program(0) +{ +} +//! [7] + +//! [8] +void Squircle::setT(qreal t) +{ + if (t == m_t) + return; + m_t = t; + emit tChanged(); + if (canvas()) + canvas()->update(); +} +//! [8] + + +//! [1] +void Squircle::itemChange(ItemChange change, const ItemChangeData &) +{ + // The ItemSceneChange event is sent when we are first attached to a window. + if (change == ItemSceneChange) { + QQuickWindow *c = window(); + if (!c) + return; +//! [1] + + // Connect the beforeRendering signal to our paint function. + // Since this call is executed on the rendering thread it must be + // a Qt::DirectConnection +//! [2] + connect(c, SIGNAL(beforeRendering()), this, SLOT(paint()), Qt::DirectConnection); +//! [2] + + // If we allow QML to do the clearing, they would clear what we paint + // and nothing would show. +//! [3] + c->setClearBeforeRendering(false); + } +} +//! [3] //! [4] +void Squircle::paint() +{ + if (!m_program) { + m_program = new QOpenGLShaderProgram(); + m_program->addShaderFromSourceCode(QOpenGLShader::Vertex, + "attribute highp vec4 vertices;" + "varying highp vec2 coords;" + "void main() {" + " gl_Position = vertices;" + " coords = vertices.xy;" + "}"); + m_program->addShaderFromSourceCode(QOpenGLShader::Fragment, + "uniform lowp float t;" + "varying highp vec2 coords;" + "void main() {" + " lowp float i = 1. - (pow(coords.x, 4.) + pow(coords.y, 4.));" + " i = smoothstep(t - 0.8, t + 0.8, i);" + " i = floor(i * 20.) / 20.;" + " gl_FragColor = vec4(coords * .5 + .5, i, i);" + "}"); + + m_program->bindAttributeLocation("vertices", 0); + m_program->link(); + + connect(canvas()->openglContext(), SIGNAL(aboutToBeDestroyed()), + this, SLOT(cleanup()), Qt::DirectConnection); + } +//! [4] //! [5] + m_program->bind(); + + m_program->enableAttributeArray(0); + + float values[] = { + -1, -1, + 1, -1, + -1, 1, + 1, 1 + }; + m_program->setAttributeArray(0, GL_FLOAT, values, 2); + m_program->setUniformValue("t", (float) m_t); + + glViewport(0, 0, window()->width(), window()->height()); + + glDisable(GL_DEPTH_TEST); + + glClearColor(0, 0, 0, 1); + glClear(GL_COLOR_BUFFER_BIT); + + glEnable(GL_BLEND); + glBlendFunc(GL_SRC_ALPHA, GL_ONE); + + glDrawArrays(GL_TRIANGLE_STRIP, 0, 4); + + m_program->disableAttributeArray(0); + m_program->release(); +} +//! [5] + +//! [6] +void Squircle::cleanup() +{ + if (m_program) { + delete m_program; + m_program = 0; + } +} +//! [6] + + |