Currently job artifacts in CI/CD pipelines on LRZ GitLab never expire. Starting from Wed 26.1.2022 the default expiration time will be 30 days (GitLab default). Currently existing artifacts in already completed jobs will not be affected by the change. The latest artifacts for all jobs in the latest successful pipelines will be kept. More information: https://gitlab.lrz.de/help/user/admin_area/settings/continuous_integration.html#default-artifacts-expiration

abstractpipeline.h 11.3 KB
Newer Older
1
2
// ================================================================================================
// 
schultezub's avatar
schultezub committed
3
// This file is part of the CAMPVis Software Framework.
4
// 
5
// If not explicitly stated otherwise: Copyright (C) 2012-2015, all rights reserved,
schultezub's avatar
schultezub committed
6
//      Christian Schulte zu Berge <christian.szb@in.tum.de>
7
//      Chair for Computer Aided Medical Procedures
8
9
//      Technische Universitaet Muenchen
//      Boltzmannstr. 3, 85748 Garching b. Muenchen, Germany
10
// 
schultezub's avatar
schultezub committed
11
// For a full list of authors and contributors, please refer to the file "AUTHORS.txt".
12
// 
13
14
15
16
// Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file 
// except in compliance with the License. You may obtain a copy of the License at
// 
// http://www.apache.org/licenses/LICENSE-2.0
17
// 
18
19
20
21
// Unless required by applicable law or agreed to in writing, software distributed under the 
// License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, 
// either express or implied. See the License for the specific language governing permissions 
// and limitations under the License.
22
23
24
// 
// ================================================================================================

25
26
27
#ifndef ABSTRACTPIPELINE_H__
#define ABSTRACTPIPELINE_H__

28
#include "sigslot/sigslot.h"
29

30
31
32
33
34
#include "cgt/logmanager.h"
#include "cgt/runnable.h"
#include "cgt/vector.h"
#include "cgt/event/eventhandler.h"
#include "cgt/event/eventlistener.h"
35

36
37
#include <tbb/spin_mutex.h>
#include <tbb/mutex.h>
38

39
#include "core/coreapi.h"
40
#include "core/datastructures/datacontainer.h"
41
#include "core/pipeline/pipelinepainter.h"
42
43
#include "core/properties/datanameproperty.h"
#include "core/properties/floatingpointproperty.h"
schultezub's avatar
schultezub committed
44
#include "core/properties/propertycollection.h"
45

46
#include <map>
47
#include <memory>
48
49
#include <vector>

50
namespace cgt {
51
52
53
    class GLCanvas;
}

schultezub's avatar
schultezub committed
54
namespace campvis {
schultezub's avatar
schultezub committed
55
56
    class AbstractProcessor;

57
    /**
schultezub's avatar
schultezub committed
58
     * Abstract base class for CAMPVis Pipelines.
59
     */
60
    class CAMPVIS_CORE_API AbstractPipeline : public HasPropertyCollection, public cgt::RunnableWithConditionalWait, public cgt::EventHandler, public cgt::EventListener {
61
62
63
    public:
        /**
         * Creates a AbstractPipeline.
64
65
         * If you derive from AbstractPipeline, you will have to implement the pipeline evaluation
         * logic yourself. You might want to have a look at AutoEvaluationPipeline.
66
         * 
67
68
         * \param   dataContainer   Reference to the DataContainer containing local working set of data
         *                          for this pipeline, must be valid the whole lifetime of this pipeline.
69
         */
70
        explicit AbstractPipeline(DataContainer& dataContainer);
71
72
73
74
75

        /**
         * Virtual Destructor
         **/
        virtual ~AbstractPipeline();
76
77
78
79
80
        
        /**
         * Gets the name of this very pipeline. To be defined by every subclass.
         * \return  The name of this pipeline.
         */
81
        virtual std::string getName() const = 0;
82
83
84


