Commit 4f3b163b authored by shibakaneki's avatar shibakaneki

Implemented the desktop mode for Linux

parent 80ceb222
......@@ -13,882 +13,882 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#include "UBBoardView.h"
#include <QtGui>
#include "UBDrawingController.h"
#include "frameworks/UBGeometryUtils.h"
#include "core/UBSettings.h"
#include "core/UBMimeData.h"
#include "core/UBApplication.h"
#include "core/UBSetting.h"
#include "core/UBPersistenceManager.h"
#include "network/UBHttpGet.h"
#include "gui/UBStylusPalette.h"
#include "gui/UBRubberBand.h"
#include "gui/UBToolWidget.h"
#include "gui/UBResources.h"
#include "gui/UBMainWindow.h"
#include "board/UBBoardController.h"
#include "domain/UBGraphicsTextItem.h"
#include "domain/UBGraphicsPixmapItem.h"
#include "domain/UBGraphicsWidgetItem.h"
#include "domain/UBItem.h"
#include "document/UBDocumentProxy.h"
#include "../gui/UBThumbnailWidget.h"
#include "frameworks/UBPlatformUtils.h"
#include "core/memcheck.h"
UBBoardView::UBBoardView (UBBoardController* pController, QWidget* pParent)
: QGraphicsView (pParent)
, mController (pController)
, mIsCreatingTextZone (false)
, mIsCreatingSceneGrabZone (false)
{
init ();
mFilterZIndex = false;
}
UBBoardView::UBBoardView (UBBoardController* pController, int pStartLayer, int pEndLayer, QWidget* pParent)
: QGraphicsView (pParent)
, mController (pController)
{
init ();
mStartLayer = pStartLayer;
mEndLayer = pEndLayer;
mFilterZIndex = true;
}
UBBoardView::~UBBoardView () {
//NOOP
}
void
UBBoardView::init ()
{
connect (UBSettings::settings ()->boardPenPressureSensitive, SIGNAL (changed (QVariant)),
this, SLOT (settingChanged (QVariant)));
connect (UBSettings::settings ()->boardMarkerPressureSensitive, SIGNAL (changed (QVariant)),
this, SLOT (settingChanged (QVariant)));
connect (UBSettings::settings ()->boardUseHighResTabletEvent, SIGNAL (changed (QVariant)),
this, SLOT (settingChanged (QVariant)));
setWindowFlags (Qt::FramelessWindowHint);
setFrameStyle (QFrame::NoFrame);
setRenderHints (QPainter::Antialiasing | QPainter::SmoothPixmapTransform | QPainter::TextAntialiasing);
setVerticalScrollBarPolicy (Qt::ScrollBarAlwaysOff);
setHorizontalScrollBarPolicy (Qt::ScrollBarAlwaysOff);
setAcceptDrops (true);
setOptimizationFlag (QGraphicsView::IndirectPainting); // enable UBBoardView::drawItems filter
mTabletStylusIsPressed = false;
mMouseButtonIsPressed = false;
mPendingStylusReleaseEvent = false;
setCacheMode (QGraphicsView::CacheBackground);
mUsingTabletEraser = false;
mIsCreatingTextZone = false;
mRubberBand = 0;
mVirtualKeyboardActive = false;
settingChanged (QVariant ());
unsetCursor();
}
UBGraphicsScene*
UBBoardView::scene ()
{
return qobject_cast<UBGraphicsScene*> (QGraphicsView::scene ());
}
void
UBBoardView::hideEvent (QHideEvent * event)
{
Q_UNUSED (event);
emit hidden ();
}
void
UBBoardView::showEvent (QShowEvent * event)
{
Q_UNUSED (event);
emit shown ();
}
void
UBBoardView::keyPressEvent (QKeyEvent *event)
{
// send to the scene anyway
QApplication::sendEvent (scene (), event);
if (!event->isAccepted ())
{
switch (event->key ())
{
case Qt::Key_Up:
case Qt::Key_PageUp:
case Qt::Key_Left:
{
mController->previousScene ();
break;
}
case Qt::Key_Down:
case Qt::Key_PageDown:
case Qt::Key_Right:
case Qt::Key_Space:
{
mController->nextScene ();
break;
}
case Qt::Key_Home:
{
mController->firstScene ();
break;
}
case Qt::Key_End:
{
mController->lastScene ();
break;
}
case Qt::Key_Insert:
{
mController->addScene ();
break;
}
}
if (event->modifiers () & Qt::ControlModifier) // keep only ctrl/cmd keys
{
switch (event->key ())
{
case Qt::Key_Plus:
case Qt::Key_I:
{
mController->zoomIn ();
event->accept ();
break;
}
case Qt::Key_Minus:
case Qt::Key_O:
{
mController->zoomOut ();
event->accept ();
break;
}
case Qt::Key_0:
{
mController->zoomRestore ();
event->accept ();
break;
}
case Qt::Key_Left:
{
mController->handScroll (-100, 0);
event->accept ();
break;
}
case Qt::Key_Right:
{
mController->handScroll (100, 0);
event->accept ();
break;
}
case Qt::Key_Up:
{
mController->handScroll (0, -100);
event->accept ();
break;
}
case Qt::Key_Down:
{
mController->handScroll (0, 100);
event->accept ();
break;
}
default:
{
// NOOP
}
}
}
}
}
bool
UBBoardView::event (QEvent * e)
{
if (e->type () == QEvent::Gesture)
{
QGestureEvent *gestureEvent = dynamic_cast<QGestureEvent *> (e);
if (gestureEvent)
{
QSwipeGesture* swipe = dynamic_cast<QSwipeGesture*> (gestureEvent->gesture (Qt::SwipeGesture));
if (swipe)
{
if (swipe->horizontalDirection () == QSwipeGesture::Left)
{
mController->previousScene ();
gestureEvent->setAccepted (swipe, true);
}
if (swipe->horizontalDirection () == QSwipeGesture::Right)
{
mController->nextScene ();
gestureEvent->setAccepted (swipe, true);
}
}
}
}
return QGraphicsView::event (e);
}
void
UBBoardView::tabletEvent (QTabletEvent * event)
{
if (!mUseHighResTabletEvent)
{
event->setAccepted (false);
return;
}
UBDrawingController *dc = UBDrawingController::drawingController ();
QPointF tabletPos = UBGeometryUtils::pointConstrainedInRect (event->hiResGlobalPos ()
- mapToGlobal (QPoint (0, 0)), rect ());
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)dc->stylusTool ();
if (event->type () == QEvent::TabletPress || event->type () == QEvent::TabletEnterProximity)
{
if (event->pointerType () == QTabletEvent::Eraser)
{
dc->setStylusTool (UBStylusTool::Eraser);
mUsingTabletEraser = true;
}
else
{
if (mUsingTabletEraser && currentTool == UBStylusTool::Eraser)
{
dc->setStylusTool (dc->latestDrawingTool ());
}
mUsingTabletEraser = false;
}
}
// if event are not Pen events, we drop the tablet stuff and route everything through mouse event
if (currentTool != UBStylusTool::Pen
&& currentTool != UBStylusTool::Line
&& currentTool != UBStylusTool::Marker
&& !mMarkerPressureSensitive)
{
event->setAccepted (false);
return;
}
QPointF scenePos = viewportTransform ().inverted ().map (tabletPos);
qreal pressure = 1.0;
if (((currentTool == UBStylusTool::Pen || currentTool == UBStylusTool::Line)
&& mPenPressureSensitive)
|| (currentTool == UBStylusTool::Marker && mMarkerPressureSensitive))
{
pressure = event->pressure ();
}
bool acceptEvent = true;
switch (event->type ())
{
case QEvent::TabletPress:
{
mTabletStylusIsPressed = true;
scene ()->inputDevicePress (scenePos, pressure);
break;
}
case QEvent::TabletMove:
{
if (mTabletStylusIsPressed)
{
scene ()->inputDeviceMove (scenePos, pressure);
}
acceptEvent = false; // rerouted to mouse move
break;
}
case QEvent::TabletRelease:
{
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)dc->stylusTool ();
scene ()->setToolCursor (currentTool);
setToolCursor (currentTool);
scene ()->inputDeviceRelease ();
mPendingStylusReleaseEvent = false;
mTabletStylusIsPressed = false;
mMouseButtonIsPressed = false;
break;
}
default:
{
//NOOP - avoid compiler warning
}
}
// ignore mouse press and mouse move tablet event so that it is rerouted to mouse events,
// documented in QTabletEvent Class Reference:
/* The event handler QWidget::tabletEvent() receives all three types of tablet events.
Qt will first send a tabletEvent then, if it is not accepted, it will send a mouse event. */
//
// This is a workaround to the fact that tablet event are not delivered to child widget (like palettes)
//
event->setAccepted (acceptEvent);
}
void
UBBoardView::mousePressEvent (QMouseEvent *event)
{
if (isAbsurdPoint (event->pos ()))
{
event->accept ();
return;
}
mMouseDownPos = event->pos ();
if (event->button () == Qt::LeftButton && isInteractive ())
{
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)UBDrawingController::drawingController ()->stylusTool ();
if (!mTabletStylusIsPressed)
mMouseButtonIsPressed = true;
if (currentTool == UBStylusTool::ZoomIn)
{
mController->zoomIn (mapToScene (event->pos ()));
event->accept ();
}
else if (currentTool == UBStylusTool::ZoomOut)
{
mController->zoomOut (mapToScene (event->pos ()));
event->accept ();
}
else if (currentTool == UBStylusTool::Hand)
{
viewport ()->setCursor (QCursor (Qt::ClosedHandCursor));
mPreviousPoint = event->posF ();
event->accept ();
}
else if (currentTool == UBStylusTool::Selector)
{
QGraphicsView::mousePressEvent (event);
}
else if (currentTool == UBStylusTool::Text)
{
int frameWidth = UBSettings::settings ()->objectFrameWidth;
QRectF fuzzyRect (0, 0, frameWidth * 4, frameWidth * 4);
fuzzyRect.moveCenter (mapToScene (mMouseDownPos));
UBGraphicsTextItem* foundTextItem = 0;
QListIterator<QGraphicsItem *> it (scene ()->items (fuzzyRect));
while (it.hasNext () && !foundTextItem)
{
foundTextItem = qgraphicsitem_cast<UBGraphicsTextItem*>(it.next ());
}
if (foundTextItem)
{
mIsCreatingTextZone = false;
QGraphicsView::mousePressEvent (event);
}
else
{
scene ()->deselectAllItems ();
if (!mRubberBand)
mRubberBand = new UBRubberBand (QRubberBand::Rectangle, this);
mRubberBand->setGeometry (QRect (mMouseDownPos, QSize ()));
mRubberBand->show ();
mIsCreatingTextZone = true;
event->accept ();
}
}
else if (currentTool == UBStylusTool::Capture)
{
scene ()->deselectAllItems ();
if (!mRubberBand)
mRubberBand = new UBRubberBand (QRubberBand::Rectangle, this);
mRubberBand->setGeometry (QRect (mMouseDownPos, QSize ()));
mRubberBand->show ();
mIsCreatingSceneGrabZone = true;
event->accept ();
}
else
{
if(UBDrawingController::drawingController()->mActiveRuler==NULL)
{
viewport()->setCursor (QCursor (Qt::BlankCursor));
}
if (scene () && !mTabletStylusIsPressed)
{
scene ()->inputDevicePress (mapToScene (UBGeometryUtils::pointConstrainedInRect (event->pos (), rect ())));
}
event->accept ();
}
}
}
void
UBBoardView::mouseMoveEvent (QMouseEvent *event)
{
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)UBDrawingController::drawingController ()->stylusTool ();
if (isAbsurdPoint (event->pos ()))
{
event->accept ();
return;
}
if (currentTool == UBStylusTool::Hand && (mMouseButtonIsPressed || mTabletStylusIsPressed))
{
QPointF eventPosition = event->posF ();
qreal dx = eventPosition.x () - mPreviousPoint.x ();
qreal dy = eventPosition.y () - mPreviousPoint.y ();
mController->handScroll (dx, dy);
mPreviousPoint = eventPosition;
event->accept ();
}
else if (currentTool == UBStylusTool::Selector)
{
QGraphicsView::mouseMoveEvent (event);
}
else if ((UBDrawingController::drawingController()->isDrawingTool())
&& !mMouseButtonIsPressed)
{
QGraphicsView::mouseMoveEvent (event);
}
else if (currentTool == UBStylusTool::Text || currentTool == UBStylusTool::Capture)
{
if (mRubberBand && (mIsCreatingTextZone || mIsCreatingSceneGrabZone))
{
mRubberBand->setGeometry (QRect (mMouseDownPos, event->pos ()).normalized ());
event->accept ();
}
else
{
QGraphicsView::mouseMoveEvent (event);
}
}
else
{
if (!mTabletStylusIsPressed && scene ())
{
scene ()->inputDeviceMove (mapToScene (UBGeometryUtils::pointConstrainedInRect (event->pos (), rect ())), mMouseButtonIsPressed);
}
event->accept ();
}
}
void
UBBoardView::mouseReleaseEvent (QMouseEvent *event)
{
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)UBDrawingController::drawingController ()->stylusTool ();
scene ()->setToolCursor (currentTool);
setToolCursor (currentTool);
// first propagate device release to the scene
if (scene ())
scene ()->inputDeviceRelease ();
if (currentTool == UBStylusTool::Selector)
{
QGraphicsView::mouseReleaseEvent (event);
}
else if (currentTool == UBStylusTool::Text)
{
if (mRubberBand)
mRubberBand->hide ();
if (scene () && mRubberBand && mIsCreatingTextZone)
{
QRect rubberRect = mRubberBand->geometry ();
UBGraphicsTextItem* textItem = scene ()->addText ("", mapToScene (rubberRect.topLeft ()));
event->accept ();
UBDrawingController::drawingController ()->setStylusTool (UBStylusTool::Selector);
textItem->setSelected (true);
}
else
{
QGraphicsView::mouseReleaseEvent (event);
}
mIsCreatingTextZone = false;
}
else if (currentTool == UBStylusTool::Capture)
{
if (mRubberBand)
mRubberBand->hide ();
if (scene () && mRubberBand && mIsCreatingSceneGrabZone && mRubberBand->geometry ().width () > 16)
{
QRect rect = mRubberBand->geometry ();
QPointF sceneTopLeft = mapToScene (rect.topLeft ());
QPointF sceneBottomRight = mapToScene (rect.bottomRight ());
QRectF sceneRect (sceneTopLeft, sceneBottomRight);
mController->grabScene (sceneRect);
event->accept ();
}
else
{
QGraphicsView::mouseReleaseEvent (event);
}
mIsCreatingSceneGrabZone = false;
}
else
{
if (mPendingStylusReleaseEvent || mMouseButtonIsPressed)
{
event->accept ();
}
}
mMouseButtonIsPressed = false;
mPendingStylusReleaseEvent = false;
mTabletStylusIsPressed = false;
}
void
UBBoardView::forcedTabletRelease ()
{
if (mMouseButtonIsPressed || mTabletStylusIsPressed || mPendingStylusReleaseEvent)
{
qWarning () << "dirty mouse/tablet state:";
qWarning () << "mMouseButtonIsPressed =" << mMouseButtonIsPressed;
qWarning () << "mTabletStylusIsPressed = " << mTabletStylusIsPressed;
qWarning () << "mPendingStylusReleaseEvent" << mPendingStylusReleaseEvent;
qWarning () << "forcing device release";
scene ()->inputDeviceRelease ();
mMouseButtonIsPressed = false;
mTabletStylusIsPressed = false;
mPendingStylusReleaseEvent = false;
}
}
void
UBBoardView::mouseDoubleClickEvent (QMouseEvent *event)
{
// We don't want a double click, we want two clicks
mousePressEvent (event);
}
void
UBBoardView::wheelEvent (QWheelEvent *event)
{
if (isInteractive () && event->orientation () == Qt::Vertical)
{
// Too many wheelEvent are sent, how should we handle them to "smoothly" zoom ?
// something like zoom( pow(zoomFactor, event->delta() / 120) )
}
event->accept ();
}
void
UBBoardView::leaveEvent (QEvent * event)
{
if (scene ())
scene ()->leaveEvent (event);
QGraphicsView::leaveEvent (event);
}
void
UBBoardView::drawItems (QPainter *painter, int numItems,
QGraphicsItem* items[],
const QStyleOptionGraphicsItem options[])
{
if (!mFilterZIndex)
{
QGraphicsView::drawItems (painter, numItems, items, options);
}
else
{
int count = 0;
QGraphicsItem** itemsFiltered = new QGraphicsItem*[numItems];
QStyleOptionGraphicsItem *optionsFiltered = new QStyleOptionGraphicsItem[numItems];
for (int i = 0; i < numItems; i++)
{
if (shouldDisplayItem (items[i]))
{
itemsFiltered[count] = items[i];
optionsFiltered[count] = options[i];
count++;
}
}
QGraphicsView::drawItems (painter, count, itemsFiltered, optionsFiltered);
delete[] optionsFiltered;
delete[] itemsFiltered;
}
}
void
UBBoardView::dragEnterEvent (QDragEnterEvent *event)
{
// TODO UB 4.x be smarter with drag accept code .... we cannot handle everything ...
event->acceptProposedAction ();
}
void
UBBoardView::dragMoveEvent (QDragMoveEvent *event)
{
event->acceptProposedAction ();
}
void
UBBoardView::dropEvent (QDropEvent *event)
{
if(!event->source() || dynamic_cast<UBThumbnailWidget *>(event->source()))
{
mController->processMimeData (event->mimeData (), mapToScene (event->pos ()));
event->acceptProposedAction ();
}
}
void
UBBoardView::resizeEvent (QResizeEvent * event)
{
const qreal maxWidth = width () * 10;
const qreal maxHeight = height () * 10;
setSceneRect (-(maxWidth / 2), -(maxHeight / 2), maxWidth, maxHeight);
centerOn (0, 0);
emit resized (event);
}
void
UBBoardView::drawBackground (QPainter *painter, const QRectF &rect)
{
if (testAttribute (Qt::WA_TranslucentBackground))
{
QGraphicsView::drawBackground (painter, rect);
return;
}
bool darkBackground = scene () && scene ()->isDarkBackground ();
if (darkBackground)
{
painter->fillRect (rect, QBrush (QColor (Qt::black)));
}
else
{
painter->fillRect (rect, QBrush (QColor (Qt::white)));
}
if (transform ().m11 () > 0.5)
{
QColor bgCrossColor;
if (darkBackground)
bgCrossColor = UBSettings::crossDarkBackground;
else
bgCrossColor = UBSettings::crossLightBackground;
if (transform ().m11 () < 1.0)
{
int alpha = 255 * transform ().m11 () / 2;
bgCrossColor.setAlpha (alpha); // fade the crossing on small zooms
}
painter->setPen (bgCrossColor);
if (scene () && scene ()->isCrossedBackground ())
{
qreal firstY = ((int) (rect.y () / UBSettings::crossSize)) * UBSettings::crossSize;
for (qreal yPos = firstY; yPos < rect.y () + rect.height (); yPos += UBSettings::crossSize)
{
painter->drawLine (rect.x (), yPos, rect.x () + rect.width (), yPos);
}
qreal firstX = ((int) (rect.x () / UBSettings::crossSize)) * UBSettings::crossSize;
for (qreal xPos = firstX; xPos < rect.x () + rect.width (); xPos += UBSettings::crossSize)
{
painter->drawLine (xPos, rect.y (), xPos, rect.y () + rect.height ());
}
}
}
if (!mFilterZIndex && scene ())
{
QSize pageNominalSize = scene ()->nominalSize ();
if (pageNominalSize.isValid ())
{
qreal penWidth = 8.0 / transform ().m11 ();
QRectF pageRect (pageNominalSize.width () / -2, pageNominalSize.height () / -2
, pageNominalSize.width (), pageNominalSize.height ());
pageRect.adjust (-penWidth / 2, -penWidth / 2, penWidth / 2, penWidth / 2);
QColor docSizeColor;
if (darkBackground)
docSizeColor = UBSettings::documentSizeMarkColorDarkBackground;
else
docSizeColor = UBSettings::documentSizeMarkColorLightBackground;
QPen pen (docSizeColor);
pen.setWidth (penWidth);
painter->setPen (pen);
painter->drawRect (pageRect);
}
}
}
void
UBBoardView::settingChanged (QVariant newValue)
{
Q_UNUSED (newValue);
mPenPressureSensitive = UBSettings::settings ()->boardPenPressureSensitive->get ().toBool ();
mMarkerPressureSensitive = UBSettings::settings ()->boardMarkerPressureSensitive->get ().toBool ();
mUseHighResTabletEvent = UBSettings::settings ()->boardUseHighResTabletEvent->get ().toBool ();
}
void UBBoardView::virtualKeyboardActivated(bool b)
{
UBPlatformUtils::setWindowNonActivableFlag(this, b);
mVirtualKeyboardActive = b;
setInteractive(!b);
}
// Apple remote desktop sends funny events when the transmission is bad
bool
UBBoardView::isAbsurdPoint (QPoint point)
{
QDesktopWidget *desktop = qApp->desktop ();
bool isValidPoint = false;
for (int i = 0; i < desktop->numScreens (); i++)
{
QRect screenRect = desktop->screenGeometry (i);
isValidPoint = isValidPoint || screenRect.contains (point);
}
return !isValidPoint;
}
void
UBBoardView::focusOutEvent (QFocusEvent * event)
{
Q_UNUSED (event);
}
void
UBBoardView::setToolCursor (int tool)
{
QWidget *controlViewport = viewport ();
switch (tool)
{
case UBStylusTool::Pen:
controlViewport->setCursor (UBResources::resources ()->penCursor);
break;
case UBStylusTool::Eraser:
controlViewport->setCursor (UBResources::resources ()->eraserCursor);
break;
case UBStylusTool::Marker:
controlViewport->setCursor (UBResources::resources ()->markerCursor);
break;
case UBStylusTool::Pointer:
controlViewport->setCursor (UBResources::resources ()->pointerCursor);
break;
case UBStylusTool::Hand:
controlViewport->setCursor (UBResources::resources ()->handCursor);
break;
case UBStylusTool::ZoomIn:
controlViewport->setCursor (UBResources::resources ()->zoomInCursor);
break;
case UBStylusTool::ZoomOut:
controlViewport->setCursor (UBResources::resources ()->zoomOutCursor);
break;
case UBStylusTool::Selector:
controlViewport->setCursor (UBResources::resources ()->arrowCursor);
break;
case UBStylusTool::Line:
controlViewport->setCursor (UBResources::resources ()->penCursor);
break;
case UBStylusTool::Text:
controlViewport->setCursor (UBResources::resources ()->textCursor);
break;
case UBStylusTool::Capture:
controlViewport->setCursor (UBResources::resources ()->penCursor);
break;
default:
Q_ASSERT (false);
//failsafe
controlViewport->setCursor (UBResources::resources ()->penCursor);
}
}
#include "UBBoardView.h"
#include <QtGui>
#include "UBDrawingController.h"
#include "frameworks/UBGeometryUtils.h"
#include "core/UBSettings.h"
#include "core/UBMimeData.h"
#include "core/UBApplication.h"
#include "core/UBSetting.h"
#include "core/UBPersistenceManager.h"
#include "network/UBHttpGet.h"
#include "gui/UBStylusPalette.h"
#include "gui/UBRubberBand.h"
#include "gui/UBToolWidget.h"
#include "gui/UBResources.h"
#include "gui/UBMainWindow.h"
#include "board/UBBoardController.h"
#include "domain/UBGraphicsTextItem.h"
#include "domain/UBGraphicsPixmapItem.h"
#include "domain/UBGraphicsWidgetItem.h"
#include "domain/UBItem.h"
#include "document/UBDocumentProxy.h"
#include "../gui/UBThumbnailWidget.h"
#include "frameworks/UBPlatformUtils.h"
#include "core/memcheck.h"
UBBoardView::UBBoardView (UBBoardController* pController, QWidget* pParent)
: QGraphicsView (pParent)
, mController (pController)
, mIsCreatingTextZone (false)
, mIsCreatingSceneGrabZone (false)
{
init ();
mFilterZIndex = false;
}
UBBoardView::UBBoardView (UBBoardController* pController, int pStartLayer, int pEndLayer, QWidget* pParent)
: QGraphicsView (pParent)
, mController (pController)
{
init ();
mStartLayer = pStartLayer;
mEndLayer = pEndLayer;
mFilterZIndex = true;
}
UBBoardView::~UBBoardView () {
//NOOP
}
void
UBBoardView::init ()
{
connect (UBSettings::settings ()->boardPenPressureSensitive, SIGNAL (changed (QVariant)),
this, SLOT (settingChanged (QVariant)));
connect (UBSettings::settings ()->boardMarkerPressureSensitive, SIGNAL (changed (QVariant)),
this, SLOT (settingChanged (QVariant)));
connect (UBSettings::settings ()->boardUseHighResTabletEvent, SIGNAL (changed (QVariant)),
this, SLOT (settingChanged (QVariant)));
setWindowFlags (Qt::FramelessWindowHint);
setFrameStyle (QFrame::NoFrame);
setRenderHints (QPainter::Antialiasing | QPainter::SmoothPixmapTransform | QPainter::TextAntialiasing);
setVerticalScrollBarPolicy (Qt::ScrollBarAlwaysOff);
setHorizontalScrollBarPolicy (Qt::ScrollBarAlwaysOff);
setAcceptDrops (true);
setOptimizationFlag (QGraphicsView::IndirectPainting); // enable UBBoardView::drawItems filter
mTabletStylusIsPressed = false;
mMouseButtonIsPressed = false;
mPendingStylusReleaseEvent = false;
setCacheMode (QGraphicsView::CacheBackground);
mUsingTabletEraser = false;
mIsCreatingTextZone = false;
mRubberBand = 0;
mVirtualKeyboardActive = false;
settingChanged (QVariant ());
unsetCursor();
}
UBGraphicsScene*
UBBoardView::scene ()
{
return qobject_cast<UBGraphicsScene*> (QGraphicsView::scene ());
}
void
UBBoardView::hideEvent (QHideEvent * event)
{
Q_UNUSED (event);
emit hidden ();
}
void
UBBoardView::showEvent (QShowEvent * event)
{
Q_UNUSED (event);
emit shown ();
}
void
UBBoardView::keyPressEvent (QKeyEvent *event)
{
// send to the scene anyway
QApplication::sendEvent (scene (), event);
if (!event->isAccepted ())
{
switch (event->key ())
{
case Qt::Key_Up:
case Qt::Key_PageUp:
case Qt::Key_Left:
{
mController->previousScene ();
break;
}
case Qt::Key_Down:
case Qt::Key_PageDown:
case Qt::Key_Right:
case Qt::Key_Space:
{
mController->nextScene ();
break;
}
case Qt::Key_Home:
{
mController->firstScene ();
break;
}
case Qt::Key_End:
{
mController->lastScene ();
break;
}
case Qt::Key_Insert:
{
mController->addScene ();
break;
}
}
if (event->modifiers () & Qt::ControlModifier) // keep only ctrl/cmd keys
{
switch (event->key ())
{
case Qt::Key_Plus:
case Qt::Key_I:
{
mController->zoomIn ();
event->accept ();
break;
}
case Qt::Key_Minus:
case Qt::Key_O:
{
mController->zoomOut ();
event->accept ();
break;
}
case Qt::Key_0:
{
mController->zoomRestore ();
event->accept ();
break;
}
case Qt::Key_Left:
{
mController->handScroll (-100, 0);
event->accept ();
break;
}
case Qt::Key_Right:
{
mController->handScroll (100, 0);
event->accept ();
break;
}
case Qt::Key_Up:
{
mController->handScroll (0, -100);
event->accept ();
break;
}
case Qt::Key_Down:
{
mController->handScroll (0, 100);
event->accept ();
break;
}
default:
{
// NOOP
}
}
}
}
}
bool
UBBoardView::event (QEvent * e)
{
if (e->type () == QEvent::Gesture)
{
QGestureEvent *gestureEvent = dynamic_cast<QGestureEvent *> (e);
if (gestureEvent)
{
QSwipeGesture* swipe = dynamic_cast<QSwipeGesture*> (gestureEvent->gesture (Qt::SwipeGesture));
if (swipe)
{
if (swipe->horizontalDirection () == QSwipeGesture::Left)
{
mController->previousScene ();
gestureEvent->setAccepted (swipe, true);
}
if (swipe->horizontalDirection () == QSwipeGesture::Right)
{
mController->nextScene ();
gestureEvent->setAccepted (swipe, true);
}
}
}
}
return QGraphicsView::event (e);
}
void
UBBoardView::tabletEvent (QTabletEvent * event)
{
if (!mUseHighResTabletEvent)
{
event->setAccepted (false);
return;
}
UBDrawingController *dc = UBDrawingController::drawingController ();
QPointF tabletPos = UBGeometryUtils::pointConstrainedInRect (event->hiResGlobalPos ()
- mapToGlobal (QPoint (0, 0)), rect ());
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)dc->stylusTool ();
if (event->type () == QEvent::TabletPress || event->type () == QEvent::TabletEnterProximity)
{
if (event->pointerType () == QTabletEvent::Eraser)
{
dc->setStylusTool (UBStylusTool::Eraser);
mUsingTabletEraser = true;
}
else
{
if (mUsingTabletEraser && currentTool == UBStylusTool::Eraser)
{
dc->setStylusTool (dc->latestDrawingTool ());
}
mUsingTabletEraser = false;
}
}
// if event are not Pen events, we drop the tablet stuff and route everything through mouse event
if (currentTool != UBStylusTool::Pen
&& currentTool != UBStylusTool::Line
&& currentTool != UBStylusTool::Marker
&& !mMarkerPressureSensitive)
{
event->setAccepted (false);
return;
}
QPointF scenePos = viewportTransform ().inverted ().map (tabletPos);
qreal pressure = 1.0;
if (((currentTool == UBStylusTool::Pen || currentTool == UBStylusTool::Line)
&& mPenPressureSensitive)
|| (currentTool == UBStylusTool::Marker && mMarkerPressureSensitive))
{
pressure = event->pressure ();
}
bool acceptEvent = true;
switch (event->type ())
{
case QEvent::TabletPress:
{
mTabletStylusIsPressed = true;
scene ()->inputDevicePress (scenePos, pressure);
break;
}
case QEvent::TabletMove:
{
if (mTabletStylusIsPressed)
{
scene ()->inputDeviceMove (scenePos, pressure);
}
acceptEvent = false; // rerouted to mouse move
break;
}
case QEvent::TabletRelease:
{
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)dc->stylusTool ();
scene ()->setToolCursor (currentTool);
setToolCursor (currentTool);
scene ()->inputDeviceRelease ();
mPendingStylusReleaseEvent = false;
mTabletStylusIsPressed = false;
mMouseButtonIsPressed = false;
break;
}
default:
{
//NOOP - avoid compiler warning
}
}
// ignore mouse press and mouse move tablet event so that it is rerouted to mouse events,
// documented in QTabletEvent Class Reference:
/* The event handler QWidget::tabletEvent() receives all three types of tablet events.
Qt will first send a tabletEvent then, if it is not accepted, it will send a mouse event. */
//
// This is a workaround to the fact that tablet event are not delivered to child widget (like palettes)
//
event->setAccepted (acceptEvent);
}
void
UBBoardView::mousePressEvent (QMouseEvent *event)
{
if (isAbsurdPoint (event->pos ()))
{
event->accept ();
return;
}
mMouseDownPos = event->pos ();
if (event->button () == Qt::LeftButton && isInteractive ())
{
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)UBDrawingController::drawingController ()->stylusTool ();
if (!mTabletStylusIsPressed)
mMouseButtonIsPressed = true;
if (currentTool == UBStylusTool::ZoomIn)
{
mController->zoomIn (mapToScene (event->pos ()));
event->accept ();
}
else if (currentTool == UBStylusTool::ZoomOut)
{
mController->zoomOut (mapToScene (event->pos ()));
event->accept ();
}
else if (currentTool == UBStylusTool::Hand)
{
viewport ()->setCursor (QCursor (Qt::ClosedHandCursor));
mPreviousPoint = event->posF ();
event->accept ();
}
else if (currentTool == UBStylusTool::Selector)
{
QGraphicsView::mousePressEvent (event);
}
else if (currentTool == UBStylusTool::Text)
{
int frameWidth = UBSettings::settings ()->objectFrameWidth;
QRectF fuzzyRect (0, 0, frameWidth * 4, frameWidth * 4);
fuzzyRect.moveCenter (mapToScene (mMouseDownPos));
UBGraphicsTextItem* foundTextItem = 0;
QListIterator<QGraphicsItem *> it (scene ()->items (fuzzyRect));
while (it.hasNext () && !foundTextItem)
{
foundTextItem = qgraphicsitem_cast<UBGraphicsTextItem*>(it.next ());
}
if (foundTextItem)
{
mIsCreatingTextZone = false;
QGraphicsView::mousePressEvent (event);
}
else
{
scene ()->deselectAllItems ();
if (!mRubberBand)
mRubberBand = new UBRubberBand (QRubberBand::Rectangle, this);
mRubberBand->setGeometry (QRect (mMouseDownPos, QSize ()));
mRubberBand->show ();
mIsCreatingTextZone = true;
event->accept ();
}
}
else if (currentTool == UBStylusTool::Capture)
{
scene ()->deselectAllItems ();
if (!mRubberBand)
mRubberBand = new UBRubberBand (QRubberBand::Rectangle, this);
mRubberBand->setGeometry (QRect (mMouseDownPos, QSize ()));
mRubberBand->show ();
mIsCreatingSceneGrabZone = true;
event->accept ();
}
else
{
if(UBDrawingController::drawingController()->mActiveRuler==NULL)
{
viewport()->setCursor (QCursor (Qt::BlankCursor));
}
if (scene () && !mTabletStylusIsPressed)
{
scene ()->inputDevicePress (mapToScene (UBGeometryUtils::pointConstrainedInRect (event->pos (), rect ())));
}
event->accept ();
}
}
}
void
UBBoardView::mouseMoveEvent (QMouseEvent *event)
{
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)UBDrawingController::drawingController ()->stylusTool ();
if (isAbsurdPoint (event->pos ()))
{
event->accept ();
return;
}
if (currentTool == UBStylusTool::Hand && (mMouseButtonIsPressed || mTabletStylusIsPressed))
{
QPointF eventPosition = event->posF ();
qreal dx = eventPosition.x () - mPreviousPoint.x ();
qreal dy = eventPosition.y () - mPreviousPoint.y ();
mController->handScroll (dx, dy);
mPreviousPoint = eventPosition;
event->accept ();
}
else if (currentTool == UBStylusTool::Selector)
{
QGraphicsView::mouseMoveEvent (event);
}
else if ((UBDrawingController::drawingController()->isDrawingTool())
&& !mMouseButtonIsPressed)
{
QGraphicsView::mouseMoveEvent (event);
}
else if (currentTool == UBStylusTool::Text || currentTool == UBStylusTool::Capture)
{
if (mRubberBand && (mIsCreatingTextZone || mIsCreatingSceneGrabZone))
{
mRubberBand->setGeometry (QRect (mMouseDownPos, event->pos ()).normalized ());
event->accept ();
}
else
{
QGraphicsView::mouseMoveEvent (event);
}
}
else
{
if (!mTabletStylusIsPressed && scene ())
{
scene ()->inputDeviceMove (mapToScene (UBGeometryUtils::pointConstrainedInRect (event->pos (), rect ())), mMouseButtonIsPressed);
}
event->accept ();
}
}
void
UBBoardView::mouseReleaseEvent (QMouseEvent *event)
{
UBStylusTool::Enum currentTool = (UBStylusTool::Enum)UBDrawingController::drawingController ()->stylusTool ();
scene ()->setToolCursor (currentTool);
setToolCursor (currentTool);
// first propagate device release to the scene
if (scene ())
scene ()->inputDeviceRelease ();
if (currentTool == UBStylusTool::Selector)
{
QGraphicsView::mouseReleaseEvent (event);
}
else if (currentTool == UBStylusTool::Text)
{
if (mRubberBand)
mRubberBand->hide ();
if (scene () && mRubberBand && mIsCreatingTextZone)
{
QRect rubberRect = mRubberBand->geometry ();
UBGraphicsTextItem* textItem = scene ()->addText ("", mapToScene (rubberRect.topLeft ()));
event->accept ();
UBDrawingController::drawingController ()->setStylusTool (UBStylusTool::Selector);
textItem->setSelected (true);
}
else
{
QGraphicsView::mouseReleaseEvent (event);
}
mIsCreatingTextZone = false;
}
else if (currentTool == UBStylusTool::Capture)
{
if (mRubberBand)
mRubberBand->hide ();
if (scene () && mRubberBand && mIsCreatingSceneGrabZone && mRubberBand->geometry ().width () > 16)
{
QRect rect = mRubberBand->geometry ();
QPointF sceneTopLeft = mapToScene (rect.topLeft ());
QPointF sceneBottomRight = mapToScene (rect.bottomRight ());
QRectF sceneRect (sceneTopLeft, sceneBottomRight);
mController->grabScene (sceneRect);
event->accept ();
}
else
{
QGraphicsView::mouseReleaseEvent (event);
}
mIsCreatingSceneGrabZone = false;
}
else
{
if (mPendingStylusReleaseEvent || mMouseButtonIsPressed)
{
event->accept ();
}
}
mMouseButtonIsPressed = false;
mPendingStylusReleaseEvent = false;
mTabletStylusIsPressed = false;
}
void
UBBoardView::forcedTabletRelease ()
{
if (mMouseButtonIsPressed || mTabletStylusIsPressed || mPendingStylusReleaseEvent)
{
qWarning () << "dirty mouse/tablet state:";
qWarning () << "mMouseButtonIsPressed =" << mMouseButtonIsPressed;
qWarning () << "mTabletStylusIsPressed = " << mTabletStylusIsPressed;
qWarning () << "mPendingStylusReleaseEvent" << mPendingStylusReleaseEvent;
qWarning () << "forcing device release";
scene ()->inputDeviceRelease ();
mMouseButtonIsPressed = false;
mTabletStylusIsPressed = false;
mPendingStylusReleaseEvent = false;
}
}
void
UBBoardView::mouseDoubleClickEvent (QMouseEvent *event)
{
// We don't want a double click, we want two clicks
mousePressEvent (event);
}
void
UBBoardView::wheelEvent (QWheelEvent *event)
{
if (isInteractive () && event->orientation () == Qt::Vertical)
{
// Too many wheelEvent are sent, how should we handle them to "smoothly" zoom ?
// something like zoom( pow(zoomFactor, event->delta() / 120) )
}
event->accept ();
}
void
UBBoardView::leaveEvent (QEvent * event)
{
if (scene ())
scene ()->leaveEvent (event);
QGraphicsView::leaveEvent (event);
}
void
UBBoardView::drawItems (QPainter *painter, int numItems,
QGraphicsItem* items[],
const QStyleOptionGraphicsItem options[])
{
if (!mFilterZIndex)
{
QGraphicsView::drawItems (painter, numItems, items, options);
}
else
{
int count = 0;
QGraphicsItem** itemsFiltered = new QGraphicsItem*[numItems];
QStyleOptionGraphicsItem *optionsFiltered = new QStyleOptionGraphicsItem[numItems];
for (int i = 0; i < numItems; i++)
{
if (shouldDisplayItem (items[i]))
{
itemsFiltered[count] = items[i];
optionsFiltered[count] = options[i];
count++;
}
}
QGraphicsView::drawItems (painter, count, itemsFiltered, optionsFiltered);
delete[] optionsFiltered;
delete[] itemsFiltered;
}
}
void
UBBoardView::dragEnterEvent (QDragEnterEvent *event)
{
// TODO UB 4.x be smarter with drag accept code .... we cannot handle everything ...
event->acceptProposedAction ();
}
void
UBBoardView::dragMoveEvent (QDragMoveEvent *event)
{
event->acceptProposedAction ();
}
void
UBBoardView::dropEvent (QDropEvent *event)
{
if(!event->source() || dynamic_cast<UBThumbnailWidget *>(event->source()))
{
mController->processMimeData (event->mimeData (), mapToScene (event->pos ()));
event->acceptProposedAction ();
}
}
void
UBBoardView::resizeEvent (QResizeEvent * event)
{
const qreal maxWidth = width () * 10;
const qreal maxHeight = height () * 10;
setSceneRect (-(maxWidth / 2), -(maxHeight / 2), maxWidth, maxHeight);
centerOn (0, 0);
emit resized (event);
}
void
UBBoardView::drawBackground (QPainter *painter, const QRectF &rect)
{
if (testAttribute (Qt::WA_TranslucentBackground))
{
QGraphicsView::drawBackground (painter, rect);
return;
}
bool darkBackground = scene () && scene ()->isDarkBackground ();
if (darkBackground)
{
painter->fillRect (rect, QBrush (QColor (Qt::black)));
}
else
{
painter->fillRect (rect, QBrush (QColor (Qt::white)));
}
if (transform ().m11 () > 0.5)
{
QColor bgCrossColor;
if (darkBackground)
bgCrossColor = UBSettings::crossDarkBackground;
else
bgCrossColor = UBSettings::crossLightBackground;
if (transform ().m11 () < 1.0)
{
int alpha = 255 * transform ().m11 () / 2;
bgCrossColor.setAlpha (alpha); // fade the crossing on small zooms
}
painter->setPen (bgCrossColor);
if (scene () && scene ()->isCrossedBackground ())
{
qreal firstY = ((int) (rect.y () / UBSettings::crossSize)) * UBSettings::crossSize;
for (qreal yPos = firstY; yPos < rect.y () + rect.height (); yPos += UBSettings::crossSize)
{
painter->drawLine (rect.x (), yPos, rect.x () + rect.width (), yPos);
}
qreal firstX = ((int) (rect.x () / UBSettings::crossSize)) * UBSettings::crossSize;
for (qreal xPos = firstX; xPos < rect.x () + rect.width (); xPos += UBSettings::crossSize)
{
painter->drawLine (xPos, rect.y (), xPos, rect.y () + rect.height ());
}
}
}
if (!mFilterZIndex && scene ())
{
QSize pageNominalSize = scene ()->nominalSize ();
if (pageNominalSize.isValid ())
{
qreal penWidth = 8.0 / transform ().m11 ();
QRectF pageRect (pageNominalSize.width () / -2, pageNominalSize.height () / -2
, pageNominalSize.width (), pageNominalSize.height ());
pageRect.adjust (-penWidth / 2, -penWidth / 2, penWidth / 2, penWidth / 2);
QColor docSizeColor;
if (darkBackground)
docSizeColor = UBSettings::documentSizeMarkColorDarkBackground;
else
docSizeColor = UBSettings::documentSizeMarkColorLightBackground;
QPen pen (docSizeColor);
pen.setWidth (penWidth);
painter->setPen (pen);
painter->drawRect (pageRect);
}
}
}
void
UBBoardView::settingChanged (QVariant newValue)
{
Q_UNUSED (newValue);
mPenPressureSensitive = UBSettings::settings ()->boardPenPressureSensitive->get ().toBool ();
mMarkerPressureSensitive = UBSettings::settings ()->boardMarkerPressureSensitive->get ().toBool ();
mUseHighResTabletEvent = UBSettings::settings ()->boardUseHighResTabletEvent->get ().toBool ();
}
void UBBoardView::virtualKeyboardActivated(bool b)
{
UBPlatformUtils::setWindowNonActivableFlag(this, b);
mVirtualKeyboardActive = b;
setInteractive(!b);
}
// Apple remote desktop sends funny events when the transmission is bad
bool
UBBoardView::isAbsurdPoint (QPoint point)
{
QDesktopWidget *desktop = qApp->desktop ();
bool isValidPoint = false;
for (int i = 0; i < desktop->numScreens (); i++)
{
QRect screenRect = desktop->screenGeometry (i);
isValidPoint = isValidPoint || screenRect.contains (point);
}
return !isValidPoint;
}
void
UBBoardView::focusOutEvent (QFocusEvent * event)
{
Q_UNUSED (event);
}
void
UBBoardView::setToolCursor (int tool)
{
QWidget *controlViewport = viewport ();
switch (tool)
{
case UBStylusTool::Pen:
controlViewport->setCursor (UBResources::resources ()->penCursor);
break;
case UBStylusTool::Eraser:
controlViewport->setCursor (UBResources::resources ()->eraserCursor);
break;
case UBStylusTool::Marker:
controlViewport->setCursor (UBResources::resources ()->markerCursor);
break;
case UBStylusTool::Pointer:
controlViewport->setCursor (UBResources::resources ()->pointerCursor);
break;
case UBStylusTool::Hand:
controlViewport->setCursor (UBResources::resources ()->handCursor);
break;
case UBStylusTool::ZoomIn:
controlViewport->setCursor (UBResources::resources ()->zoomInCursor);
break;
case UBStylusTool::ZoomOut:
controlViewport->setCursor (UBResources::resources ()->zoomOutCursor);
break;
case UBStylusTool::Selector:
controlViewport->setCursor (UBResources::resources ()->arrowCursor);
break;
case UBStylusTool::Line:
controlViewport->setCursor (UBResources::resources ()->penCursor);
break;
case UBStylusTool::Text:
controlViewport->setCursor (UBResources::resources ()->textCursor);
break;
case UBStylusTool::Capture:
controlViewport->setCursor (UBResources::resources ()->penCursor);
break;
default:
Q_ASSERT (false);
//failsafe
controlViewport->setCursor (UBResources::resources ()->penCursor);
}
}
......@@ -90,6 +90,7 @@ UBDesktopAnnotationController::UBDesktopAnnotationController(QObject *parent)
mKeyboardPalette = UBKeyboardPalette::create(mTransparentDrawingView);
mKeyboardPalette->setParent(mTransparentDrawingView);
connect(mKeyboardPalette, SIGNAL(keyboardActivated(bool)), mTransparentDrawingView, SLOT(virtualKeyboardActivated(bool)));
connect(mKeyboardPalette, SIGNAL(moved(QPoint)), this, SLOT(refreshMask()));
}
connect(mDesktopPalette, SIGNAL(uniboardClick()), this, SLOT(goToUniboard()));
......@@ -143,12 +144,16 @@ UBDesktopAnnotationController::UBDesktopAnnotationController(QObject *parent)
connect(&mHoldTimerMarker, SIGNAL(timeout()), this, SLOT(markerActionReleased()));
connect(&mHoldTimerEraser, SIGNAL(timeout()), this, SLOT(eraserActionReleased()));
connect(mDesktopPalette, SIGNAL(moving()), this, SLOT(refreshMask()));
connect(mLibPalette, SIGNAL(resized()), this, SLOT(refreshMask()));
onDesktopPaletteMaximized();
}
void UBDesktopAnnotationController::showKeyboard(bool show)
{
mKeyboardPalette->setVisible(show);
updateMask(true);
// mDesktopPalette->showVirtualKeyboard(show);
}
......@@ -332,6 +337,10 @@ void UBDesktopAnnotationController::showWindow()
UBPlatformUtils::setDesktopMode(true);
mDesktopPalette->appear();
#ifdef Q_WS_X11
updateMask(true);
#endif
}
......@@ -343,7 +352,15 @@ void UBDesktopAnnotationController::close()
void UBDesktopAnnotationController::stylusToolChanged(int tool)
{
Q_UNUSED(tool);
UBStylusTool::Enum eTool = (UBStylusTool::Enum)tool;
mDesktopPalette->notifySelectorSelection(UBStylusTool::Selector == eTool);
if(UBStylusTool::Selector != eTool)
{
UBApplication::mainWindow->actionVirtualKeyboard->setChecked(false);
mKeyboardPalette->setVisible(false);
}
updateBackground();
}
......@@ -356,6 +373,9 @@ void UBDesktopAnnotationController::updateBackground()
|| UBDrawingController::drawingController()->stylusTool() == UBStylusTool::Selector)
{
newBrush = QBrush(Qt::transparent);
#ifdef Q_WS_X11
updateMask(true);
#endif
}
else
{
......@@ -363,6 +383,9 @@ void UBDesktopAnnotationController::updateBackground()
newBrush = QBrush(QColor(127, 127, 127, 15));
#else
newBrush = QBrush(QColor(127, 127, 127, 1));
#endif
#ifdef Q_WS_X11
updateMask(false);
#endif
}
......@@ -389,6 +412,8 @@ void UBDesktopAnnotationController::goToUniboard()
UBPlatformUtils::setDesktopMode(false);
UBApplication::mainWindow->actionVirtualKeyboard->setEnabled(true);
emit restoreUniboard();
}
......@@ -751,3 +776,83 @@ void UBDesktopAnnotationController::onTransparentWidgetResized()
// qDebug() << "mLibPalette (" << mLibPalette->width() << "," << mLibPalette->height() << ")";
mLibPalette->resize(mLibPalette->width(), mTransparentDrawingView->height());
}
void UBDesktopAnnotationController::updateMask(bool bTransparent)
{
if(bTransparent)
{
// Here we have to generate a new mask. This method is certainly resource
// consuming but for the moment this is the only solution that I found.
mMask = QPixmap(mTransparentDrawingView->width(), mTransparentDrawingView->height());
QPainter p;
p.begin(&mMask);
p.setPen(Qt::red);
p.setBrush(QBrush(Qt::red));
// Here we draw the widget mask
if(mDesktopPalette->isVisible())
{
p.drawRect(mDesktopPalette->geometry().x(), mDesktopPalette->geometry().y(), mDesktopPalette->width(), mDesktopPalette->height());
}
if(mKeyboardPalette->isVisible())
{
p.drawRect(mKeyboardPalette->geometry().x(), mKeyboardPalette->geometry().y(), mKeyboardPalette->width(), mKeyboardPalette->height());
}
if(mLibPalette->isVisible())
{
p.drawRect(mLibPalette->geometry().x(), mLibPalette->geometry().y(), mLibPalette->width(), mLibPalette->height());
}
p.end();
// Then we add the annotations. We create another painter because we need to
// apply transformations on it for coordinates matching
QPainter annotationPainter;
QTransform trans;
trans.translate(mTransparentDrawingView->width()/2, mTransparentDrawingView->height()/2);
annotationPainter.begin(&mMask);
annotationPainter.setPen(Qt::red);
annotationPainter.setBrush(Qt::red);
annotationPainter.setTransform(trans);
QList<QGraphicsItem*> allItems = mTransparentDrawingScene->items();
for(int i = 0; i < allItems.size(); i++)
{
QGraphicsItem* pCrntItem = allItems.at(i);
if(pCrntItem->isVisible())
{
QPainterPath crntPath = pCrntItem->shape();
QRectF rect = crntPath.boundingRect();
annotationPainter.drawRect(rect);
}
}
annotationPainter.end();
mTransparentDrawingView->setMask(mMask.createMaskFromColor(Qt::black));
}
else
{
// Remove the mask
QPixmap noMask(mTransparentDrawingView->width(), mTransparentDrawingView->height());
mTransparentDrawingView->setMask(noMask.mask());
}
}
void UBDesktopAnnotationController::refreshMask()
{
if(mIsFullyTransparent
|| UBDrawingController::drawingController()->stylusTool() == UBStylusTool::Selector)
{
updateMask(true);
}
}
......@@ -94,10 +94,12 @@ class UBDesktopAnnotationController : public QObject
void onDesktopPaletteMaximized();
void onDesktopPaletteMinimize();
void onTransparentWidgetResized();
void refreshMask();
private:
void setAssociatedPalettePosition(UBActionPalette* palette, const QString& actionName);
void togglePropertyPalette(UBActionPalette* palette);
void updateMask(bool bTransparent);
UBDesktopPalette *mDesktopPalette;
UBKeyboardPalette *mKeyboardPalette;
......@@ -126,6 +128,8 @@ class UBDesktopAnnotationController : public QObject
int mBoardStylusTool;
int mDesktopStylusTool;
QPixmap mMask;
};
#endif /* UBUNINOTESWINDOWCONTROLLER_H_ */
......@@ -36,9 +36,7 @@ UBDesktopPalette::UBDesktopPalette(QWidget *parent)
actions << UBApplication::mainWindow->actionPen;
actions << UBApplication::mainWindow->actionEraser;
actions << UBApplication::mainWindow->actionMarker;
#ifndef Q_WS_X11
actions << UBApplication::mainWindow->actionSelector;
#endif
actions << UBApplication::mainWindow->actionPointer;
if (UBPlatformUtils::hasVirtualKeyboard())
......@@ -152,9 +150,7 @@ void UBDesktopPalette::maximizeMe()
actions << UBApplication::mainWindow->actionPen;
actions << UBApplication::mainWindow->actionEraser;
actions << UBApplication::mainWindow->actionMarker;
#ifndef Q_WS_X11
actions << UBApplication::mainWindow->actionSelector;
#endif
actions << UBApplication::mainWindow->actionPointer;
if (UBPlatformUtils::hasVirtualKeyboard())
actions << UBApplication::mainWindow->actionVirtualKeyboard;
......@@ -221,3 +217,8 @@ QPoint UBDesktopPalette::buttonPos(QAction *action)
return p;
}
void UBDesktopPalette::notifySelectorSelection(bool selected)
{
UBApplication::mainWindow->actionVirtualKeyboard->setEnabled(selected);
}
......@@ -27,6 +27,7 @@ class UBDesktopPalette : public UBActionPalette
void disappearForCapture();
void appear();
QPoint buttonPos(QAction* action);
void notifySelectorSelection(bool selected);
signals:
void uniboardClick();
......
......@@ -249,6 +249,8 @@ bool UBGraphicsScene::inputDeviceMove(const QPointF& scenePos, const qreal& pres
{
if (currentTool == UBStylusTool::Line)
{
// TODO: Verify this beautiful implementation and check if
// it is possible to optimize it
QLineF radius(mPreviousPoint, position);
qreal angle = radius.angle();
angle = qRound(angle / 45) * 45;
......@@ -257,7 +259,7 @@ bool UBGraphicsScene::inputDeviceMove(const QPointF& scenePos, const qreal& pres
mPreviousPoint.x() + radiusLength * cos((angle * PI) / 180),
mPreviousPoint.y() - radiusLength * sin((angle * PI) / 180));
QLineF chord(position, newPosition);
if (chord.length() < qMin((int)16, (int)(radiusLength / 20)))
if (chord.length() < qMin((int)16, (int)(radiusLength / 20)))
position = newPosition;
}
......
......@@ -106,6 +106,7 @@ void UBFloatingPalette::mouseMoveEvent(QMouseEvent *event)
{
moveInsideParent(event->globalPos() - mDragPosition);
event->accept();
emit moving();
}
else
{
......
......@@ -78,6 +78,7 @@ class UBFloatingPalette : public QWidget
void minimizeStart(eMinimizedLocation location);
void maximizeStart();
void maximized();
void moving();
};
......
......@@ -34,7 +34,7 @@ UBLibPalette::UBLibPalette(QWidget *parent, const char *name):UBDockPalette(pare
mIcon = QPixmap(":images/paletteLibrary.png");
setAcceptDrops(true);
resize(UBSettings::settings()->libPaletteWidth->get().toInt(), height());
resize(UBSettings::settings()->libPaletteWidth->get().toInt(), parentWidget()->height());
setContentsMargins(border(), 0, 0, 0);
mCollapseWidth = 180;
mLastWidth = 300;
......@@ -201,6 +201,7 @@ void UBLibPalette::resizeEvent(QResizeEvent *event)
{
UBDockPalette::resizeEvent(event);
UBSettings::settings()->libPaletteWidth->set(width());
emit resized();
}
// --------------------------------------------------------------------------
......
......@@ -55,6 +55,9 @@ public:
UBLibActionBar* actionBar(){return mActionBar;}
signals:
void resized();
protected:
void updateMaxWidth();
void dragEnterEvent(QDragEnterEvent* pEvent);
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment