Shape2DCollection.h 6.05 KB
Newer Older
1
2
3
4
5
6
// Mantid Repository : https://github.com/mantidproject/mantid
//
// Copyright © 2018 ISIS Rutherford Appleton Laboratory UKRI,
//     NScD Oak Ridge National Laboratory, European Spallation Source
//     & Institut Laue - Langevin
// SPDX - License - Identifier: GPL - 3.0 +
7
8
9
#ifndef MANTIDPLOT_SHAPE2DCOLLECTION_H_
#define MANTIDPLOT_SHAPE2DCOLLECTION_H_

10
11
#include "MantidAPI/ITableWorkspace.h"

12
#include "RectF.h"
LamarMoore's avatar
LamarMoore committed
13
#include "Shape2D.h"
14
15
16
17
18
19
20
21
22

#include <QList>
#include <QTransform>

class QPainter;
class QMouseEvent;
class QWheelEvent;
class QKeyEvent;

23
24
25
26
namespace MantidQt {
namespace MantidWidgets {

/**
LamarMoore's avatar
LamarMoore committed
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
 * Class Shape2DCollection is a collection of 2D shapes.
 * It supports operations on teh shapes such as adding, removing, and aditting
 *either
 * with the mouse via control points (CPs) or via properties.
 *
 * The shapes operate in two coordinate systems:
 * 1. 'Real' or logical coordinates
 * 2. Transformed screen coordinates
 *
 * Shape2DCollection must know the boundaries of the drawing area in logical and
 *transformed screen coords.
 * They are set by calling setWindow(...) method. The first argument is the
 *logical drawing rectangle and
 * the second one is the corresponding screen viewport in pixels. The individual
 *shapes draw themselves in the
 * logical coords and unaware of the screen ones at all. If the size of the
 *screen/widget changes setWindow
 * must be called again. Changing the logical drawing bounds translates and
 *zooms the picture. The transformation is done by Qt's QTransform object.
 */
47
48
49
50
51
class Shape2DCollection : public QObject, public Shape2D {
  Q_OBJECT
public:
  Shape2DCollection();
  ~Shape2DCollection() override;
52
  Shape2D *clone() const override { return nullptr; }
53
54
55
56
57
58
59
60
61
62
  void setWindow(const RectF &surface, const QRect &viewport) const;
  void draw(QPainter &painter) const override;
  virtual void addShape(Shape2D *, bool slct = false);
  virtual void removeShape(Shape2D *, bool sendSignal = true);
  virtual void removeShapes(const QList<Shape2D *> &);
  virtual void clear();

  void keyPressEvent(QKeyEvent *);

  bool selectAtXY(int x, int y, bool edit = true);
63
  bool selectAtXY(const QPointF &point, bool edit = true);
64
  void deselectAtXY(int x, int y);
65
  void deselectAtXY(const QPointF &point);
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
  bool selectIn(const QRect &rect);
  void removeCurrentShape();
  bool isEmpty() const { return m_shapes.isEmpty(); }
  size_t size() const { return static_cast<size_t>(m_shapes.size()); }
  void addToSelection(int i);
  bool hasSelection() const;

  RectF getCurrentBoundingRect() const;
  void setCurrentBoundingRect(const RectF &rect);
  // double properties
  QStringList getCurrentDoubleNames() const;
  double getCurrentDouble(const QString &prop) const;
  void setCurrentDouble(const QString &prop, double value);
  // QPointF properties
  QStringList getCurrentPointNames() const;
  QPointF getCurrentPoint(const QString &prop) const;
  void setCurrentPoint(const QString &prop, const QPointF &value);

  using Shape2D::isMasked; // Unhide base class method (avoids Intel compiler
                           // warning)
  // is a point in real space masked by any of the shapes
  bool isMasked(double x, double y) const;
  // collect all screen pixels that are masked by the shapes
  QList<QPoint> getMaskedPixels() const;

  // set the bounding rect of the current shape such that its real rect is given
  // by the argument
  void setCurrentBoundingRectReal(const QRectF &rect);

  /// Change border color of all shapes.
  void changeBorderColor(const QColor &color);
97
98
99
100
  /// Save shape collection to a Table workspace
  void saveToTableWorkspace();
  /// Load shape collectio from a Table workspace
  void loadFromTableWorkspace(Mantid::API::ITableWorkspace_const_sptr ws);
101
  /// Load settings for the shape 2D collection from a project file
Samuel Jackson's avatar
Samuel Jackson committed
102
  virtual void loadFromProject(const std::string &lines);
103
  /// Save settings for the shape 2D collection to a project file
Samuel Jackson's avatar
Samuel Jackson committed
104
  virtual std::string saveToProject() const override;
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161

signals:

  void shapeCreated();
  void shapeSelected();
  void shapesDeselected();
  void shapesRemoved();
  void shapeChanged();
  void shapeChangeFinished();
  void cleared();

public slots:
  void addShape(const QString &type, int x, int y, const QColor &borderColor,
                const QColor &fillColor);
  void addFreeShape(const QPolygonF &, const QColor &borderColor,
                    const QColor &fillColor);
  void deselectAll();
  void moveRightBottomTo(int, int);
  void selectShapeOrControlPointAt(int x, int y);
  void addToSelectionShapeAt(int x, int y);
  void moveShapeOrControlPointBy(int dx, int dy);
  void touchShapeOrControlPointAt(int x, int y);
  void removeSelectedShapes();
  void restoreOverrideCursor();
  void drawFree(const QPolygonF &polygon);
  void eraseFree(const QPolygonF &polygon);

protected:
  void drawShape(QPainter &) const override {} // never called
  void addToPath(QPainterPath &) const override {}
  void refit() override;
  void resetBoundingRect() override;

  Shape2D *createShape(const QString &type, int x, int y) const;
  bool selectControlPointAt(int x, int y);
  void deselectControlPoint();
  bool isOverCurrentAt(int x, int y);
  bool isOverSelectionAt(int x, int y);
  void addToSelection(Shape2D *shape);
  void removeFromSelection(Shape2D *shape);
  void edit(Shape2D *shape);
  void finishEdit();
  QList<Shape2D *> getSelectedShapes() const { return m_selectedShapes; }

  QList<Shape2D *> m_shapes;
  mutable RectF
      m_surfaceRect; ///< original surface window in "real" coordinates
  mutable double m_wx, m_wy;
  mutable int m_h;                ///< original screen viewport height
  mutable QRect m_viewport;       ///< current screen viewport
  mutable QTransform m_transform; ///< current transform

  Shape2D *m_currentShape; ///< shape selected to edit (change size/shape)
  size_t m_currentCP;      ///< control point of m_currentShape selected to edit
  QList<Shape2D *>
      m_selectedShapes; ///< A list of selected shapes (can be moved or deleted)
  bool m_overridingCursor;
Samuel Jones's avatar
Samuel Jones committed
162
  friend class InstrumentWidgetEncoder;
163
};
LamarMoore's avatar
LamarMoore committed
164
165
} // namespace MantidWidgets
} // namespace MantidQt
166
167

#endif /*MANTIDPLOT_SHAPE2DCOLLECTION_H_*/