File indexing completed on 2024-06-02 04:51:24

0001 /*
0002  * Copyright 2018  Malte Veerman <malte.veerman@gmail.com>
0003  *
0004  * This program is free software; you can redistribute it and/or
0005  * modify it under the terms of the GNU General Public License as
0006  * published by the Free Software Foundation; either version 2 of
0007  * the License or (at your option) version 3 or any later version
0008  * accepted by the membership of KDE e.V. (or its successor approved
0009  * by the membership of KDE e.V.), which shall act as a proxy
0010  * defined in Section 14 of version 3 of the license.
0011  *
0012  * This program is distributed in the hope that it will be useful,
0013  * but WITHOUT ANY WARRANTY; without even the implied warranty of
0014  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
0015  * GNU General Public License for more details.
0016  *
0017  * You should have received a copy of the GNU General Public License
0018  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
0019  */
0020 
0021 #include "PixmapItem.h"
0022 
0023 #include <QPaintEngine>
0024 #include <QPainter>
0025 #include <QSGSimpleTextureNode>
0026 #include <QQuickWindow>
0027 
0028 #include <KDeclarative/KQuickAddons/ManagedTextureNode>
0029 
0030 
0031 PixmapItem::PixmapItem()
0032     : m_sizeChanged( true )
0033 {
0034     setFlag( ItemHasContents );
0035 }
0036 
0037 void PixmapItem::setSource( const QPixmap& source )
0038 {
0039     if( m_source.toImage() == source.toImage() )
0040         return;
0041 
0042     m_source = source;
0043     m_pixmapChanged = true;
0044     Q_EMIT sourceChanged();
0045 
0046     setImplicitSize( source.width(), source.height() );
0047 
0048     update();
0049 }
0050 
0051 QSGNode* PixmapItem::updatePaintNode( QSGNode *oldNode, UpdatePaintNodeData *updatePaintNodeData )
0052 {
0053     Q_UNUSED( updatePaintNodeData )
0054 
0055     if( m_source.isNull() || width() == 0 || height() == 0 )
0056     {
0057         delete oldNode;
0058 
0059         return nullptr;
0060     }
0061 
0062     ManagedTextureNode *textureNode = dynamic_cast<ManagedTextureNode*>( oldNode );
0063 
0064     if( !textureNode || m_pixmapChanged )
0065     {
0066         delete oldNode;
0067         textureNode = new ManagedTextureNode;
0068         textureNode->setFiltering( QSGTexture::Linear );
0069         textureNode->setTexture( QSharedPointer<QSGTexture>( window()->createTextureFromImage( m_source.toImage(), QQuickWindow::TextureCanUseAtlas ) ) );
0070         m_sizeChanged = true;
0071         m_pixmapChanged = false;
0072     }
0073 
0074     if( m_sizeChanged )
0075     {
0076         textureNode->setRect( boundingRect() );
0077         m_sizeChanged = false;
0078     }
0079 
0080     return textureNode;
0081 }
0082 
0083 void PixmapItem::geometryChanged( const QRectF &newGeometry, const QRectF &oldGeometry )
0084 {
0085     if( newGeometry.size() != oldGeometry.size() )
0086         m_sizeChanged = true;
0087 
0088     update();
0089 
0090     QQuickItem::geometryChanged( newGeometry, oldGeometry );
0091 }