1 /* 2 Drawpile - a collaborative drawing program. 3 4 Copyright (C) 2015-2016 Calle Laakkonen 5 6 Drawpile is free software: you can redistribute it and/or modify 7 it under the terms of the GNU General Public License as published by 8 the Free Software Foundation, either version 3 of the License, or 9 (at your option) any later version. 10 11 Drawpile is distributed in the hope that it will be useful, 12 but WITHOUT ANY WARRANTY; without even the implied warranty of 13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 GNU General Public License for more details. 15 16 You should have received a copy of the GNU General Public License 17 along with Drawpile. If not, see <http://www.gnu.org/licenses/>. 18 */ 19 20 #ifndef TOOLCONTROLLER_H 21 #define TOOLCONTROLLER_H 22 23 #include "strokesmoother.h" 24 #include "tool.h" 25 #include "brushes/brush.h" 26 #include "canvas/features.h" 27 28 #include <QObject> 29 30 class QCursor; 31 32 namespace canvas { class CanvasModel; } 33 namespace net { class Client; } 34 35 namespace tools { 36 37 class Tool; 38 39 /** 40 * @brief The ToolController dispatches user input to the currently active tool 41 */ 42 class ToolController : public QObject 43 { 44 Q_PROPERTY(QCursor activeToolCursor READ activeToolCursor() NOTIFY toolCursorChanged) 45 Q_PROPERTY(int smoothing READ smoothing WRITE setSmoothing NOTIFY smoothingChanged) 46 Q_PROPERTY(uint16_t activeLayer READ activeLayer WRITE setActiveLayer NOTIFY activeLayerChanged) 47 Q_PROPERTY(uint16_t activeAnnotation READ activeAnnotation WRITE setActiveAnnotation NOTIFY activeAnnotationChanged) 48 Q_PROPERTY(brushes::ClassicBrush activeBrush READ activeBrush WRITE setActiveBrush NOTIFY activeBrushChanged) 49 Q_PROPERTY(canvas::CanvasModel* model READ model WRITE setModel NOTIFY modelChanged) 50 51 Q_OBJECT 52 public: 53 explicit ToolController(net::Client *client, QObject *parent=nullptr); 54 ~ToolController(); 55 56 void setActiveTool(Tool::Type tool); 57 Tool::Type activeTool() const; 58 59 QCursor activeToolCursor() const; 60 61 void setActiveLayer(uint16_t id); activeLayer()62 uint16_t activeLayer() const { return m_activeLayer; } 63 64 void setActiveAnnotation(uint16_t id); activeAnnotation()65 uint16_t activeAnnotation() const { return m_activeAnnotation; } 66 67 void setActiveBrush(const brushes::ClassicBrush &b); activeBrush()68 const brushes::ClassicBrush &activeBrush() const { return m_activebrush; } 69 70 void setModel(canvas::CanvasModel *model); model()71 canvas::CanvasModel *model() const { return m_model; } 72 73 void setSmoothing(int smoothing); smoothing()74 int smoothing() const { return m_smoothing; } 75 76 // TODO this is used just for sending the commands. Replace with a signal? client()77 inline net::Client *client() const { return m_client; } 78 79 Tool *getTool(Tool::Type type); 80 81 //! Is there a multipart drawing operation in progress? 82 bool isMultipartDrawing() const; 83 84 /** 85 * Apply an offset to the position of the active tool 86 * 87 * This is used to correct the tool position when the canvas is 88 * resized while the local user is still drawing. 89 */ 90 void offsetActiveTool(int xOffset, int yOffset); 91 92 public slots: 93 //! Start a new stroke 94 void startDrawing(const QPointF &point, qreal pressure, bool right, float zoom); 95 96 //! Continue a stroke 97 void continueDrawing(const QPointF &point, qreal pressure, bool shift, bool alt); 98 99 //! Stylus hover (not yet drawing) 100 void hoverDrawing(const QPointF &point); 101 102 //! End a stroke 103 void endDrawing(); 104 105 /** 106 * @brief Undo the latest part of a multipart drawing 107 * 108 * Multipart drawings are not committed until finishMultipartDrawing is 109 * called, so undoing is a local per-tool operation. 110 * 111 * @return false if there was nothing to undo 112 */ 113 bool undoMultipartDrawing(); 114 115 //! Commit the current multipart drawing (if any) 116 void finishMultipartDrawing(); 117 118 //! Cancel the current multipart drawing (if any) 119 void cancelMultipartDrawing(); 120 121 signals: 122 void activeToolChanged(Tool::Type type); 123 void toolCursorChanged(const QCursor &cursor); 124 void activeLayerChanged(int layerId); 125 void activeAnnotationChanged(uint16_t annotationId); 126 void activeBrushChanged(const brushes::ClassicBrush&); 127 void modelChanged(canvas::CanvasModel *model); 128 void smoothingChanged(int smoothing); 129 130 void colorUsed(const QColor &color); 131 void zoomRequested(const QRect &rect, int steps); 132 133 private slots: 134 void onAnnotationRowDelete(const QModelIndex&, int first, int last); 135 void onFeatureAccessChange(canvas::Feature feature, bool canUse); 136 137 private: 138 void registerTool(Tool *tool); 139 140 Tool *m_toolbox[Tool::_LASTTOOL]; 141 net::Client *m_client; 142 143 canvas::CanvasModel *m_model; 144 145 brushes::ClassicBrush m_activebrush; 146 Tool *m_activeTool; 147 uint16_t m_activeLayer; 148 uint16_t m_activeAnnotation; 149 bool m_prevShift, m_prevAlt; 150 151 int m_smoothing; 152 StrokeSmoother m_smoother; 153 }; 154 155 } 156 157 #endif // TOOLCONTROLLER_H 158