        /**
85
86
87
         * Initializes this pipeline, its OpenGL context  and all of its processors.
         * Everything that requires a valid OpenGL context, valid construction of all other 
         * processors/properties or is otherwise expensive gets in here.
88
         * 
89
         * \note    Must be called with a valid and locked OpenGL context.
90
         * \note    When overwriting this method, make sure to call the base class version first.
91
         */
92
        virtual void init();
93

94
        /**
95
96
97
98
99
         * Deinitializes this pipeline, its OpenGL context and all of its processors.
         * Everything that requires a valid OpenGL context, cannont be executed during destruction
         * or is otherwise expensive gets in here.
         * 
         * \note    Must be called with a valid and locked OpenGL context.
100
101
102
         * \note    When overwriting this method, make sure to call the base class version first.
         */
        virtual void deinit();
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
        
        /**
         * Adds the processor \a processor to this pipeline's processor list.
         * \note    The s_invalidated signal of each processor on this list will be automatically 
         *          connected to onProcessorInvalidated() during initialization and disconnected
         *          during deinitialization.
         * \param   processor   The processor to add.
         */
        virtual void addProcessor(AbstractProcessor* processor);
                
        /**
         * Performs the event handling for the assigned canvas.
         * Default behaviour is to execute all assigned EventHandlers, may be overwritten by subclasses.
         * \param e     event parameters
         */
118
        virtual void onEvent(cgt::Event* e);
119

120
121
122
123
124
125
        /**
         * Entrance point for the pipeline thread.
         * \see Runnable::run
         */
        virtual void run();

126
127
128
129
130
        /**
         * Executes this pipeline.
         * To be implemented in the subclass.
         */
        virtual void executePipeline() = 0;
131
132
133
134
135
        
        /**
         * Sets the resultDirty flag of this pipeline and starts its execution if necessary.
         */
        void setPipelineDirty();
136

137
138
139
140
141
142
143
        /**
         * Paints an additional overlay directly onto the frame buffer.
         * Gets called from CampvisPainter just after copying the rendered image and just before
         * swapping the canvas' buffers. The default implementation performs nothing.
         */
        virtual void paint();

schultezub's avatar
schultezub committed
144
        /**
145
         * Returns the DataContainer of this pipeline, const version.
146
         * \return _dataContainer
schultezub's avatar
schultezub committed
147
148
         */
        const DataContainer& getDataContainer() const;
149

150
151
        /**
         * Returns the DataContainer of this pipeline, non-const version.
152
         * \return _dataContainer
153
154
155
         */
        DataContainer& getDataContainer();

156
157
158
159
160
161
        /**
         * Returns the list of processors of this pipeline.
         * \return  _processors
         */
        const std::vector<AbstractProcessor*>& getProcessors() const;

162
163
164
165
166
167
168
        /**
         * Returns the first processor of this pipeline whose name matches \a name.
         * \param   name    The name of the processor to find
         * \return  The first processor whose name matches \a name, 0 if no such processor exists.
         */
        AbstractProcessor* getProcessor(const std::string& name) const;

169
170
171
172
173
        /**
         * Returns the first processor of this pipeline whose name matches \a name.
         * \param   index    The index of the processor to get
         * \return  The first processor whose name matches \a name, 0 if no such processor exists.
         */
174
        AbstractProcessor* getProcessor(size_t index) const;
175

176
177
178
179
180
181
182
183
184
185
186
187
        /**
         * Gets the flag whether this pipeline is currently enabled.
         * \return _enabled
         */
        bool getEnabled() const;

        /**
         * Sets the flag whether this pipeline is currently enabled.
         * \param   enabled     New flag whether this pipeline is currently enabled.
         */
        void setEnabled(bool enabled);

188
        /**
189
190
         * Sets the Canvas hosting the OpenGL context for this pipeline.
         * \param   canvas  Canvas hosting the OpenGL context for this pipeline
191
         */
192
        void setCanvas(cgt::GLCanvas* canvas);
193
194

        /**
195
196
         * Sets the size of the render target
         * \param size  New viewport dimensions
197
         */
198
        void setRenderTargetSize(const cgt::ivec2& size);
199

schultezub's avatar
schultezub committed
200
        /**
201
202
         * Returns the viewport size of the target canvas
         * \return _canvasSize
schultezub's avatar
schultezub committed
203
         */
204
        const cgt::ivec2& getRenderTargetSize() const;
schultezub's avatar
schultezub committed
205
206

        /**
207
208
         * Returns the ID of the render target image to be rendered to the canvas
         * \return  The DataHandle named _renderTargetID in the pipeline's DataContainer, 0 if no such handle exists.
schultezub's avatar
schultezub committed
209
         */
210
        const std::string& getRenderTargetID() const;
211
212
213
214
215
        
        /**
         * Returns the canvas size 
         * \return  The IVec2Property with current canvas size on it
         */
216
        IVec2Property& getCanvasSize() { return _canvasSize; }
217

218
219
220
221
222
223
        /**
         * Returns this pipelines PipelinePainter.
         * \return  _painter
         */
        const std::unique_ptr<PipelinePainter>& getPipelinePainter() const;

224
225
226
227
        /// Signal emitted at the end of AbstractPipeline::init()
        sigslot::signal0 s_init;
        /// Signal emitted at the beginning of AbstractPipeline::deinit()
        sigslot::signal0 s_deinit;
228
229

    protected:
230
231
232
233
234
235
        /**
         * Forces the execution of the given processor regardless of its invalidation or enabled state.
         * \param   processor   Processor to execute.
         */
        void forceExecuteProcessor(AbstractProcessor* processor);

236
237
        /**
         * Executes the processor \a processor on the pipeline's data and locks its properties meanwhile.
238
239
         * \param   processor   Processor to execute.
         */
240
        void executeProcessor(AbstractProcessor* processor);
241
242
243
244
245
246
247
248
        
        /**
         * Executes \a processor and afterwards checks the OpenGL state to be valid.
         * \note    Only call from with a valid OpenGL context
         * \param   processor   Processor to execute
         */
        void executeProcessorAndCheckOpenGLState(AbstractProcessor* processor);

249
250
251
252
253
254
255
256
        /**
         * Gets called when the data collection of this pipeline has changed and thus has notified its observers.
         * If \a name equals the name of the renderTarget, setPipelineDirty will be called.
         * \param   name    Name of the added data.
         * \param   dh      DataHandle to the newly added data.
         */
        virtual void onDataContainerDataAdded(std::string name, DataHandle dh);

257
258
259
260
261
262
        /**
         * Slot getting called when one of the observed properties changed and notifies its observers.
         * The default behaviour is just to set the invalidation level to invalid.
         * \param   prop    Property that emitted the signal
         */
        virtual void onPropertyChanged(const AbstractProperty* prop);
263
264


265
        /// Pointer to the DataContainer containing local working set of data for this Pipeline, must not be 0.
266
        DataContainer* _dataContainer;
267

268
        std::vector<AbstractProcessor*> _processors;        ///< List of all processors of this pipeline
schultezub's avatar
schultezub committed
269

270
271
        cgt::GLCanvas* _canvas;                             ///< Canvas hosting the OpenGL context for this pipeline. We do *not* own this pointer.
        std::unique_ptr<PipelinePainter> _painter;          ///< PipelinePainter used to paint this pipeline's result onto the canvas.
272
273
274
275
        IVec2Property _canvasSize;                          ///< original canvas size
        bool _ignoreCanvasSizeUpdate;

        DataNameProperty _renderTargetID;                   ///< ID of the render target image to be rendered to the canvas
276

277
278
279
280
    private:
        tbb::atomic<bool> _enabled;                         ///< flag whether this pipeline is currently enabled
        tbb::atomic<bool> _pipelineDirty;                   ///< Flag whether this pipeline is dirty and executePipeline() needs to be called.

281
        static const std::string loggerCat_;
282

283
284
285
286
287
288
    };

}


#endif // ABSTRACTPIPELINE_H__