10 #include "qwt_widget_overlay.h" 
   11 #include "qwt_painter.h" 
   14 #include <qpaintengine.h> 
   15 #include <qpainterpath.h> 
   21 static QImage::Format qwtMaskImageFormat()
 
   24         return QImage::Format_ARGB32;
 
   26     return QImage::Format_ARGB32_Premultiplied;
 
   29 static QRegion qwtAlphaMask( 
const QImage& image, 
const QRegion& region )
 
   31     const int w = image.width();
 
   32     const int h = image.height();
 
   37 #if QT_VERSION >= 0x050800 
   38     for ( QRegion::const_iterator it = region.cbegin();
 
   39         it != region.cend(); ++it )
 
   44     for ( 
int i = 0; i < rects.size(); i++ )
 
   46         const QRect& r = rects[i];
 
   49         r.getCoords( &x1, &y1, &x2, &y2 );
 
   52         x2 = qMin( x2, w - 1 );
 
   54         y2 = qMin( y2, h - 1 );
 
   56         for ( 
int y = y1; y <= y2; ++y )
 
   62                 reinterpret_cast< const uint* 
> ( image.scanLine( y ) ) + x1;
 
   63             for ( 
int x = x1; x <= x2; x++ )
 
   65                 const bool on = ( ( *line++ >> 24 ) != 0 );
 
   70                         rect.setCoords( rx0, y, x - 1, y );
 
   84                 rect.setCoords( rx0, y, x2, y );
 
   85                 mask = mask.united( rect );
 
   93 class QwtWidgetOverlay::PrivateData
 
  108     void resetRgbaBuffer()
 
  112             std::free( rgbaBuffer );
 
  129     m_data = 
new PrivateData;
 
  131     setAttribute( Qt::WA_TransparentForMouseEvents );
 
  132     setAttribute( Qt::WA_NoSystemBackground );
 
  133     setFocusPolicy( Qt::NoFocus );
 
  137         resize( widget->size() );
 
  138         widget->installEventFilter( 
this );
 
  156     if ( mode != m_data->maskMode )
 
  158         m_data->maskMode = mode;
 
  159         m_data->resetRgbaBuffer();
 
  169     return m_data->maskMode;
 
  180     m_data->renderMode = mode;
 
  189     return m_data->renderMode;
 
  201 void QwtWidgetOverlay::updateMask()
 
  203     m_data->resetRgbaBuffer();
 
  217         if ( hint.isEmpty() )
 
  218             hint += QRect( 0, 0, width(), height() );
 
  224         m_data->rgbaBuffer = ( uchar* )::calloc( width() * height(), 4 );
 
  226         QImage image( m_data->rgbaBuffer,
 
  227             width(), height(), qwtMaskImageFormat() );
 
  229         QPainter painter( &image );
 
  233         mask = qwtAlphaMask( image, hint );
 
  238             m_data->resetRgbaBuffer();
 
  247     if ( mask.isEmpty() )
 
  263     const QRegion& clipRegion = 
event->region();
 
  265     QPainter painter( 
this );
 
  267     bool useRgbaBuffer = 
false;
 
  270         useRgbaBuffer = 
true;
 
  274         if ( painter.paintEngine()->type() == QPaintEngine::Raster )
 
  275             useRgbaBuffer = 
true;
 
  278     if ( m_data->rgbaBuffer && useRgbaBuffer )
 
  280         const QImage image( m_data->rgbaBuffer,
 
  281             width(), height(), qwtMaskImageFormat() );
 
  283         const int rectCount = clipRegion.rectCount();
 
  285         if ( rectCount > 2000 )
 
  288             painter.setClipRegion( clipRegion );
 
  290             const QRect r = clipRegion.boundingRect();
 
  291             painter.drawImage( r.topLeft(), image, r );
 
  295 #if QT_VERSION >= 0x050800 
  296             for ( QRegion::const_iterator it = clipRegion.cbegin();
 
  297                 it != clipRegion.cend(); ++it )
 
  299                 const QRect& r = *it;
 
  300                 painter.drawImage( r.topLeft(), image, r );
 
  304             for ( 
int i = 0; i < rects.size(); i++ )
 
  306                 const QRect& r = rects[i];
 
  307                 painter.drawImage( r.topLeft(), image, r );
 
  314         painter.setClipRegion( clipRegion );
 
  327     m_data->resetRgbaBuffer();
 
  330 void QwtWidgetOverlay::draw( QPainter* painter )
 const 
  332     if ( QWidget* widget = parentWidget() )
 
  334         painter->setClipRect( widget->contentsRect() );
 
  338         const int idx = widget->metaObject()->indexOfMethod( 
"borderPath(QRect)" );
 
  341             QPainterPath clipPath;
 
  343             ( void )QMetaObject::invokeMethod(
 
  344                 widget, 
"borderPath", Qt::DirectConnection,
 
  345                 Q_RETURN_ARG( QPainterPath, clipPath ), Q_ARG( QRect, rect() ) );
 
  347             if (!clipPath.isEmpty() )
 
  348                 painter->setClipPath( clipPath, Qt::IntersectClip );
 
  391     if ( 
object == parent() && event->type() == QEvent::Resize )
 
  393         QResizeEvent* 
resizeEvent = 
static_cast< QResizeEvent* 
>( event );
 
  397     return QObject::eventFilter( 
object, event );
 
static bool isX11GraphicsSystem()