Ejemplo n.º 1
0
void KisInfinityManager::drawDecoration(QPainter& gc, const QRectF& updateArea, const KisCoordinatesConverter *converter, KisCanvas2 *canvas)
{
    Q_UNUSED(updateArea);
    Q_UNUSED(converter);
    Q_UNUSED(canvas);

    if (!m_filteringEnabled) return;

    gc.save();
    gc.setTransform(QTransform(), false);

    KisConfig cfg;
    QColor color = cfg.canvasBorderColor();
    gc.fillPath(m_decorationPath, color.darker(115));

    QPainterPath p;

    p.moveTo(5, 2);
    p.lineTo(-3, 8);
    p.lineTo(-5, 5);
    p.lineTo( 2, 0);
    p.lineTo(-5,-5);
    p.lineTo(-3,-8);
    p.lineTo( 5,-2);
    p.arcTo(QRectF(3, -2, 4, 4), 90, -180);

    foreach (const QTransform &t, m_handleTransform) {
        gc.fillPath(t.map(p), color);
    }
Ejemplo n.º 2
0
void KisOpenGLCanvas2::paintGL()
{
    if (!OPENGL_SUCCESS) {
        KisConfig cfg;
        cfg.writeEntry("canvasState", "OPENGL_PAINT_STARTED");
    }

    KisOpenglCanvasDebugger::instance()->nofityPaintRequested();

    renderCanvasGL();

    if (d->glSyncObject) {
        Sync::deleteSync(d->glSyncObject);
    }
    d->glSyncObject = Sync::getSync();

    QPainter gc(this);
    renderDecorations(&gc);
    gc.end();

    if (!OPENGL_SUCCESS) {
        KisConfig cfg;
        cfg.writeEntry("canvasState", "OPENGL_SUCCESS");
        OPENGL_SUCCESS = true;
    }
}
Ejemplo n.º 3
0
KisInputManager::Private::Private(KisInputManager *qq)
    : q(qq)
    , canvas(0)
    , toolProxy(0)
    , forwardAllEventsToTool(false)
    , disableTouchOnCanvas(false)
    , touchHasBlockedPressEvents(false)
    , lastTouchEvent(0)
    , defaultInputAction(0)
    , eventsReceiver(0)
    , moveEventCompressor(10 /* ms */, KisSignalCompressor::FIRST_ACTIVE)
    , testingAcceptCompressedTabletEvents(false)
    , testingCompressBrushEvents(false)
    , focusOnEnter(true)
    , containsPointer(true)
{
    KisConfig cfg;
    disableTouchOnCanvas = cfg.disableTouchOnCanvas();

    moveEventCompressor.setDelay(cfg.tabletEventsDelay());
    testingAcceptCompressedTabletEvents = cfg.testingAcceptCompressedTabletEvents();
    testingCompressBrushEvents = cfg.testingCompressBrushEvents();
    setupActions();
    canvasSwitcher = new CanvasSwitcher(this, q);
    qApp->installEventFilter(globalEventEater);
}
Ejemplo n.º 4
0
void KisToolFreehandHelper::stabilizerStart(KisPaintInformation firstPaintInfo)
{
    // FIXME: Ugly hack, this is no a "distance" in any way
    int sampleSize = qRound(m_d->effectiveSmoothnessDistance());
    sampleSize = qMax(3, sampleSize);

    // Fill the deque with the current value repeated until filling the sample
    m_d->stabilizerDeque.clear();
    for (int i = sampleSize; i > 0; i--) {
        m_d->stabilizerDeque.enqueue(firstPaintInfo);
    }

    // Poll and draw regularly
    KisConfig cfg;
    int stabilizerSampleSize = cfg.stabilizerSampleSize();
    m_d->stabilizerPollTimer.setInterval(stabilizerSampleSize);
    m_d->stabilizerPollTimer.start();

    int delayedPaintInterval = cfg.stabilizerDelayedPaintInterval();
    if (delayedPaintInterval < stabilizerSampleSize) {
        m_d->stabilizerDelayedPaintHelper.start(delayedPaintInterval, firstPaintInfo);
    }

    m_d->stabilizedSampler.clear();
    m_d->stabilizedSampler.addEvent(firstPaintInfo);
}
Ejemplo n.º 5
0
bool KisOpenGLImageTextures::imageCanUseHDRExposureProgram(KisImageSP image)
{
#ifdef HAVE_GLEW
    if (!image->colorSpace()->hasHighDynamicRange()) {
        return false;
    }

    KisConfig cfg;

    if (!cfg.useOpenGLShaders()) {
        return false;
    }
    if (HDRExposureProgram == 0) {
        return false;
    }
    if (!HDRExposureProgram->isValid()) {
        return false;
    }
    if (!haveHDRTextureFormat(image->colorSpace())) {
        return false;
    }
    return true;
#else
    Q_UNUSED(image);
    return false;
#endif
}
void KisCoordinatesConverter::getQPainterCheckersInfo(QTransform *transform,
                                                      QPointF *brushOrigin,
                                                      QPolygonF *polygon) const
{
    /**
     * Qt has different rounding for QPainter::drawRect/drawImage.
     * The image is rounded mathematically, while rect in aligned
     * to the next integer. That causes transparent line appear on
     * the canvas.
     *
     * See: https://bugreports.qt.nokia.com/browse/QTBUG-22827
     */

    QRectF imageRect = imageRectInViewportPixels();
    imageRect.adjust(0,0,-0.5,-0.5);

    KisConfig cfg;
    if (cfg.scrollCheckers()) {
        *transform = viewportToWidgetTransform();
        *polygon = imageRect;
        *brushOrigin = imageToViewport(QPointF(0,0));
    }
    else {
        *transform = QTransform();
        *polygon = viewportToWidgetTransform().map(imageRect);
        *brushOrigin = QPoint(0,0);
    }
}
Ejemplo n.º 7
0
void KisPaintingInformationBuilder::updateSettings()
{
    KisConfig cfg;
    KisCubicCurve curve;
    curve.fromString(cfg.pressureTabletCurve());
    m_pressureSamples = curve.floatTransfer(LEVEL_OF_PRESSURE_RESOLUTION + 1);
}
Ejemplo n.º 8
0
bool PaletteDockerDock::eventFilter(QObject* object, QEvent* event)
{
    if (object == m_wdgPaletteDock->paletteView->viewport() && event->type() == QEvent::Wheel) {
        QWheelEvent* qwheel = dynamic_cast<QWheelEvent* >(event);
        if (qwheel->modifiers() & Qt::ControlModifier) {

            int numDegrees = qwheel->delta() / 8;
            int numSteps = numDegrees / 7;
            int curSize = m_wdgPaletteDock->paletteView->horizontalHeader()->sectionSize(0);
            int setSize = numSteps + curSize;

            if ( setSize >= 12 ) {
                m_wdgPaletteDock->paletteView->horizontalHeader()->setDefaultSectionSize(setSize);
                m_wdgPaletteDock->paletteView->verticalHeader()->setDefaultSectionSize(setSize);
                KisConfig cfg;
                cfg.setPaletteDockerPaletteViewSectionSize(setSize);
            }
            return true;
        } else {
            return false;
        }
    } else {
        return QWidget::eventFilter(object, event);
    }
}
Ejemplo n.º 9
0
void KisColorSelector::loadSettings()
{
    KisConfig cfg;
    setColorSpace(KisColor::Type(cfg.readEntry<qint32>("ArtColorSel.ColorSpace" , KisColor::HSY)));
    
    setNumLightPieces(cfg.readEntry("ArtColorSel.LightPieces", 19));
    
    m_selectedColor.setH(cfg.readEntry<float>("ArtColorSel.SelColorH", 0.0f));
    m_selectedColor.setS(cfg.readEntry<float>("ArtColorSel.SelColorS", 0.0f));
    m_selectedColor.setX(cfg.readEntry<float>("ArtColorSel.SelColorX", 0.0f));
    m_selectedColor.setA(1.0f);
    
    setInverseSaturation(cfg.readEntry<bool>("ArtColorSel.InversedSaturation", false));
    setLight(cfg.readEntry<float>("ArtColorSel.Light", 0.5f), cfg.readEntry<bool>("ArtColorSel.RelativeLight", false));
    
    recalculateRings(
                cfg.readEntry("ArtColorSel.NumRings"  , 11),
                cfg.readEntry("ArtColorSel.RingPieces", 12)
                );
    
    QList<float> angles = cfg.readList<float>("ArtColorSel.RingAngles");

    for (int i = 0; i < m_colorRings.size(); ++i) {
        if (i < angles.size() && i < m_colorRings.size()) {
            m_colorRings[i].angle = angles[i];
        }
    }
    
    selectColor(m_selectedColor);
    update();
}
Ejemplo n.º 10
0
void KisGridConfig::saveStaticData() const
{
    KisConfig cfg;
    cfg.setGridMainStyle(m_lineTypeMain);
    cfg.setGridSubdivisionStyle(m_lineTypeSubdivision);
    cfg.setGridMainColor(m_colorMain);
    cfg.setGridSubdivisionColor(m_colorSubdivision);
}
Ejemplo n.º 11
0
KisFilterPreviewWidget::KisFilterPreviewWidget(QWidget* parent): QWidget(parent)
{
    KisConfig cfg;
    // for preview make it smaller than on canvas
    qint32 checkSize = qMax(1,cfg.checkSize() / 2);
    QImage checkImage = KisCanvasWidgetBase::createCheckersImage(checkSize);
    m_checkBrush = QBrush(checkImage);
    m_pixmap = QPixmap::fromImage(checkImage);
}
Ejemplo n.º 12
0
PaletteDockerDock::~PaletteDockerDock()
{
    KoResourceServer<KoColorSet>* rServer = KoResourceServerProvider::instance()->paletteServer();
    rServer->removeObserver(this);

    if (m_currentColorSet) {
        KisConfig cfg;
        cfg.setDefaultPalette(m_currentColorSet->name());
    }
}
Ejemplo n.º 13
0
KisTextureTile::~KisTextureTile()
{
#ifdef USE_PIXEL_BUFFERS
    KisConfig cfg;
    if (cfg.useOpenGLTextureBuffer()) {
        delete m_glBuffer;
    }
#endif
    glDeleteTextures(1, &m_textureId);
}
Ejemplo n.º 14
0
void KisGridConfig::loadStaticData()
{
    KisConfig cfg;

    m_lineTypeMain = LineTypeInternal(cfg.getGridMainStyle());
    m_lineTypeSubdivision = LineTypeInternal(cfg.getGridSubdivisionStyle());

    m_colorMain = cfg.getGridMainColor();
    m_colorSubdivision = cfg.getGridSubdivisionColor();
}
Ejemplo n.º 15
0
void KisOpenGLCanvas2::initializeGL()
{
    KisOpenGL::initializeContext(context());
    initializeOpenGLFunctions();

    KisConfig cfg;
    d->openGLImageTextures->setProofingConfig(canvas()->proofingConfiguration());
    d->openGLImageTextures->initGL(context()->functions());
    d->openGLImageTextures->generateCheckerTexture(createCheckersImage(cfg.checkSize()));

    initializeShaders();

    // If we support OpenGL 3.2, then prepare our VAOs and VBOs for drawing
    if (KisOpenGL::hasOpenGL3()) {
        d->quadVAO.create();
        d->quadVAO.bind();

        glEnableVertexAttribArray(PROGRAM_VERTEX_ATTRIBUTE);
        glEnableVertexAttribArray(PROGRAM_TEXCOORD_ATTRIBUTE);

        // Create the vertex buffer object, it has 6 vertices with 3 components
        d->quadBuffers[0].create();
        d->quadBuffers[0].setUsagePattern(QOpenGLBuffer::StaticDraw);
        d->quadBuffers[0].bind();
        d->quadBuffers[0].allocate(d->vertices, 6 * 3 * sizeof(float));
        glVertexAttribPointer(PROGRAM_VERTEX_ATTRIBUTE, 3, GL_FLOAT, GL_FALSE, 0, 0);

        // Create the texture buffer object, it has 6 texture coordinates with 2 components
        d->quadBuffers[1].create();
        d->quadBuffers[1].setUsagePattern(QOpenGLBuffer::StaticDraw);
        d->quadBuffers[1].bind();
        d->quadBuffers[1].allocate(d->texCoords, 6 * 2 * sizeof(float));
        glVertexAttribPointer(PROGRAM_TEXCOORD_ATTRIBUTE, 2, GL_FLOAT, GL_FALSE, 0, 0);

        // Create the outline buffer, this buffer will store the outlines of
        // tools and will frequently change data
        d->outlineVAO.create();
        d->outlineVAO.bind();

        glEnableVertexAttribArray(PROGRAM_VERTEX_ATTRIBUTE);

        // The outline buffer has a StreamDraw usage pattern, because it changes constantly
        d->lineBuffer.create();
        d->lineBuffer.setUsagePattern(QOpenGLBuffer::StreamDraw);
        d->lineBuffer.bind();
        glVertexAttribPointer(PROGRAM_VERTEX_ATTRIBUTE, 3, GL_FLOAT, GL_FALSE, 0, 0);
    }

    ptr_glLogicOp = (kis_glLogicOp)(context()->getProcAddress("glLogicOp"));

    Sync::init(context());

    d->canvasInitialized = true;
}
void KisCanvasResourceProvider::resetDisplayProfile()
{
    // XXX: The X11 monitor profile overrides the settings
    m_displayProfile = KisCanvasResourceProvider::getScreenProfile();

    if (m_displayProfile == 0) {
        KisConfig cfg;
        QString monitorProfileName = cfg.monitorProfile();
        m_displayProfile = KoColorSpaceRegistry::instance()->profileByName(monitorProfileName);
    }
    emit sigDisplayProfileChanged(m_displayProfile);
}
Ejemplo n.º 17
0
void KisNodeModel::updateSettings()
{
    KisConfig cfg;
    bool oldShowRootLayer = m_d->showRootLayer;
    bool oldShowGlobalSelection = m_d->showGlobalSelection;
    m_d->showRootLayer = cfg.showRootLayer();
    m_d->showGlobalSelection = cfg.showGlobalSelection();
    if (m_d->showRootLayer != oldShowRootLayer || m_d->showGlobalSelection != oldShowGlobalSelection) {
        resetIndexConverter();
        reset();
    }
}
Ejemplo n.º 18
0
WdgImagesplit::WdgImagesplit(QWidget* parent)
    : QWidget(parent)
{
    setupUi(this);

    KisConfig cfg;

    intHorizontalSplitLines->setValue(cfg.horizontalSplitLines());
    intVerticalSplitLines->setValue(cfg.verticalSplitLines());

    chkAutoSave->setChecked(true);
}
Ejemplo n.º 19
0
KisInputManager::Private::Private(KisInputManager *qq)
    : q(qq)
    , moveEventCompressor(10 /* ms */, KisSignalCompressor::FIRST_ACTIVE)
    , canvasSwitcher(this, qq)
{
    KisConfig cfg;
    disableTouchOnCanvas = cfg.disableTouchOnCanvas();

    moveEventCompressor.setDelay(cfg.tabletEventsDelay());
    testingAcceptCompressedTabletEvents = cfg.testingAcceptCompressedTabletEvents();
    testingCompressBrushEvents = cfg.testingCompressBrushEvents();
    setupActions();
}
KisFavoriteResourceManager::KisFavoriteResourceManager(KisPaintopBox *paintopBox)
    : m_paintopBox(paintopBox)
    , m_colorList(0)
    , m_blockUpdates(false)
    , m_initialized(false)
{
    KisConfig cfg;
    m_maxPresets = cfg.favoritePresets();
    m_colorList = new ColorDataList();
    connect(KisConfigNotifier::instance(), SIGNAL(configChanged()), SLOT(configChanged()));
    KisPaintOpPresetResourceServer * rServer = KisResourceServerProvider::instance()->paintOpPresetServer(false);
    rServer->addObserver(this);
}
Ejemplo n.º 21
0
void KisOpenGLImageTextures::createHDRExposureProgramIfCan()
{
    KisConfig cfg;
    if (!cfg.useOpenGLShaders()) return;
    
#ifdef HAVE_GLEW
    if (HDRExposureProgram == 0 && KisOpenGL::hasShadingLanguage()) {
        dbgUI << "Creating shared HDR exposure program";
        HDRExposureProgram = new KisOpenGLHDRExposureProgram();
        Q_CHECK_PTR(HDRExposureProgram);
    }
#endif
}
Ejemplo n.º 22
0
int KisOpenGL::initializeContext(QOpenGLContext* s) {
#ifdef HAVE_OPENGL
    KisConfig cfg;
    dbgUI << "OpenGL: Opening new context";

    // Double check we were given the version we requested
    QSurfaceFormat format = s->format();
    glVersion = 100 * format.majorVersion() + format.minorVersion();

    if (!SharedSurface) {
        SharedSurface = new QOffscreenSurface();
        SharedSurface->setFormat(format);
        SharedSurface->create();
    }

    if (!SharedContext) {
        SharedContext = new QOpenGLContext;
        SharedContext->setFormat(format);
        SharedContext->setShareContext(s);
        SharedContext->create();
        SharedContext->makeCurrent(SharedSurface);
    }

    QOpenGLFunctions *f = QOpenGLContext::currentContext()->functions();

    QFile log(QDesktopServices::storageLocation(QDesktopServices::TempLocation) + "/krita-opengl.txt");
    log.open(QFile::WriteOnly);
    QString vendor((const char*)f->glGetString(GL_VENDOR));
    log.write(vendor.toLatin1());
    log.write(", ");
    QString renderer((const char*)f->glGetString(GL_RENDERER));
    log.write(renderer.toLatin1());
    log.write(", ");
    QString version((const char*)f->glGetString(GL_VERSION));
    log.write(version.toLatin1());

    // Check if we have a bugged driver that needs fence workaround
    bool isOnX11 = false;
#ifdef HAVE_X11
    isOnX11 = true;
#endif

    if ((isOnX11 && renderer.startsWith("AMD")) || cfg.forceOpenGLFenceWorkaround()) {
        NeedsFenceWorkaround = true;
    }
#else
    Q_UNUSED(s);
    NeedsFenceWorkaround = false;
#endif
    return glVersion;
}
Ejemplo n.º 23
0
KisTextureTile::KisTextureTile(QRect imageRect, const KisGLTexturesInfo *texturesInfo,
                               const QByteArray &fillData, FilterMode filter)

    : m_textureId(0)
#ifdef USE_PIXEL_BUFFERS
    , m_glBuffer(0)
#endif
    , m_tileRectInImagePixels(imageRect)
    , m_filter(filter)
    , m_texturesInfo(texturesInfo)
    , m_needsMipmapRegeneration(false)
{
    const GLvoid *fd = fillData.constData();

    m_textureRectInImagePixels =
        stretchRect(m_tileRectInImagePixels, texturesInfo->border);

    m_tileRectInTexturePixels = relativeRect(m_textureRectInImagePixels,
                                m_tileRectInImagePixels,
                                m_texturesInfo);

    glGenTextures(1, &m_textureId);
    glBindTexture(GL_TEXTURE_2D, m_textureId);

    setTextureParameters();

#ifdef USE_PIXEL_BUFFERS
    createTextureBuffer(fillData);
    // we set fill data to 0 so the next glTexImage2D call uses our buffer
    fd = 0;
#endif

    glTexImage2D(GL_TEXTURE_2D, 0,
                 m_texturesInfo->internalFormat,
                 m_texturesInfo->width,
                 m_texturesInfo->height, 0,
                 m_texturesInfo->format,
                 m_texturesInfo->type, fd);

#ifdef USE_PIXEL_BUFFERS
    KisConfig cfg;
    if (cfg.useOpenGLTextureBuffer()) {
        m_glBuffer->release();
    }
#endif

    setNeedsMipmapRegeneration();
}
Ejemplo n.º 24
0
/**
 * Displays a message box telling the user that
 * shader compilation failed and turns off OpenGL.
 */
void KisOpenGLCanvas2::reportFailedShaderCompilation(const QString &context)
{
    KisConfig cfg;

    if (cfg.useVerboseOpenGLDebugOutput()) {
        dbgUI << "GL-log:" << context;
    }

    qDebug() << "Shader Compilation Failure: " << context;
    QMessageBox::critical(this, i18nc("@title:window", "Krita"),
                          QString(i18n("Krita could not initialize the OpenGL canvas:\n\n%1\n\n Krita will disable OpenGL and close now.")).arg(context),
                          QMessageBox::Close);

    cfg.setUseOpenGL(false);
    cfg.setCanvasState("OPENGL_FAILED");
}
Ejemplo n.º 25
0
void KisCanvas2::createCanvas()
{
    KisConfig cfg;
    slotSetDisplayProfile( KoColorSpaceRegistry::instance()->profileByName(cfg.monitorProfile()) );

    if (cfg.useOpenGL()) {
#ifdef HAVE_OPENGL
        createOpenGLCanvas();
#else
        warnKrita << "OpenGL requested while its not available, starting qpainter canvas";
        createQPainterCanvas();
#endif
    } else {
        createQPainterCanvas();

    }

}
Ejemplo n.º 26
0
void HistoryDock::setCanvas(KoCanvasBase *canvas) {

    setEnabled(canvas != 0);

    KisCanvas2* myCanvas = dynamic_cast<KisCanvas2*>( canvas );
    if (myCanvas) {
        KUndo2Stack* undoStack = canvas->shapeController()->resourceManager()->undoStack();

        m_undoView->setStack(undoStack);
        KisConfig cfg;
        m_undoView->stack()->setUseCumulativeUndoRedo(cfg.useCumulativeUndoRedo());
        m_undoView->stack()->setTimeT1(cfg.stackT1());
        m_undoView->stack()->setTimeT2(cfg.stackT2());
        m_undoView->stack()->setStrokesN(cfg.stackN());
    }
    m_undoView->setCanvas( myCanvas );

}
Ejemplo n.º 27
0
void ImageBuilder::createImageFromClipboardDelayed()
{
    DocumentManager::instance()->disconnect(this, SLOT(createImageFromClipboardDelayed()));
    KisConfig cfg;
    cfg.setPasteBehaviour(PASTE_ASSUME_MONITOR);

    QSize sz = KisClipboard::instance()->clipSize();
    KisPaintDeviceSP clipDevice = KisClipboard::instance()->clip(QRect(0, 0, sz.width(), sz.height()), false);
    KisImageWSP image = DocumentManager::instance()->document()->image();
    if (image && image->root() && image->root()->firstChild()) {
        KisLayer * layer = dynamic_cast<KisLayer*>(image->root()->firstChild().data());
        Q_ASSERT(layer);
        layer->setOpacity(OPACITY_OPAQUE_U8);
        QRect r = clipDevice->exactBounds();

        KisPainter::copyAreaOptimized(QPoint(), clipDevice, layer->paintDevice(), r);
        layer->setDirty(QRect(0, 0, sz.width(), sz.height()));
    }
}
Ejemplo n.º 28
0
MainWindow::MainWindow(QStringList fileNames, QWidget* parent, Qt::WindowFlags flags )
    : QMainWindow( parent, flags ), d( new Private(this) )
{
    qApp->setActiveWindow( this );

    setWindowTitle(i18n("Krita Sketch"));
    setWindowIcon(KIcon("kritasketch"));

    // Load filters and other plugins in the gui thread
    Q_UNUSED(KisFilterRegistry::instance());
    Q_UNUSED(KisPaintOpRegistry::instance());

    KisConfig cfg;
    cfg.setCursorStyle(CURSOR_STYLE_NO_CURSOR);
    cfg.setUseOpenGL(true);

    foreach(QString fileName, fileNames) {
        DocumentManager::instance()->recentFileManager()->addRecent(fileName);
    }
QPointF KisCoordinatesConverter::centeringCorrection() const
{
    KisConfig cfg;

    QSize documentSize = imageRectInWidgetPixels().toAlignedRect().size();
    QPointF dPoint(documentSize.width(), documentSize.height());
    QPointF wPoint(m_d->canvasWidgetSize.width(), m_d->canvasWidgetSize.height());

    QPointF minOffset = -cfg.vastScrolling() * wPoint;
    QPointF maxOffset = dPoint - wPoint + cfg.vastScrolling() * wPoint;

    QPointF range = maxOffset - minOffset;

    range.rx() = qMin(range.x(), (qreal)0.0);
    range.ry() = qMin(range.y(), (qreal)0.0);

    range /= 2;

    return -range;
}
void KisCoordinatesConverter::getOpenGLCheckersInfo(const QRectF &viewportRect,
                                                    QTransform *textureTransform,
                                                    QTransform *modelTransform,
                                                    QRectF *textureRect,
                                                    QRectF *modelRect) const
{
    KisConfig cfg;

    if(cfg.scrollCheckers()) {
        *textureTransform = QTransform();
        *textureRect = QRectF(0, 0, viewportRect.width(),viewportRect.height());
    }
    else {
        *textureTransform = viewportToWidgetTransform();
        *textureRect = viewportRect;
    }

    *modelTransform = viewportToWidgetTransform();
    *modelRect = viewportRect;
}