##// END OF EJS Templates
Merge pull request 340 from SciQLop-fork develop...
leroux -
r932:16999d8139e2 merge
parent child
Show More
@@ -0,0 +1,18
1 #ifndef SCIQLOP_MACSCROLLBARSTYLE_H
2 #define SCIQLOP_MACSCROLLBARSTYLE_H
3
4 #include <QProxyStyle>
5
6 /**
7 * @brief Special style to always display the scrollbars on MAC.
8 */
9 class MacScrollBarStyle : public QProxyStyle {
10
11 public:
12 int styleHint(StyleHint hint, const QStyleOption *option, const QWidget *widget,
13 QStyleHintReturn *returnData) const;
14
15 void selfInstallOn(QWidget *widget, bool installOnSubWidgets);
16 };
17
18 #endif // SCIQLOP_MACSCROLLBARSTYLE_H
@@ -0,0 +1,40
1 #include "Visualization/MacScrollBarStyle.h"
2
3 #include <QWidget>
4
5 int MacScrollBarStyle::styleHint(QStyle::StyleHint hint, const QStyleOption *option,
6 const QWidget *widget, QStyleHintReturn *returnData) const
7 {
8 switch (hint) {
9 case SH_ScrollBar_Transient:
10 return false; // Makes the scrollbar always visible
11 case SH_ScrollView_FrameOnlyAroundContents:
12 return true; // Avoid that the scrollbar is drawn on top of the widget
13 default:
14 break;
15 }
16
17 return QProxyStyle::styleHint(hint, option, widget, returnData);
18 }
19
20 void MacScrollBarStyle::selfInstallOn(QWidget *widget, bool installOnSubWidgets)
21 {
22 // Note: a style can be installed on a particular widget but it is not automatically applied its
23 // children widgets.
24
25 QList<QWidget *> widgetsToStyle{widget};
26 while (!widgetsToStyle.isEmpty()) {
27
28 auto widget = widgetsToStyle.takeFirst();
29 widget->setStyle(this);
30
31 if (installOnSubWidgets) {
32 for (auto child : widget->children()) {
33 auto childWidget = qobject_cast<QWidget *>(child);
34 if (childWidget) {
35 widgetsToStyle << childWidget;
36 }
37 }
38 }
39 }
40 }
@@ -1,34 +1,37
1 #ifndef SCIQLOP_AXISRENDERINGUTILS_H
1 #ifndef SCIQLOP_AXISRENDERINGUTILS_H
2 #define SCIQLOP_AXISRENDERINGUTILS_H
2 #define SCIQLOP_AXISRENDERINGUTILS_H
3
3
4 #include <memory>
4 #include <memory>
5
5
6 #include <QtCore/QLoggingCategory>
6 #include <QtCore/QString>
7 #include <QtCore/QString>
7
8
9 Q_DECLARE_LOGGING_CATEGORY(LOG_AxisRenderingUtils)
10
8 class IDataSeries;
11 class IDataSeries;
9 class QCPAxis;
12 class QCPAxis;
10 class QCPColorScale;
13 class QCPColorScale;
11 class QCustomPlot;
14 class QCustomPlot;
12
15
13 /// Formats a data value according to the axis on which it is present
16 /// Formats a data value according to the axis on which it is present
14 QString formatValue(double value, const QCPAxis &axis);
17 QString formatValue(double value, const QCPAxis &axis);
15
18
16 /**
19 /**
17 * Helper used to handle axes rendering
20 * Helper used to handle axes rendering
18 */
21 */
19 struct IAxisHelper {
22 struct IAxisHelper {
20 virtual ~IAxisHelper() noexcept = default;
23 virtual ~IAxisHelper() noexcept = default;
21
24
22 /// Set properties of the plot's axes and the color scale associated to plot passed as
25 /// Set properties of the plot's axes and the color scale associated to plot passed as
23 /// parameters
26 /// parameters
24 /// @param plot the plot for which to set axe properties
27 /// @param plot the plot for which to set axe properties
25 /// @param colorScale the color scale for which to set properties
28 /// @param colorScale the color scale for which to set properties
26 virtual void setProperties(QCustomPlot &plot, QCPColorScale &colorScale) = 0;
29 virtual void setProperties(QCustomPlot &plot, QCPColorScale &colorScale) = 0;
27 };
30 };
28
31
29 struct IAxisHelperFactory {
32 struct IAxisHelperFactory {
30 /// Creates IAxisHelper according to a data series
33 /// Creates IAxisHelper according to a data series
31 static std::unique_ptr<IAxisHelper> create(std::shared_ptr<IDataSeries> dataSeries) noexcept;
34 static std::unique_ptr<IAxisHelper> create(std::shared_ptr<IDataSeries> dataSeries) noexcept;
32 };
35 };
33
36
34 #endif // SCIQLOP_AXISRENDERINGUTILS_H
37 #endif // SCIQLOP_AXISRENDERINGUTILS_H
@@ -1,29 +1,33
1 #ifndef SCIQLOP_PLOTTABLESRENDERINGUTILS_H
1 #ifndef SCIQLOP_PLOTTABLESRENDERINGUTILS_H
2 #define SCIQLOP_PLOTTABLESRENDERINGUTILS_H
2 #define SCIQLOP_PLOTTABLESRENDERINGUTILS_H
3
3
4 #include <Visualization/VisualizationDefs.h>
4 #include <Visualization/VisualizationDefs.h>
5
5
6 #include <memory>
6 #include <memory>
7
7
8 #include <QtCore/QLoggingCategory>
9
10 Q_DECLARE_LOGGING_CATEGORY(LOG_PlottablesRenderingUtils)
11
8 class IDataSeries;
12 class IDataSeries;
9 class QCPColorScale;
13 class QCPColorScale;
10 class QCustomPlot;
14 class QCustomPlot;
11
15
12 /**
16 /**
13 * Helper used to handle plottables rendering
17 * Helper used to handle plottables rendering
14 */
18 */
15 struct IPlottablesHelper {
19 struct IPlottablesHelper {
16 virtual ~IPlottablesHelper() noexcept = default;
20 virtual ~IPlottablesHelper() noexcept = default;
17
21
18 /// Set properties of the plottables passed as parameter
22 /// Set properties of the plottables passed as parameter
19 /// @param plottables the plottables for which to set properties
23 /// @param plottables the plottables for which to set properties
20 virtual void setProperties(PlottablesMap &plottables) = 0;
24 virtual void setProperties(PlottablesMap &plottables) = 0;
21 };
25 };
22
26
23 struct IPlottablesHelperFactory {
27 struct IPlottablesHelperFactory {
24 /// Creates IPlottablesHelper according to a data series
28 /// Creates IPlottablesHelper according to a data series
25 static std::unique_ptr<IPlottablesHelper>
29 static std::unique_ptr<IPlottablesHelper>
26 create(std::shared_ptr<IDataSeries> dataSeries) noexcept;
30 create(std::shared_ptr<IDataSeries> dataSeries) noexcept;
27 };
31 };
28
32
29 #endif // SCIQLOP_PLOTTABLESRENDERINGUTILS_H
33 #endif // SCIQLOP_PLOTTABLESRENDERINGUTILS_H
@@ -1,97 +1,98
1
1
2 gui_moc_headers = [
2 gui_moc_headers = [
3 'include/DataSource/DataSourceWidget.h',
3 'include/DataSource/DataSourceWidget.h',
4 'include/DataSource/DataSourceTreeWidget.h',
4 'include/DataSource/DataSourceTreeWidget.h',
5 'include/Settings/SqpSettingsDialog.h',
5 'include/Settings/SqpSettingsDialog.h',
6 'include/Settings/SqpSettingsGeneralWidget.h',
6 'include/Settings/SqpSettingsGeneralWidget.h',
7 'include/SidePane/SqpSidePane.h',
7 'include/SidePane/SqpSidePane.h',
8 'include/SqpApplication.h',
8 'include/SqpApplication.h',
9 'include/DragAndDrop/DragDropHelper.h',
9 'include/DragAndDrop/DragDropHelper.h',
10 'include/DragAndDrop/DragDropScroller.h',
10 'include/DragAndDrop/DragDropScroller.h',
11 'include/DragAndDrop/DragDropTabSwitcher.h',
11 'include/DragAndDrop/DragDropTabSwitcher.h',
12 'include/TimeWidget/TimeWidget.h',
12 'include/TimeWidget/TimeWidget.h',
13 'include/Variable/VariableInspectorWidget.h',
13 'include/Variable/VariableInspectorWidget.h',
14 'include/Variable/VariableInspectorTableView.h',
14 'include/Variable/VariableInspectorTableView.h',
15 'include/Variable/RenameVariableDialog.h',
15 'include/Variable/RenameVariableDialog.h',
16 'include/Visualization/qcustomplot.h',
16 'include/Visualization/qcustomplot.h',
17 'include/Visualization/VisualizationGraphWidget.h',
17 'include/Visualization/VisualizationGraphWidget.h',
18 'include/Visualization/VisualizationTabWidget.h',
18 'include/Visualization/VisualizationTabWidget.h',
19 'include/Visualization/VisualizationWidget.h',
19 'include/Visualization/VisualizationWidget.h',
20 'include/Visualization/VisualizationZoneWidget.h',
20 'include/Visualization/VisualizationZoneWidget.h',
21 'include/Visualization/VisualizationDragDropContainer.h',
21 'include/Visualization/VisualizationDragDropContainer.h',
22 'include/Visualization/VisualizationDragWidget.h'
22 'include/Visualization/VisualizationDragWidget.h'
23 ]
23 ]
24
24
25 gui_ui_files = [
25 gui_ui_files = [
26 'ui/DataSource/DataSourceWidget.ui',
26 'ui/DataSource/DataSourceWidget.ui',
27 'ui/Settings/SqpSettingsDialog.ui',
27 'ui/Settings/SqpSettingsDialog.ui',
28 'ui/Settings/SqpSettingsGeneralWidget.ui',
28 'ui/Settings/SqpSettingsGeneralWidget.ui',
29 'ui/SidePane/SqpSidePane.ui',
29 'ui/SidePane/SqpSidePane.ui',
30 'ui/TimeWidget/TimeWidget.ui',
30 'ui/TimeWidget/TimeWidget.ui',
31 'ui/Variable/VariableInspectorWidget.ui',
31 'ui/Variable/VariableInspectorWidget.ui',
32 'ui/Variable/RenameVariableDialog.ui',
32 'ui/Variable/RenameVariableDialog.ui',
33 'ui/Variable/VariableMenuHeaderWidget.ui',
33 'ui/Variable/VariableMenuHeaderWidget.ui',
34 'ui/Visualization/VisualizationGraphWidget.ui',
34 'ui/Visualization/VisualizationGraphWidget.ui',
35 'ui/Visualization/VisualizationTabWidget.ui',
35 'ui/Visualization/VisualizationTabWidget.ui',
36 'ui/Visualization/VisualizationWidget.ui',
36 'ui/Visualization/VisualizationWidget.ui',
37 'ui/Visualization/VisualizationZoneWidget.ui'
37 'ui/Visualization/VisualizationZoneWidget.ui'
38 ]
38 ]
39
39
40 gui_qresources = ['resources/sqpguiresources.qrc']
40 gui_qresources = ['resources/sqpguiresources.qrc']
41
41
42 gui_moc_files = qt5.preprocess(moc_headers : gui_moc_headers,
42 gui_moc_files = qt5.preprocess(moc_headers : gui_moc_headers,
43 ui_files : gui_ui_files,
43 ui_files : gui_ui_files,
44 qresources : gui_qresources)
44 qresources : gui_qresources)
45
45
46 gui_sources = [
46 gui_sources = [
47 'src/SqpApplication.cpp',
47 'src/SqpApplication.cpp',
48 'src/DragAndDrop/DragDropHelper.cpp',
48 'src/DragAndDrop/DragDropHelper.cpp',
49 'src/DragAndDrop/DragDropScroller.cpp',
49 'src/DragAndDrop/DragDropScroller.cpp',
50 'src/DragAndDrop/DragDropTabSwitcher.cpp',
50 'src/DragAndDrop/DragDropTabSwitcher.cpp',
51 'src/Common/ColorUtils.cpp',
51 'src/Common/ColorUtils.cpp',
52 'src/Common/VisualizationDef.cpp',
52 'src/Common/VisualizationDef.cpp',
53 'src/DataSource/DataSourceTreeWidgetItem.cpp',
53 'src/DataSource/DataSourceTreeWidgetItem.cpp',
54 'src/DataSource/DataSourceTreeWidgetHelper.cpp',
54 'src/DataSource/DataSourceTreeWidgetHelper.cpp',
55 'src/DataSource/DataSourceWidget.cpp',
55 'src/DataSource/DataSourceWidget.cpp',
56 'src/DataSource/DataSourceTreeWidget.cpp',
56 'src/DataSource/DataSourceTreeWidget.cpp',
57 'src/Settings/SqpSettingsDialog.cpp',
57 'src/Settings/SqpSettingsDialog.cpp',
58 'src/Settings/SqpSettingsGeneralWidget.cpp',
58 'src/Settings/SqpSettingsGeneralWidget.cpp',
59 'src/SidePane/SqpSidePane.cpp',
59 'src/SidePane/SqpSidePane.cpp',
60 'src/TimeWidget/TimeWidget.cpp',
60 'src/TimeWidget/TimeWidget.cpp',
61 'src/Variable/VariableInspectorWidget.cpp',
61 'src/Variable/VariableInspectorWidget.cpp',
62 'src/Variable/VariableInspectorTableView.cpp',
62 'src/Variable/VariableInspectorTableView.cpp',
63 'src/Variable/VariableMenuHeaderWidget.cpp',
63 'src/Variable/VariableMenuHeaderWidget.cpp',
64 'src/Variable/RenameVariableDialog.cpp',
64 'src/Variable/RenameVariableDialog.cpp',
65 'src/Visualization/VisualizationGraphHelper.cpp',
65 'src/Visualization/VisualizationGraphHelper.cpp',
66 'src/Visualization/VisualizationGraphRenderingDelegate.cpp',
66 'src/Visualization/VisualizationGraphRenderingDelegate.cpp',
67 'src/Visualization/VisualizationGraphWidget.cpp',
67 'src/Visualization/VisualizationGraphWidget.cpp',
68 'src/Visualization/VisualizationTabWidget.cpp',
68 'src/Visualization/VisualizationTabWidget.cpp',
69 'src/Visualization/VisualizationWidget.cpp',
69 'src/Visualization/VisualizationWidget.cpp',
70 'src/Visualization/VisualizationZoneWidget.cpp',
70 'src/Visualization/VisualizationZoneWidget.cpp',
71 'src/Visualization/qcustomplot.cpp',
71 'src/Visualization/qcustomplot.cpp',
72 'src/Visualization/QCustomPlotSynchronizer.cpp',
72 'src/Visualization/QCustomPlotSynchronizer.cpp',
73 'src/Visualization/operations/FindVariableOperation.cpp',
73 'src/Visualization/operations/FindVariableOperation.cpp',
74 'src/Visualization/operations/GenerateVariableMenuOperation.cpp',
74 'src/Visualization/operations/GenerateVariableMenuOperation.cpp',
75 'src/Visualization/operations/MenuBuilder.cpp',
75 'src/Visualization/operations/MenuBuilder.cpp',
76 'src/Visualization/operations/RemoveVariableOperation.cpp',
76 'src/Visualization/operations/RemoveVariableOperation.cpp',
77 'src/Visualization/operations/RescaleAxeOperation.cpp',
77 'src/Visualization/operations/RescaleAxeOperation.cpp',
78 'src/Visualization/VisualizationDragDropContainer.cpp',
78 'src/Visualization/VisualizationDragDropContainer.cpp',
79 'src/Visualization/VisualizationDragWidget.cpp'
79 'src/Visualization/VisualizationDragWidget.cpp',
80 'src/Visualization/AxisRenderingUtils.cpp',
80 'src/Visualization/AxisRenderingUtils.cpp',
81 'src/Visualization/PlottablesRenderingUtils.cpp'
81 'src/Visualization/PlottablesRenderingUtils.cpp',
82 'src/Visualization/MacScrollBarStyle.cpp'
82 ]
83 ]
83
84
84 gui_inc = include_directories(['include'])
85 gui_inc = include_directories(['include'])
85
86
86 sciqlop_gui_lib = library('sciqlopgui',
87 sciqlop_gui_lib = library('sciqlopgui',
87 gui_sources,
88 gui_sources,
88 gui_moc_files,
89 gui_moc_files,
89 include_directories : [gui_inc],
90 include_directories : [gui_inc],
90 dependencies : [ qt5printsupport, qt5gui, qt5widgets, qt5svg, sciqlop_core],
91 dependencies : [ qt5printsupport, qt5gui, qt5widgets, qt5svg, sciqlop_core],
91 install : true
92 install : true
92 )
93 )
93
94
94 sciqlop_gui = declare_dependency(link_with : sciqlop_gui_lib,
95 sciqlop_gui = declare_dependency(link_with : sciqlop_gui_lib,
95 include_directories : gui_inc,
96 include_directories : gui_inc,
96 dependencies : [qt5printsupport, qt5gui, qt5widgets, qt5svg, sciqlop_core])
97 dependencies : [qt5printsupport, qt5gui, qt5widgets, qt5svg, sciqlop_core])
97
98
@@ -1,163 +1,173
1 #include "Visualization/AxisRenderingUtils.h"
1 #include "Visualization/AxisRenderingUtils.h"
2
2
3 #include <Data/ScalarSeries.h>
3 #include <Data/ScalarSeries.h>
4 #include <Data/SpectrogramSeries.h>
4 #include <Data/SpectrogramSeries.h>
5 #include <Data/VectorSeries.h>
5 #include <Data/VectorSeries.h>
6
6
7 #include <Visualization/qcustomplot.h>
7 #include <Visualization/qcustomplot.h>
8
8
9 Q_LOGGING_CATEGORY(LOG_AxisRenderingUtils, "AxisRenderingUtils")
10
9 namespace {
11 namespace {
10
12
11 const auto DATETIME_FORMAT = QStringLiteral("yyyy/MM/dd hh:mm:ss:zzz");
13 const auto DATETIME_FORMAT = QStringLiteral("yyyy/MM/dd hh:mm:ss:zzz");
12
14
13 /// Format for datetimes on a axis
15 /// Format for datetimes on a axis
14 const auto DATETIME_TICKER_FORMAT = QStringLiteral("yyyy/MM/dd \nhh:mm:ss");
16 const auto DATETIME_TICKER_FORMAT = QStringLiteral("yyyy/MM/dd \nhh:mm:ss");
15
17
16 /// Generates the appropriate ticker for an axis, depending on whether the axis displays time or
18 /// Generates the appropriate ticker for an axis, depending on whether the axis displays time or
17 /// non-time data
19 /// non-time data
18 QSharedPointer<QCPAxisTicker> axisTicker(bool isTimeAxis)
20 QSharedPointer<QCPAxisTicker> axisTicker(bool isTimeAxis, QCPAxis::ScaleType scaleType)
19 {
21 {
20 if (isTimeAxis) {
22 if (isTimeAxis) {
21 auto dateTicker = QSharedPointer<QCPAxisTickerDateTime>::create();
23 auto dateTicker = QSharedPointer<QCPAxisTickerDateTime>::create();
22 dateTicker->setDateTimeFormat(DATETIME_TICKER_FORMAT);
24 dateTicker->setDateTimeFormat(DATETIME_TICKER_FORMAT);
23 dateTicker->setDateTimeSpec(Qt::UTC);
25 dateTicker->setDateTimeSpec(Qt::UTC);
24
26
25 return dateTicker;
27 return dateTicker;
26 }
28 }
29 else if (scaleType == QCPAxis::stLogarithmic) {
30 return QSharedPointer<QCPAxisTickerLog>::create();
31 }
27 else {
32 else {
28 // default ticker
33 // default ticker
29 return QSharedPointer<QCPAxisTicker>::create();
34 return QSharedPointer<QCPAxisTicker>::create();
30 }
35 }
31 }
36 }
32
37
33 /**
38 /**
34 * Sets properties of the axis passed as parameter
39 * Sets properties of the axis passed as parameter
35 * @param axis the axis to set
40 * @param axis the axis to set
36 * @param unit the unit to set for the axis
41 * @param unit the unit to set for the axis
37 * @param scaleType the scale type to set for the axis
42 * @param scaleType the scale type to set for the axis
38 */
43 */
39 void setAxisProperties(QCPAxis &axis, const Unit &unit,
44 void setAxisProperties(QCPAxis &axis, const Unit &unit,
40 QCPAxis::ScaleType scaleType = QCPAxis::stLinear)
45 QCPAxis::ScaleType scaleType = QCPAxis::stLinear)
41 {
46 {
42 // label (unit name)
47 // label (unit name)
43 axis.setLabel(unit.m_Name);
48 axis.setLabel(unit.m_Name);
44
49
45 // scale type
50 // scale type
46 axis.setScaleType(scaleType);
51 axis.setScaleType(scaleType);
52 if (scaleType == QCPAxis::stLogarithmic) {
53 // Scientific notation
54 axis.setNumberPrecision(0);
55 axis.setNumberFormat("eb");
56 }
47
57
48 // ticker (depending on the type of unit)
58 // ticker (depending on the type of unit)
49 axis.setTicker(axisTicker(unit.m_TimeUnit));
59 axis.setTicker(axisTicker(unit.m_TimeUnit, scaleType));
50 }
60 }
51
61
52 /**
62 /**
53 * Delegate used to set axes properties
63 * Delegate used to set axes properties
54 */
64 */
55 template <typename T, typename Enabled = void>
65 template <typename T, typename Enabled = void>
56 struct AxisSetter {
66 struct AxisSetter {
57 static void setProperties(T &, QCustomPlot &, QCPColorScale &)
67 static void setProperties(T &, QCustomPlot &, QCPColorScale &)
58 {
68 {
59 // Default implementation does nothing
69 // Default implementation does nothing
70 qCCritical(LOG_AxisRenderingUtils()) << "Can't set axis properties: unmanaged type of data";
60 }
71 }
61 };
72 };
62
73
63 /**
74 /**
64 * Specialization of AxisSetter for scalars and vectors
75 * Specialization of AxisSetter for scalars and vectors
65 * @sa ScalarSeries
76 * @sa ScalarSeries
66 * @sa VectorSeries
77 * @sa VectorSeries
67 */
78 */
68 template <typename T>
79 template <typename T>
69 struct AxisSetter<T, typename std::enable_if_t<std::is_base_of<ScalarSeries, T>::value
80 struct AxisSetter<T, typename std::enable_if_t<std::is_base_of<ScalarSeries, T>::value
70 or std::is_base_of<VectorSeries, T>::value> > {
81 or std::is_base_of<VectorSeries, T>::value> > {
71 static void setProperties(T &dataSeries, QCustomPlot &plot, QCPColorScale &)
82 static void setProperties(T &dataSeries, QCustomPlot &plot, QCPColorScale &)
72 {
83 {
73 dataSeries.lockRead();
84 dataSeries.lockRead();
74 auto xAxisUnit = dataSeries.xAxisUnit();
85 auto xAxisUnit = dataSeries.xAxisUnit();
75 auto valuesUnit = dataSeries.valuesUnit();
86 auto valuesUnit = dataSeries.valuesUnit();
76 dataSeries.unlock();
87 dataSeries.unlock();
77
88
78 setAxisProperties(*plot.xAxis, xAxisUnit);
89 setAxisProperties(*plot.xAxis, xAxisUnit);
79 setAxisProperties(*plot.yAxis, valuesUnit);
90 setAxisProperties(*plot.yAxis, valuesUnit);
80 }
91 }
81 };
92 };
82
93
83 /**
94 /**
84 * Specialization of AxisSetter for spectrograms
95 * Specialization of AxisSetter for spectrograms
85 * @sa SpectrogramSeries
96 * @sa SpectrogramSeries
86 */
97 */
87 template <typename T>
98 template <typename T>
88 struct AxisSetter<T, typename std::enable_if_t<std::is_base_of<SpectrogramSeries, T>::value> > {
99 struct AxisSetter<T, typename std::enable_if_t<std::is_base_of<SpectrogramSeries, T>::value> > {
89 static void setProperties(T &dataSeries, QCustomPlot &plot, QCPColorScale &colorScale)
100 static void setProperties(T &dataSeries, QCustomPlot &plot, QCPColorScale &colorScale)
90 {
101 {
91 dataSeries.lockRead();
102 dataSeries.lockRead();
92 auto xAxisUnit = dataSeries.xAxisUnit();
103 auto xAxisUnit = dataSeries.xAxisUnit();
93 /// @todo ALX: use iterators here
104 /// @todo ALX: use iterators here
94 auto yAxisUnit = dataSeries.yAxis().unit();
105 auto yAxisUnit = dataSeries.yAxis().unit();
95 auto valuesUnit = dataSeries.valuesUnit();
106 auto valuesUnit = dataSeries.valuesUnit();
96 dataSeries.unlock();
107 dataSeries.unlock();
97
108
98 setAxisProperties(*plot.xAxis, xAxisUnit);
109 setAxisProperties(*plot.xAxis, xAxisUnit);
99 setAxisProperties(*plot.yAxis, yAxisUnit);
110 setAxisProperties(*plot.yAxis, yAxisUnit, QCPAxis::stLogarithmic);
100
111
101 // Displays color scale in plot
112 // Displays color scale in plot
102 plot.plotLayout()->insertRow(0);
113 plot.plotLayout()->insertRow(0);
103 plot.plotLayout()->addElement(0, 0, &colorScale);
114 plot.plotLayout()->addElement(0, 0, &colorScale);
104 colorScale.setType(QCPAxis::atTop);
115 colorScale.setType(QCPAxis::atTop);
105 colorScale.setMinimumMargins(QMargins{0, 0, 0, 0});
116 colorScale.setMinimumMargins(QMargins{0, 0, 0, 0});
106
117
107 // Aligns color scale with axes
118 // Aligns color scale with axes
108 auto marginGroups = plot.axisRect()->marginGroups();
119 auto marginGroups = plot.axisRect()->marginGroups();
109 for (auto it = marginGroups.begin(), end = marginGroups.end(); it != end; ++it) {
120 for (auto it = marginGroups.begin(), end = marginGroups.end(); it != end; ++it) {
110 colorScale.setMarginGroup(it.key(), it.value());
121 colorScale.setMarginGroup(it.key(), it.value());
111 }
122 }
112
123
113 // Set color scale properties
124 // Set color scale properties
114 colorScale.setLabel(valuesUnit.m_Name);
125 setAxisProperties(*colorScale.axis(), valuesUnit, QCPAxis::stLogarithmic);
115 colorScale.setDataScaleType(QCPAxis::stLogarithmic); // Logarithmic scale
116 }
126 }
117 };
127 };
118
128
119 /**
129 /**
120 * Default implementation of IAxisHelper, which takes data series to set axes properties
130 * Default implementation of IAxisHelper, which takes data series to set axes properties
121 * @tparam T the data series' type
131 * @tparam T the data series' type
122 */
132 */
123 template <typename T>
133 template <typename T>
124 struct AxisHelper : public IAxisHelper {
134 struct AxisHelper : public IAxisHelper {
125 explicit AxisHelper(T &dataSeries) : m_DataSeries{dataSeries} {}
135 explicit AxisHelper(T &dataSeries) : m_DataSeries{dataSeries} {}
126
136
127 void setProperties(QCustomPlot &plot, QCPColorScale &colorScale) override
137 void setProperties(QCustomPlot &plot, QCPColorScale &colorScale) override
128 {
138 {
129 AxisSetter<T>::setProperties(m_DataSeries, plot, colorScale);
139 AxisSetter<T>::setProperties(m_DataSeries, plot, colorScale);
130 }
140 }
131
141
132 T &m_DataSeries;
142 T &m_DataSeries;
133 };
143 };
134
144
135 } // namespace
145 } // namespace
136
146
137 QString formatValue(double value, const QCPAxis &axis)
147 QString formatValue(double value, const QCPAxis &axis)
138 {
148 {
139 // If the axis is a time axis, formats the value as a date
149 // If the axis is a time axis, formats the value as a date
140 if (auto axisTicker = qSharedPointerDynamicCast<QCPAxisTickerDateTime>(axis.ticker())) {
150 if (auto axisTicker = qSharedPointerDynamicCast<QCPAxisTickerDateTime>(axis.ticker())) {
141 return DateUtils::dateTime(value, axisTicker->dateTimeSpec()).toString(DATETIME_FORMAT);
151 return DateUtils::dateTime(value, axisTicker->dateTimeSpec()).toString(DATETIME_FORMAT);
142 }
152 }
143 else {
153 else {
144 return QString::number(value);
154 return QString::number(value);
145 }
155 }
146 }
156 }
147
157
148 std::unique_ptr<IAxisHelper>
158 std::unique_ptr<IAxisHelper>
149 IAxisHelperFactory::create(std::shared_ptr<IDataSeries> dataSeries) noexcept
159 IAxisHelperFactory::create(std::shared_ptr<IDataSeries> dataSeries) noexcept
150 {
160 {
151 if (auto scalarSeries = std::dynamic_pointer_cast<ScalarSeries>(dataSeries)) {
161 if (auto scalarSeries = std::dynamic_pointer_cast<ScalarSeries>(dataSeries)) {
152 return std::make_unique<AxisHelper<ScalarSeries> >(*scalarSeries);
162 return std::make_unique<AxisHelper<ScalarSeries> >(*scalarSeries);
153 }
163 }
154 else if (auto spectrogramSeries = std::dynamic_pointer_cast<SpectrogramSeries>(dataSeries)) {
164 else if (auto spectrogramSeries = std::dynamic_pointer_cast<SpectrogramSeries>(dataSeries)) {
155 return std::make_unique<AxisHelper<SpectrogramSeries> >(*spectrogramSeries);
165 return std::make_unique<AxisHelper<SpectrogramSeries> >(*spectrogramSeries);
156 }
166 }
157 else if (auto vectorSeries = std::dynamic_pointer_cast<VectorSeries>(dataSeries)) {
167 else if (auto vectorSeries = std::dynamic_pointer_cast<VectorSeries>(dataSeries)) {
158 return std::make_unique<AxisHelper<VectorSeries> >(*vectorSeries);
168 return std::make_unique<AxisHelper<VectorSeries> >(*vectorSeries);
159 }
169 }
160 else {
170 else {
161 return std::make_unique<AxisHelper<IDataSeries> >(*dataSeries);
171 return std::make_unique<AxisHelper<IDataSeries> >(*dataSeries);
162 }
172 }
163 }
173 }
@@ -1,120 +1,127
1 #include "Visualization/PlottablesRenderingUtils.h"
1 #include "Visualization/PlottablesRenderingUtils.h"
2
2
3 #include <Common/ColorUtils.h>
3 #include <Common/ColorUtils.h>
4
4
5 #include <Data/ScalarSeries.h>
5 #include <Data/ScalarSeries.h>
6 #include <Data/SpectrogramSeries.h>
6 #include <Data/SpectrogramSeries.h>
7 #include <Data/VectorSeries.h>
7 #include <Data/VectorSeries.h>
8
8
9 #include <Visualization/qcustomplot.h>
9 #include <Visualization/qcustomplot.h>
10
10
11 Q_LOGGING_CATEGORY(LOG_PlottablesRenderingUtils, "PlottablesRenderingUtils")
12
11 namespace {
13 namespace {
12
14
13 /// Default gradient used for colormap
15 /// Default gradient used for colormap
14 const auto DEFAULT_COLORMAP_GRADIENT = QCPColorGradient::gpJet;
16 const auto DEFAULT_COLORMAP_GRADIENT = QCPColorGradient::gpJet;
15
17
16 /**
18 /**
17 * Delegate used to set plottables properties
19 * Delegate used to set plottables properties
18 */
20 */
19 template <typename T, typename Enabled = void>
21 template <typename T, typename Enabled = void>
20 struct PlottablesSetter {
22 struct PlottablesSetter {
21 static void setProperties(T &, PlottablesMap &)
23 static void setProperties(T &, PlottablesMap &)
22 {
24 {
23 // Default implementation does nothing
25 // Default implementation does nothing
26 qCCritical(LOG_PlottablesRenderingUtils())
27 << "Can't set plottables properties: unmanaged type of data";
24 }
28 }
25 };
29 };
26
30
27 /**
31 /**
28 * Specialization of PlottablesSetter for scalars and vectors
32 * Specialization of PlottablesSetter for scalars and vectors
29 * @sa ScalarSeries
33 * @sa ScalarSeries
30 * @sa VectorSeries
34 * @sa VectorSeries
31 */
35 */
32 template <typename T>
36 template <typename T>
33 struct PlottablesSetter<T, typename std::enable_if_t<std::is_base_of<ScalarSeries, T>::value
37 struct PlottablesSetter<T, typename std::enable_if_t<std::is_base_of<ScalarSeries, T>::value
34 or std::is_base_of<VectorSeries, T>::value> > {
38 or std::is_base_of<VectorSeries, T>::value> > {
35 static void setProperties(T &dataSeries, PlottablesMap &plottables)
39 static void setProperties(T &dataSeries, PlottablesMap &plottables)
36 {
40 {
37 // Gets the number of components of the data series
41 // Gets the number of components of the data series
38 dataSeries.lockRead();
42 dataSeries.lockRead();
39 auto componentCount = dataSeries.valuesData()->componentCount();
43 auto componentCount = dataSeries.valuesData()->componentCount();
40 dataSeries.unlock();
44 dataSeries.unlock();
41
45
42 // Generates colors for each component
46 // Generates colors for each component
43 auto colors = ColorUtils::colors(Qt::blue, Qt::red, componentCount);
47 auto colors = ColorUtils::colors(Qt::blue, Qt::red, componentCount);
44
48
45 // For each component of the data series, creates a QCPGraph to add to the plot
49 // For each component of the data series, creates a QCPGraph to add to the plot
46 for (auto i = 0; i < componentCount; ++i) {
50 for (auto i = 0; i < componentCount; ++i) {
47 auto graph = plottables.at(i);
51 auto graph = plottables.at(i);
48 graph->setPen(QPen{colors.at(i)});
52 graph->setPen(QPen{colors.at(i)});
49 }
53 }
50 }
54 }
51 };
55 };
52
56
53 /**
57 /**
54 * Specialization of PlottablesSetter for spectrograms
58 * Specialization of PlottablesSetter for spectrograms
55 * @sa SpectrogramSeries
59 * @sa SpectrogramSeries
56 */
60 */
57 template <typename T>
61 template <typename T>
58 struct PlottablesSetter<T,
62 struct PlottablesSetter<T,
59 typename std::enable_if_t<std::is_base_of<SpectrogramSeries, T>::value> > {
63 typename std::enable_if_t<std::is_base_of<SpectrogramSeries, T>::value> > {
60 static void setProperties(T &, PlottablesMap &plottables)
64 static void setProperties(T &, PlottablesMap &plottables)
61 {
65 {
62 // Checks that for a spectrogram there is only one plottable, that is a colormap
66 // Checks that for a spectrogram there is only one plottable, that is a colormap
63 if (plottables.size() != 1) {
67 if (plottables.size() != 1) {
64 return;
68 return;
65 }
69 }
66
70
67 if (auto colormap = dynamic_cast<QCPColorMap *>(plottables.begin()->second)) {
71 if (auto colormap = dynamic_cast<QCPColorMap *>(plottables.begin()->second)) {
68 colormap->setInterpolate(false); // No value interpolation
72 colormap->setInterpolate(false); // No value interpolation
69 colormap->setTightBoundary(true);
73 colormap->setTightBoundary(true);
70
74
71 // Finds color scale in the colormap's plot to associate with it
75 // Finds color scale in the colormap's plot to associate with it
72 auto plot = colormap->parentPlot();
76 auto plot = colormap->parentPlot();
73 auto plotElements = plot->plotLayout()->elements(false);
77 auto plotElements = plot->plotLayout()->elements(false);
74 for (auto plotElement : plotElements) {
78 for (auto plotElement : plotElements) {
75 if (auto colorScale = dynamic_cast<QCPColorScale *>(plotElement)) {
79 if (auto colorScale = dynamic_cast<QCPColorScale *>(plotElement)) {
76 colormap->setColorScale(colorScale);
80 colormap->setColorScale(colorScale);
77 }
81 }
78 }
82 }
79
83
80 // Sets gradient used for color scale
84 // Sets gradient used for color scale
81 colormap->setGradient(DEFAULT_COLORMAP_GRADIENT);
85 colormap->setGradient(DEFAULT_COLORMAP_GRADIENT);
82 colormap->rescaleDataRange();
86 colormap->rescaleDataRange();
83 }
87 }
88 else {
89 qCCritical(LOG_PlottablesRenderingUtils()) << "Can't get colormap of the spectrogram";
90 }
84 }
91 }
85 };
92 };
86
93
87 /**
94 /**
88 * Default implementation of IPlottablesHelper, which takes data series to set plottables properties
95 * Default implementation of IPlottablesHelper, which takes data series to set plottables properties
89 * @tparam T the data series' type
96 * @tparam T the data series' type
90 */
97 */
91 template <typename T>
98 template <typename T>
92 struct PlottablesHelper : public IPlottablesHelper {
99 struct PlottablesHelper : public IPlottablesHelper {
93 explicit PlottablesHelper(T &dataSeries) : m_DataSeries{dataSeries} {}
100 explicit PlottablesHelper(T &dataSeries) : m_DataSeries{dataSeries} {}
94
101
95 void setProperties(PlottablesMap &plottables) override
102 void setProperties(PlottablesMap &plottables) override
96 {
103 {
97 PlottablesSetter<T>::setProperties(m_DataSeries, plottables);
104 PlottablesSetter<T>::setProperties(m_DataSeries, plottables);
98 }
105 }
99
106
100 T &m_DataSeries;
107 T &m_DataSeries;
101 };
108 };
102
109
103 } // namespace
110 } // namespace
104
111
105 std::unique_ptr<IPlottablesHelper>
112 std::unique_ptr<IPlottablesHelper>
106 IPlottablesHelperFactory::create(std::shared_ptr<IDataSeries> dataSeries) noexcept
113 IPlottablesHelperFactory::create(std::shared_ptr<IDataSeries> dataSeries) noexcept
107 {
114 {
108 if (auto scalarSeries = std::dynamic_pointer_cast<ScalarSeries>(dataSeries)) {
115 if (auto scalarSeries = std::dynamic_pointer_cast<ScalarSeries>(dataSeries)) {
109 return std::make_unique<PlottablesHelper<ScalarSeries> >(*scalarSeries);
116 return std::make_unique<PlottablesHelper<ScalarSeries> >(*scalarSeries);
110 }
117 }
111 else if (auto spectrogramSeries = std::dynamic_pointer_cast<SpectrogramSeries>(dataSeries)) {
118 else if (auto spectrogramSeries = std::dynamic_pointer_cast<SpectrogramSeries>(dataSeries)) {
112 return std::make_unique<PlottablesHelper<SpectrogramSeries> >(*spectrogramSeries);
119 return std::make_unique<PlottablesHelper<SpectrogramSeries> >(*spectrogramSeries);
113 }
120 }
114 else if (auto vectorSeries = std::dynamic_pointer_cast<VectorSeries>(dataSeries)) {
121 else if (auto vectorSeries = std::dynamic_pointer_cast<VectorSeries>(dataSeries)) {
115 return std::make_unique<PlottablesHelper<VectorSeries> >(*vectorSeries);
122 return std::make_unique<PlottablesHelper<VectorSeries> >(*vectorSeries);
116 }
123 }
117 else {
124 else {
118 return std::make_unique<PlottablesHelper<IDataSeries> >(*dataSeries);
125 return std::make_unique<PlottablesHelper<IDataSeries> >(*dataSeries);
119 }
126 }
120 }
127 }
@@ -1,309 +1,319
1 #include "Visualization/VisualizationTabWidget.h"
1 #include "Visualization/VisualizationTabWidget.h"
2 #include "Visualization/IVisualizationWidgetVisitor.h"
2 #include "Visualization/IVisualizationWidgetVisitor.h"
3 #include "ui_VisualizationTabWidget.h"
3 #include "ui_VisualizationTabWidget.h"
4
4
5 #include "Visualization/VisualizationGraphWidget.h"
5 #include "Visualization/VisualizationGraphWidget.h"
6 #include "Visualization/VisualizationZoneWidget.h"
6 #include "Visualization/VisualizationZoneWidget.h"
7
7
8 #include "Visualization/MacScrollBarStyle.h"
9
8 #include "Variable/VariableController.h"
10 #include "Variable/VariableController.h"
9
11
10 #include "Common/MimeTypesDef.h"
12 #include "Common/MimeTypesDef.h"
11
13
12 #include "DragAndDrop/DragDropHelper.h"
14 #include "DragAndDrop/DragDropHelper.h"
13 #include "SqpApplication.h"
15 #include "SqpApplication.h"
14
16
15 Q_LOGGING_CATEGORY(LOG_VisualizationTabWidget, "VisualizationTabWidget")
17 Q_LOGGING_CATEGORY(LOG_VisualizationTabWidget, "VisualizationTabWidget")
16
18
17 namespace {
19 namespace {
18
20
19 /// Generates a default name for a new zone, according to the number of zones already displayed in
21 /// Generates a default name for a new zone, according to the number of zones already displayed in
20 /// the tab
22 /// the tab
21 QString defaultZoneName(const QLayout &layout)
23 QString defaultZoneName(const QLayout &layout)
22 {
24 {
23 auto count = 0;
25 auto count = 0;
24 for (auto i = 0; i < layout.count(); ++i) {
26 for (auto i = 0; i < layout.count(); ++i) {
25 if (dynamic_cast<VisualizationZoneWidget *>(layout.itemAt(i)->widget())) {
27 if (dynamic_cast<VisualizationZoneWidget *>(layout.itemAt(i)->widget())) {
26 count++;
28 count++;
27 }
29 }
28 }
30 }
29
31
30 return QObject::tr("Zone %1").arg(count + 1);
32 return QObject::tr("Zone %1").arg(count + 1);
31 }
33 }
32
34
33 /**
35 /**
34 * Applies a function to all zones of the tab represented by its layout
36 * Applies a function to all zones of the tab represented by its layout
35 * @param layout the layout that contains zones
37 * @param layout the layout that contains zones
36 * @param fun the function to apply to each zone
38 * @param fun the function to apply to each zone
37 */
39 */
38 template <typename Fun>
40 template <typename Fun>
39 void processZones(QLayout &layout, Fun fun)
41 void processZones(QLayout &layout, Fun fun)
40 {
42 {
41 for (auto i = 0; i < layout.count(); ++i) {
43 for (auto i = 0; i < layout.count(); ++i) {
42 if (auto item = layout.itemAt(i)) {
44 if (auto item = layout.itemAt(i)) {
43 if (auto visualizationZoneWidget
45 if (auto visualizationZoneWidget
44 = dynamic_cast<VisualizationZoneWidget *>(item->widget())) {
46 = dynamic_cast<VisualizationZoneWidget *>(item->widget())) {
45 fun(*visualizationZoneWidget);
47 fun(*visualizationZoneWidget);
46 }
48 }
47 }
49 }
48 }
50 }
49 }
51 }
50
52
51 } // namespace
53 } // namespace
52
54
53 struct VisualizationTabWidget::VisualizationTabWidgetPrivate {
55 struct VisualizationTabWidget::VisualizationTabWidgetPrivate {
54 explicit VisualizationTabWidgetPrivate(const QString &name) : m_Name{name} {}
56 explicit VisualizationTabWidgetPrivate(const QString &name) : m_Name{name} {}
55
57
56 QString m_Name;
58 QString m_Name;
57
59
60 #ifdef Q_OS_MAC
61 std::unique_ptr<MacScrollBarStyle> m_MacScrollBarStyle = std::make_unique<MacScrollBarStyle>();
62 #endif
63
58 void dropGraph(int index, VisualizationTabWidget *tabWidget);
64 void dropGraph(int index, VisualizationTabWidget *tabWidget);
59 void dropZone(int index, VisualizationTabWidget *tabWidget);
65 void dropZone(int index, VisualizationTabWidget *tabWidget);
60 void dropVariables(const QList<std::shared_ptr<Variable> > &variables, int index,
66 void dropVariables(const QList<std::shared_ptr<Variable> > &variables, int index,
61 VisualizationTabWidget *tabWidget);
67 VisualizationTabWidget *tabWidget);
62 };
68 };
63
69
64 VisualizationTabWidget::VisualizationTabWidget(const QString &name, QWidget *parent)
70 VisualizationTabWidget::VisualizationTabWidget(const QString &name, QWidget *parent)
65 : QWidget{parent},
71 : QWidget{parent},
66 ui{new Ui::VisualizationTabWidget},
72 ui{new Ui::VisualizationTabWidget},
67 impl{spimpl::make_unique_impl<VisualizationTabWidgetPrivate>(name)}
73 impl{spimpl::make_unique_impl<VisualizationTabWidgetPrivate>(name)}
68 {
74 {
69 ui->setupUi(this);
75 ui->setupUi(this);
70
76
77 #ifdef Q_OS_MAC
78 impl->m_MacScrollBarStyle->selfInstallOn(ui->scrollArea, true);
79 #endif
80
71 ui->dragDropContainer->setPlaceHolderType(DragDropHelper::PlaceHolderType::Zone, "Zone");
81 ui->dragDropContainer->setPlaceHolderType(DragDropHelper::PlaceHolderType::Zone, "Zone");
72 ui->dragDropContainer->layout()->setContentsMargins(0, 0, 0, 5);
82 ui->dragDropContainer->layout()->setContentsMargins(0, 0, 0, 5);
73 ui->dragDropContainer->addAcceptedMimeType(
83 ui->dragDropContainer->addAcceptedMimeType(
74 MIME_TYPE_GRAPH, VisualizationDragDropContainer::DropBehavior::Inserted);
84 MIME_TYPE_GRAPH, VisualizationDragDropContainer::DropBehavior::Inserted);
75 ui->dragDropContainer->addAcceptedMimeType(
85 ui->dragDropContainer->addAcceptedMimeType(
76 MIME_TYPE_ZONE, VisualizationDragDropContainer::DropBehavior::Inserted);
86 MIME_TYPE_ZONE, VisualizationDragDropContainer::DropBehavior::Inserted);
77 ui->dragDropContainer->addAcceptedMimeType(
87 ui->dragDropContainer->addAcceptedMimeType(
78 MIME_TYPE_VARIABLE_LIST, VisualizationDragDropContainer::DropBehavior::Inserted);
88 MIME_TYPE_VARIABLE_LIST, VisualizationDragDropContainer::DropBehavior::Inserted);
79
89
80 ui->dragDropContainer->setAcceptMimeDataFunction([this](auto mimeData) {
90 ui->dragDropContainer->setAcceptMimeDataFunction([this](auto mimeData) {
81 return sqpApp->dragDropHelper().checkMimeDataForVisualization(mimeData,
91 return sqpApp->dragDropHelper().checkMimeDataForVisualization(mimeData,
82 ui->dragDropContainer);
92 ui->dragDropContainer);
83 });
93 });
84
94
85 connect(ui->dragDropContainer, &VisualizationDragDropContainer::dropOccuredInContainer, this,
95 connect(ui->dragDropContainer, &VisualizationDragDropContainer::dropOccuredInContainer, this,
86 &VisualizationTabWidget::dropMimeData);
96 &VisualizationTabWidget::dropMimeData);
87
97
88 sqpApp->dragDropHelper().addDragDropScrollArea(ui->scrollArea);
98 sqpApp->dragDropHelper().addDragDropScrollArea(ui->scrollArea);
89
99
90 // Widget is deleted when closed
100 // Widget is deleted when closed
91 setAttribute(Qt::WA_DeleteOnClose);
101 setAttribute(Qt::WA_DeleteOnClose);
92 }
102 }
93
103
94 VisualizationTabWidget::~VisualizationTabWidget()
104 VisualizationTabWidget::~VisualizationTabWidget()
95 {
105 {
96 sqpApp->dragDropHelper().removeDragDropScrollArea(ui->scrollArea);
106 sqpApp->dragDropHelper().removeDragDropScrollArea(ui->scrollArea);
97 delete ui;
107 delete ui;
98 }
108 }
99
109
100 void VisualizationTabWidget::addZone(VisualizationZoneWidget *zoneWidget)
110 void VisualizationTabWidget::addZone(VisualizationZoneWidget *zoneWidget)
101 {
111 {
102 ui->dragDropContainer->addDragWidget(zoneWidget);
112 ui->dragDropContainer->addDragWidget(zoneWidget);
103 }
113 }
104
114
105 void VisualizationTabWidget::insertZone(int index, VisualizationZoneWidget *zoneWidget)
115 void VisualizationTabWidget::insertZone(int index, VisualizationZoneWidget *zoneWidget)
106 {
116 {
107 ui->dragDropContainer->insertDragWidget(index, zoneWidget);
117 ui->dragDropContainer->insertDragWidget(index, zoneWidget);
108 }
118 }
109
119
110 VisualizationZoneWidget *VisualizationTabWidget::createZone(std::shared_ptr<Variable> variable)
120 VisualizationZoneWidget *VisualizationTabWidget::createZone(std::shared_ptr<Variable> variable)
111 {
121 {
112 return createZone({variable}, -1);
122 return createZone({variable}, -1);
113 }
123 }
114
124
115 VisualizationZoneWidget *
125 VisualizationZoneWidget *
116 VisualizationTabWidget::createZone(const QList<std::shared_ptr<Variable> > &variables, int index)
126 VisualizationTabWidget::createZone(const QList<std::shared_ptr<Variable> > &variables, int index)
117 {
127 {
118 auto zoneWidget = createEmptyZone(index);
128 auto zoneWidget = createEmptyZone(index);
119
129
120 // Creates a new graph into the zone
130 // Creates a new graph into the zone
121 zoneWidget->createGraph(variables, index);
131 zoneWidget->createGraph(variables, index);
122
132
123 return zoneWidget;
133 return zoneWidget;
124 }
134 }
125
135
126 VisualizationZoneWidget *VisualizationTabWidget::createEmptyZone(int index)
136 VisualizationZoneWidget *VisualizationTabWidget::createEmptyZone(int index)
127 {
137 {
128 auto zoneWidget
138 auto zoneWidget
129 = new VisualizationZoneWidget{defaultZoneName(*ui->dragDropContainer->layout()), this};
139 = new VisualizationZoneWidget{defaultZoneName(*ui->dragDropContainer->layout()), this};
130 this->insertZone(index, zoneWidget);
140 this->insertZone(index, zoneWidget);
131
141
132 return zoneWidget;
142 return zoneWidget;
133 }
143 }
134
144
135 void VisualizationTabWidget::accept(IVisualizationWidgetVisitor *visitor)
145 void VisualizationTabWidget::accept(IVisualizationWidgetVisitor *visitor)
136 {
146 {
137 if (visitor) {
147 if (visitor) {
138 visitor->visitEnter(this);
148 visitor->visitEnter(this);
139
149
140 // Apply visitor to zone children: widgets different from zones are not visited (no action)
150 // Apply visitor to zone children: widgets different from zones are not visited (no action)
141 processZones(tabLayout(), [visitor](VisualizationZoneWidget &zoneWidget) {
151 processZones(tabLayout(), [visitor](VisualizationZoneWidget &zoneWidget) {
142 zoneWidget.accept(visitor);
152 zoneWidget.accept(visitor);
143 });
153 });
144
154
145 visitor->visitLeave(this);
155 visitor->visitLeave(this);
146 }
156 }
147 else {
157 else {
148 qCCritical(LOG_VisualizationTabWidget()) << tr("Can't visit widget : the visitor is null");
158 qCCritical(LOG_VisualizationTabWidget()) << tr("Can't visit widget : the visitor is null");
149 }
159 }
150 }
160 }
151
161
152 bool VisualizationTabWidget::canDrop(const Variable &variable) const
162 bool VisualizationTabWidget::canDrop(const Variable &variable) const
153 {
163 {
154 // A tab can always accomodate a variable
164 // A tab can always accomodate a variable
155 Q_UNUSED(variable);
165 Q_UNUSED(variable);
156 return true;
166 return true;
157 }
167 }
158
168
159 bool VisualizationTabWidget::contains(const Variable &variable) const
169 bool VisualizationTabWidget::contains(const Variable &variable) const
160 {
170 {
161 Q_UNUSED(variable);
171 Q_UNUSED(variable);
162 return false;
172 return false;
163 }
173 }
164
174
165 QString VisualizationTabWidget::name() const
175 QString VisualizationTabWidget::name() const
166 {
176 {
167 return impl->m_Name;
177 return impl->m_Name;
168 }
178 }
169
179
170 void VisualizationTabWidget::closeEvent(QCloseEvent *event)
180 void VisualizationTabWidget::closeEvent(QCloseEvent *event)
171 {
181 {
172 // Closes zones in the tab
182 // Closes zones in the tab
173 processZones(tabLayout(), [](VisualizationZoneWidget &zoneWidget) { zoneWidget.close(); });
183 processZones(tabLayout(), [](VisualizationZoneWidget &zoneWidget) { zoneWidget.close(); });
174
184
175 QWidget::closeEvent(event);
185 QWidget::closeEvent(event);
176 }
186 }
177
187
178 QLayout &VisualizationTabWidget::tabLayout() const noexcept
188 QLayout &VisualizationTabWidget::tabLayout() const noexcept
179 {
189 {
180 return *ui->dragDropContainer->layout();
190 return *ui->dragDropContainer->layout();
181 }
191 }
182
192
183 void VisualizationTabWidget::dropMimeData(int index, const QMimeData *mimeData)
193 void VisualizationTabWidget::dropMimeData(int index, const QMimeData *mimeData)
184 {
194 {
185 if (mimeData->hasFormat(MIME_TYPE_GRAPH)) {
195 if (mimeData->hasFormat(MIME_TYPE_GRAPH)) {
186 impl->dropGraph(index, this);
196 impl->dropGraph(index, this);
187 }
197 }
188 else if (mimeData->hasFormat(MIME_TYPE_ZONE)) {
198 else if (mimeData->hasFormat(MIME_TYPE_ZONE)) {
189 impl->dropZone(index, this);
199 impl->dropZone(index, this);
190 }
200 }
191 else if (mimeData->hasFormat(MIME_TYPE_VARIABLE_LIST)) {
201 else if (mimeData->hasFormat(MIME_TYPE_VARIABLE_LIST)) {
192 auto variables = sqpApp->variableController().variablesForMimeData(
202 auto variables = sqpApp->variableController().variablesForMimeData(
193 mimeData->data(MIME_TYPE_VARIABLE_LIST));
203 mimeData->data(MIME_TYPE_VARIABLE_LIST));
194 impl->dropVariables(variables, index, this);
204 impl->dropVariables(variables, index, this);
195 }
205 }
196 else {
206 else {
197 qCWarning(LOG_VisualizationZoneWidget())
207 qCWarning(LOG_VisualizationZoneWidget())
198 << tr("VisualizationTabWidget::dropMimeData, unknown MIME data received.");
208 << tr("VisualizationTabWidget::dropMimeData, unknown MIME data received.");
199 }
209 }
200 }
210 }
201
211
202 void VisualizationTabWidget::VisualizationTabWidgetPrivate::dropGraph(
212 void VisualizationTabWidget::VisualizationTabWidgetPrivate::dropGraph(
203 int index, VisualizationTabWidget *tabWidget)
213 int index, VisualizationTabWidget *tabWidget)
204 {
214 {
205 auto &helper = sqpApp->dragDropHelper();
215 auto &helper = sqpApp->dragDropHelper();
206
216
207 auto graphWidget = qobject_cast<VisualizationGraphWidget *>(helper.getCurrentDragWidget());
217 auto graphWidget = qobject_cast<VisualizationGraphWidget *>(helper.getCurrentDragWidget());
208 if (!graphWidget) {
218 if (!graphWidget) {
209 qCWarning(LOG_VisualizationZoneWidget())
219 qCWarning(LOG_VisualizationZoneWidget())
210 << tr("VisualizationTabWidget::dropGraph, drop aborted, the dropped graph is not "
220 << tr("VisualizationTabWidget::dropGraph, drop aborted, the dropped graph is not "
211 "found or invalid.");
221 "found or invalid.");
212 Q_ASSERT(false);
222 Q_ASSERT(false);
213 return;
223 return;
214 }
224 }
215
225
216 auto parentDragDropContainer
226 auto parentDragDropContainer
217 = qobject_cast<VisualizationDragDropContainer *>(graphWidget->parentWidget());
227 = qobject_cast<VisualizationDragDropContainer *>(graphWidget->parentWidget());
218 if (!parentDragDropContainer) {
228 if (!parentDragDropContainer) {
219 qCWarning(LOG_VisualizationZoneWidget())
229 qCWarning(LOG_VisualizationZoneWidget())
220 << tr("VisualizationTabWidget::dropGraph, drop aborted, the parent container of "
230 << tr("VisualizationTabWidget::dropGraph, drop aborted, the parent container of "
221 "the dropped graph is not found.");
231 "the dropped graph is not found.");
222 Q_ASSERT(false);
232 Q_ASSERT(false);
223 return;
233 return;
224 }
234 }
225
235
226 auto nbGraph = parentDragDropContainer->countDragWidget();
236 auto nbGraph = parentDragDropContainer->countDragWidget();
227
237
228 const auto &variables = graphWidget->variables();
238 const auto &variables = graphWidget->variables();
229
239
230 if (!variables.isEmpty()) {
240 if (!variables.isEmpty()) {
231 // Abort the requests for the variables (if any)
241 // Abort the requests for the variables (if any)
232 // Commented, because it's not sure if it's needed or not
242 // Commented, because it's not sure if it's needed or not
233 // for (const auto& var : variables)
243 // for (const auto& var : variables)
234 //{
244 //{
235 // sqpApp->variableController().onAbortProgressRequested(var);
245 // sqpApp->variableController().onAbortProgressRequested(var);
236 //}
246 //}
237
247
238 if (nbGraph == 1) {
248 if (nbGraph == 1) {
239 // This is the only graph in the previous zone, close the zone
249 // This is the only graph in the previous zone, close the zone
240 helper.delayedCloseWidget(graphWidget->parentZoneWidget());
250 helper.delayedCloseWidget(graphWidget->parentZoneWidget());
241 }
251 }
242 else {
252 else {
243 // Close the graph
253 // Close the graph
244 helper.delayedCloseWidget(graphWidget);
254 helper.delayedCloseWidget(graphWidget);
245 }
255 }
246
256
247 tabWidget->createZone(variables, index);
257 tabWidget->createZone(variables, index);
248 }
258 }
249 else {
259 else {
250 // The graph is empty, create an empty zone and move the graph inside
260 // The graph is empty, create an empty zone and move the graph inside
251
261
252 auto parentZoneWidget = graphWidget->parentZoneWidget();
262 auto parentZoneWidget = graphWidget->parentZoneWidget();
253
263
254 parentDragDropContainer->layout()->removeWidget(graphWidget);
264 parentDragDropContainer->layout()->removeWidget(graphWidget);
255
265
256 auto zoneWidget = tabWidget->createEmptyZone(index);
266 auto zoneWidget = tabWidget->createEmptyZone(index);
257 zoneWidget->addGraph(graphWidget);
267 zoneWidget->addGraph(graphWidget);
258
268
259 // Close the old zone if it was the only graph inside
269 // Close the old zone if it was the only graph inside
260 if (nbGraph == 1) {
270 if (nbGraph == 1) {
261 helper.delayedCloseWidget(parentZoneWidget);
271 helper.delayedCloseWidget(parentZoneWidget);
262 }
272 }
263 }
273 }
264 }
274 }
265
275
266 void VisualizationTabWidget::VisualizationTabWidgetPrivate::dropZone(
276 void VisualizationTabWidget::VisualizationTabWidgetPrivate::dropZone(
267 int index, VisualizationTabWidget *tabWidget)
277 int index, VisualizationTabWidget *tabWidget)
268 {
278 {
269 auto &helper = sqpApp->dragDropHelper();
279 auto &helper = sqpApp->dragDropHelper();
270
280
271 auto zoneWidget = qobject_cast<VisualizationZoneWidget *>(helper.getCurrentDragWidget());
281 auto zoneWidget = qobject_cast<VisualizationZoneWidget *>(helper.getCurrentDragWidget());
272 if (!zoneWidget) {
282 if (!zoneWidget) {
273 qCWarning(LOG_VisualizationZoneWidget())
283 qCWarning(LOG_VisualizationZoneWidget())
274 << tr("VisualizationTabWidget::dropZone, drop aborted, the dropped zone is not "
284 << tr("VisualizationTabWidget::dropZone, drop aborted, the dropped zone is not "
275 "found or invalid.");
285 "found or invalid.");
276 Q_ASSERT(false);
286 Q_ASSERT(false);
277 return;
287 return;
278 }
288 }
279
289
280 auto parentDragDropContainer
290 auto parentDragDropContainer
281 = qobject_cast<VisualizationDragDropContainer *>(zoneWidget->parentWidget());
291 = qobject_cast<VisualizationDragDropContainer *>(zoneWidget->parentWidget());
282 if (!parentDragDropContainer) {
292 if (!parentDragDropContainer) {
283 qCWarning(LOG_VisualizationZoneWidget())
293 qCWarning(LOG_VisualizationZoneWidget())
284 << tr("VisualizationTabWidget::dropZone, drop aborted, the parent container of "
294 << tr("VisualizationTabWidget::dropZone, drop aborted, the parent container of "
285 "the dropped zone is not found.");
295 "the dropped zone is not found.");
286 Q_ASSERT(false);
296 Q_ASSERT(false);
287 return;
297 return;
288 }
298 }
289
299
290 // Simple move of the zone, no variable operation associated
300 // Simple move of the zone, no variable operation associated
291 parentDragDropContainer->layout()->removeWidget(zoneWidget);
301 parentDragDropContainer->layout()->removeWidget(zoneWidget);
292 tabWidget->ui->dragDropContainer->insertDragWidget(index, zoneWidget);
302 tabWidget->ui->dragDropContainer->insertDragWidget(index, zoneWidget);
293 }
303 }
294
304
295 void VisualizationTabWidget::VisualizationTabWidgetPrivate::dropVariables(
305 void VisualizationTabWidget::VisualizationTabWidgetPrivate::dropVariables(
296 const QList<std::shared_ptr<Variable> > &variables, int index,
306 const QList<std::shared_ptr<Variable> > &variables, int index,
297 VisualizationTabWidget *tabWidget)
307 VisualizationTabWidget *tabWidget)
298 {
308 {
299 // Note: the AcceptMimeDataFunction (set on the drop container) ensure there is a single and
309 // Note: the AcceptMimeDataFunction (set on the drop container) ensure there is a single and
300 // compatible variable here
310 // compatible variable here
301 if (variables.count() > 1) {
311 if (variables.count() > 1) {
302 qCWarning(LOG_VisualizationZoneWidget())
312 qCWarning(LOG_VisualizationZoneWidget())
303 << tr("VisualizationTabWidget::dropVariables, dropping multiple variables, operation "
313 << tr("VisualizationTabWidget::dropVariables, dropping multiple variables, operation "
304 "aborted.");
314 "aborted.");
305 return;
315 return;
306 }
316 }
307
317
308 tabWidget->createZone(variables, index);
318 tabWidget->createZone(variables, index);
309 }
319 }
General Comments 0
You need to be logged in to leave comments. Login now