1 /* 2 * SPDX-FileCopyrightText: 2014 Hugo Pereira Da Costa <hugo.pereira@free.fr> 3 * 4 * SPDX-License-Identifier: GPL-2.0-or-later 5 */ 6 7 #include "breezebusyindicatorengine.h" 8 9 #include "breezemetrics.h" 10 11 #include <QVariant> 12 13 namespace Breeze 14 { 15 16 //_______________________________________________ BusyIndicatorEngine(QObject * object)17 BusyIndicatorEngine::BusyIndicatorEngine( QObject* object ): 18 BaseEngine( object ) 19 {} 20 21 //_______________________________________________ registerWidget(QObject * object)22 bool BusyIndicatorEngine::registerWidget( QObject* object ) 23 { 24 25 // check widget validity 26 if( !object ) return false; 27 28 // create new data class 29 if( !_data.contains( object ) ) 30 { 31 _data.insert( object, new BusyIndicatorData( this ) ); 32 33 // connect destruction signal 34 connect( object, SIGNAL(destroyed(QObject*)), this, SLOT(unregisterWidget(QObject*)), Qt::UniqueConnection ); 35 } 36 37 return true; 38 39 } 40 41 //____________________________________________________________ isAnimated(const QObject * object)42 bool BusyIndicatorEngine::isAnimated( const QObject* object ) 43 { 44 45 DataMap<BusyIndicatorData>::Value data( BusyIndicatorEngine::data( object ) ); 46 return data && data.data()->isAnimated(); 47 48 } 49 50 //____________________________________________________________ setDuration(int value)51 void BusyIndicatorEngine::setDuration( int value ) 52 { 53 54 if( duration() == value ) return; 55 BaseEngine::setDuration( value ); 56 57 // restart timer with specified time 58 if( _animation ) 59 { _animation.data()->setDuration( value ); } 60 61 } 62 63 //____________________________________________________________ setAnimated(const QObject * object,bool value)64 void BusyIndicatorEngine::setAnimated( const QObject* object, bool value ) 65 { 66 67 DataMap<BusyIndicatorData>::Value data( BusyIndicatorEngine::data( object ) ); 68 if( data ) 69 { 70 // update data 71 data.data()->setAnimated( value ); 72 73 // start timer if needed 74 if( value ) 75 { 76 if( !_animation ) 77 { 78 79 // create animation if not already there 80 _animation = new Animation( duration(), this ); 81 82 // setup 83 _animation.data()->setStartValue( 0 ); 84 _animation.data()->setEndValue( 2*Metrics::ProgressBar_BusyIndicatorSize ); 85 _animation.data()->setTargetObject( this ); 86 _animation.data()->setPropertyName( "value" ); 87 _animation.data()->setLoopCount( -1 ); 88 _animation.data()->setDuration( duration() ); 89 90 } 91 92 // start if not already running 93 if( !_animation.data()->isRunning() ) 94 { _animation.data()->start(); } 95 96 } 97 98 } 99 100 101 } 102 103 104 //____________________________________________________________ data(const QObject * object)105 DataMap<BusyIndicatorData>::Value BusyIndicatorEngine::data( const QObject* object ) 106 { return _data.find( object ).data(); } 107 108 //_______________________________________________ setValue(int value)109 void BusyIndicatorEngine::setValue( int value ) 110 { 111 112 // update 113 _value = value; 114 115 bool animated( false ); 116 117 // loop over objects in map 118 for( DataMap<BusyIndicatorData>::iterator iter = _data.begin(); iter != _data.end(); ++iter ) 119 { 120 121 if( iter.value().data()->isAnimated() ) 122 { 123 124 // update animation flag 125 animated = true; 126 127 // emit update signal on object 128 if( const_cast<QObject*>( iter.key() )->inherits( "QQuickStyleItem" )) 129 { 130 131 //QtQuickControls "rerender" method is updateItem 132 QMetaObject::invokeMethod( const_cast<QObject*>( iter.key() ), "updateItem", Qt::QueuedConnection); 133 134 } else { 135 136 QMetaObject::invokeMethod( const_cast<QObject*>( iter.key() ), "update", Qt::QueuedConnection); 137 138 } 139 140 } 141 142 } 143 144 if( _animation && !animated ) 145 { 146 _animation.data()->stop(); 147 _animation.data()->deleteLater(); 148 _animation.clear(); 149 } 150 151 } 152 153 //__________________________________________________________ unregisterWidget(QObject * object)154 bool BusyIndicatorEngine::unregisterWidget( QObject* object ) 155 { 156 const bool removed( _data.unregisterWidget( object ) ); 157 if( _animation && _data.isEmpty() ) 158 { 159 _animation.data()->stop(); 160 _animation.data()->deleteLater(); 161 _animation.clear(); 162 } 163 164 return removed; 165 } 166 167 } 168