📄 pageviewutils.cpp.svn-base
字号:
setAttribute( Qt::WA_OpaquePaintEvent, true ); // initialize values of the private data storage structure d->anchorWidget = anchorWidget; d->anchorSide = Left; d->hiding = false; // create the animation timer d->animTimer = new QTimer( this ); connect( d->animTimer, SIGNAL( timeout() ), this, SLOT( slotAnimate() ) ); // apply a filter to get notified when anchor changes geometry d->anchorWidget->installEventFilter( this );}PageViewToolBar::~PageViewToolBar(){ // delete the private data storage structure delete d;}void PageViewToolBar::showItems( Side side, const QLinkedList<ToolBarItem> & items ){ // set parameters for sliding in d->anchorSide = side; d->hiding = false; // delete buttons if already present if ( !d->buttons.isEmpty() ) { QLinkedList< ToolBarButton * >::iterator it = d->buttons.begin(), end = d->buttons.end(); for ( ; it != end; ++it ) delete *it; d->buttons.clear(); } // create new buttons for given items QLinkedList<ToolBarItem>::const_iterator it = items.begin(), end = items.end(); for ( ; it != end; ++it ) { ToolBarButton * button = new ToolBarButton( this, *it, d->backgroundPixmap ); connect( button, SIGNAL( clicked() ), this, SLOT( slotButtonClicked() ) ); d->buttons.append( button ); } // rebuild toolbar shape and contents buildToolBar(); d->currentPosition = getOuterPoint(); d->endPosition = getInnerPoint(); move( d->currentPosition ); show(); // start scrolling in d->animTimer->start( 20 );}void PageViewToolBar::hideAndDestroy(){ // set parameters for sliding out d->hiding = true; d->endPosition = getOuterPoint(); // start scrolling out d->animTimer->start( 20 );}bool PageViewToolBar::eventFilter( QObject * obj, QEvent * e ){ // if anchorWidget changed geometry reposition toolbar if ( obj == d->anchorWidget && e->type() == QEvent::Resize ) { d->animTimer->stop(); if ( d->hiding ) deleteLater(); else reposition(); } // don't block event return false;}void PageViewToolBar::paintEvent( QPaintEvent * e ){ // paint the internal pixmap over the widget bitBlt( this, e->rect().topLeft(), &d->backgroundPixmap, e->rect() );}void PageViewToolBar::mousePressEvent( QMouseEvent * e ){ // set 'dragging' cursor if ( e->button() == Qt::LeftButton ) setCursor( Qt::SizeAllCursor );}void PageViewToolBar::mouseMoveEvent( QMouseEvent * e ){ if ( e->state() != Qt::LeftButton ) return; // compute the nearest side to attach the widget to QPoint parentPos = mapToParent( e->pos() ); float nX = (float)parentPos.x() / (float)d->anchorWidget->width(), nY = (float)parentPos.y() / (float)d->anchorWidget->height(); if ( nX > 0.3 && nX < 0.7 && nY > 0.3 && nY < 0.7 ) return; bool LT = nX < (1.0 - nY); bool LB = nX < (nY); Side side = LT ? ( LB ? Left : Top ) : ( LB ? Bottom : Right ); // check if side changed if ( side == d->anchorSide ) return; d->anchorSide = side; reposition(); emit orientationChanged( (int)side );}void PageViewToolBar::mouseReleaseEvent( QMouseEvent * e ){ // set normal cursor if ( e->button() == Qt::LeftButton ) setCursor( Qt::ArrowCursor );}void PageViewToolBar::buildToolBar(){ int buttonsNumber = d->buttons.count(), parentWidth = d->anchorWidget->width(), parentHeight = d->anchorWidget->height(), myCols = 1, myRows = 1; // 1. find out columns and rows we're going to use bool topLeft = d->anchorSide == Left || d->anchorSide == Top; bool vertical = d->anchorSide == Left || d->anchorSide == Right; if ( vertical ) { myCols = 1 + (buttonsNumber * toolBarGridSize) / (parentHeight - toolBarGridSize); myRows = (int)ceil( (float)buttonsNumber / (float)myCols ); } else { myRows = 1 + (buttonsNumber * toolBarGridSize) / (parentWidth - toolBarGridSize); myCols = (int)ceil( (float)buttonsNumber / (float)myRows ); } // 2. compute widget size (from rows/cols) int myWidth = myCols * toolBarGridSize, myHeight = myRows * toolBarGridSize, xOffset = (toolBarGridSize - ToolBarButton::buttonSize) / 2, yOffset = (toolBarGridSize - ToolBarButton::buttonSize) / 2; if ( vertical ) { myHeight += 16; myWidth += 4; yOffset += 12; if ( d->anchorSide == Right ) xOffset += 4; } else { myWidth += 16; myHeight += 4; xOffset += 12; if ( d->anchorSide == Bottom ) yOffset += 4; } bool prevUpdates = updatesEnabled(); setUpdatesEnabled( false ); // 3. resize pixmap, mask and widget static QBitmap mask; mask = QBitmap( myWidth + 1, myHeight + 1 ); d->backgroundPixmap = QPixmap( myWidth + 1, myHeight + 1 ); resize( myWidth + 1, myHeight + 1 ); // 4. create and set transparency mask QPainter maskPainter( &mask); mask.fill( Qt::white ); maskPainter.setBrush( Qt::black ); if ( vertical ) maskPainter.drawRoundRect( topLeft ? -10 : 0, 0, myWidth + 10, myHeight, 2000 / (myWidth + 10), 2000 / myHeight ); else maskPainter.drawRoundRect( 0, topLeft ? -10 : 0, myWidth, myHeight + 10, 2000 / myWidth, 2000 / (myHeight + 10) ); setMask( mask ); // 5. draw background QPainter bufferPainter( &d->backgroundPixmap ); QPalette pal = palette(); // 5.1. draw horizontal/vertical gradient QColor fromColor = topLeft ? pal.color( QPalette::Active, QPalette::Button ) : pal.color( QPalette::Active, QPalette::Light ); QColor toColor = topLeft ? pal.color( QPalette::Active, QPalette::Light ) : pal.color( QPalette::Active, QPalette::Button ); QImage gradientPattern = KImageEffect::gradient( vertical ? QSize( myWidth, 1) : QSize( 1, myHeight ), fromColor, toColor, vertical ? KImageEffect::HorizontalGradient : KImageEffect::VerticalGradient ); bufferPainter.drawTiledPixmap( 0, 0, myWidth, myHeight, QPixmap::fromImage(gradientPattern) ); // 5.2. draw rounded border bufferPainter.setPen( pal.color( QPalette::Active, QPalette::Dark ) ); if ( vertical ) bufferPainter.drawRoundRect( topLeft ? -10 : 0, 0, myWidth + 10, myHeight, 2000 / (myWidth + 10), 2000 / myHeight ); else bufferPainter.drawRoundRect( 0, topLeft ? -10 : 0, myWidth, myHeight + 10, 2000 / myWidth, 2000 / (myHeight + 10) ); // 5.3. draw handle bufferPainter.setPen( pal.color( QPalette::Active, QPalette::Mid ) ); if ( vertical ) { int dx = d->anchorSide == Left ? 2 : 4; bufferPainter.drawLine( dx, 6, dx + myWidth - 8, 6 ); bufferPainter.drawLine( dx, 9, dx + myWidth - 8, 9 ); bufferPainter.setPen( pal.color( QPalette::Active, QPalette::Light ) ); bufferPainter.drawLine( dx + 1, 7, dx + myWidth - 7, 7 ); bufferPainter.drawLine( dx + 1, 10, dx + myWidth - 7, 10 ); } else { int dy = d->anchorSide == Top ? 2 : 4; bufferPainter.drawLine( 6, dy, 6, dy + myHeight - 8 ); bufferPainter.drawLine( 9, dy, 9, dy + myHeight - 8 ); bufferPainter.setPen( pal.color( QPalette::Active, QPalette::Light ) ); bufferPainter.drawLine( 7, dy + 1, 7, dy + myHeight - 7 ); bufferPainter.drawLine( 10, dy + 1, 10, dy + myHeight - 7 ); } // 6. reposition buttons (in rows/col grid) int gridX = 0, gridY = 0; QLinkedList< ToolBarButton * >::iterator it = d->buttons.begin(), end = d->buttons.end(); for ( ; it != end; ++it ) { ToolBarButton * button = *it; button->move( gridX * toolBarGridSize + xOffset, gridY * toolBarGridSize + yOffset ); if ( ++gridX == myCols ) { gridX = 0; gridY++; } } setUpdatesEnabled( prevUpdates );}void PageViewToolBar::reposition(){ // note: hiding widget here will gives better gfx, but ends drag operation // rebuild widget and move it to its final place buildToolBar(); d->currentPosition = getInnerPoint(); move( d->currentPosition ); // repaint all buttons (to update background) QLinkedList< ToolBarButton * >::iterator it = d->buttons.begin(), end = d->buttons.end(); for ( ; it != end; ++it ) (*it)->update();}QPoint PageViewToolBar::getInnerPoint(){ // returns the final position of the widget if ( d->anchorSide == Left ) return QPoint( 0, (d->anchorWidget->height() - height()) / 2 ); if ( d->anchorSide == Top ) return QPoint( (d->anchorWidget->width() - width()) / 2, 0 ); if ( d->anchorSide == Right ) return QPoint( d->anchorWidget->width() - width() + toolBarRBMargin, (d->anchorWidget->height() - height()) / 2 ); return QPoint( (d->anchorWidget->width() - width()) / 2, d->anchorWidget->height() - height() + toolBarRBMargin );}QPoint PageViewToolBar::getOuterPoint(){ // returns the point from which the transition starts if ( d->anchorSide == Left ) return QPoint( -width(), (d->anchorWidget->height() - height()) / 2 ); if ( d->anchorSide == Top ) return QPoint( (d->anchorWidget->width() - width()) / 2, -height() ); if ( d->anchorSide == Right ) return QPoint( d->anchorWidget->width() + toolBarRBMargin, (d->anchorWidget->height() - height()) / 2 ); return QPoint( (d->anchorWidget->width() - width()) / 2, d->anchorWidget->height() + toolBarRBMargin );}void PageViewToolBar::slotAnimate(){ // move currentPosition towards endPosition int dX = d->endPosition.x() - d->currentPosition.x(), dY = d->endPosition.y() - d->currentPosition.y(); dX = dX / 6 + qMax( -1, qMin( 1, dX) ); dY = dY / 6 + qMax( -1, qMin( 1, dY) ); d->currentPosition.setX( d->currentPosition.x() + dX ); d->currentPosition.setY( d->currentPosition.y() + dY ); // move the widget move( d->currentPosition ); // handle arrival to the end if ( d->currentPosition == d->endPosition ) { d->animTimer->stop(); if ( d->hiding ) deleteLater(); }}void PageViewToolBar::slotButtonClicked(){ ToolBarButton * button = qobject_cast<ToolBarButton *>( sender() ); if ( button ) { // deselect other buttons QLinkedList< ToolBarButton * >::iterator it = d->buttons.begin(), end = d->buttons.end(); for ( ; it != end; ++it ) if ( *it != button ) (*it)->setChecked( false ); // emit signal (-1 if button has been unselected) emit toolSelected( button->isChecked() ? button->buttonID() : -1 ); }}#include "pageviewutils.moc"
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -