FiberVISH 0.2
Fish - The Fiber Bundle API for the Vish Visualization Shell
VertexFieldShader.hpp
1#ifndef __ANEMONEFISH_VERTEXFIELD_SHADER_HPP
2#define __ANEMONEFISH_VERTEXFIELD_SHADER_HPP
3
4#include <fish/pond/anemonefish/FieldAnemone.hpp>
5#include <ocean/Anemonia/FloatOrigin.hpp>
6#include "FloatingAnemone.hpp"
7
8#include <utility>
9
10/*
11 The Programmable header file is includered merely for convenience of
12 derived classes, it is not used here.
13 */
14#include <ocean/Anemonia/Programmable.hpp>
15
16namespace Wizt
17{
18
19#if 0
20template <typename T>
21class has_getShaderConditionals
22{
23 /*
24private:
25
26 template<typename U, U> struct SFINAE {};
27
28 template<typename U> static char Test(SFINAE<
29 string (U::*)(Anemone&RenderAnemone,
30 const FieldAnemone::AnemoneCreationContext&ARC,
31 const RefPtr<FieldAnemone::AnemoneExplorer>&AE) const, &U::getShaderConditionals>*);
32 template<typename U> static int Test(...);
33
34public:
35static const bool value = sizeof(Test<T>(0)) == sizeof(char);
36 */
37
38 struct Fallback {};
39
40 template<typename C>
41static auto Test(std::nullptr_t)
42 -> decltype( std::declval<C>().getShaderPrefix(
43 std::declval<Anemone>(),
44 std::declval<const FieldAnemone::AnemoneCreationContext>(),
45 std::declval<const RefPtr<FieldAnemone::AnemoneExplorer>>()
46 ) );
47
48// template<typename>
49//static Fallback Test(...);
50
51public:
52static bool const value = !std::is_same<decltype(Test<T>(nullptr)),Fallback>::value;
53
54};
55
56/*
57template <bool>
58struct GetDisplayShaderPrefixFunction;
59
60template <> struct GetDisplayShaderPrefixFunction<true>
61{
62 template <class DisplayShader>
63static string call(const DisplayShader&DS,
64 Anemone&RenderAnemone,
65 const FieldAnemone::AnemoneCreationContext&ARC,
66 const RefPtr<FieldAnemone::AnemoneExplorer>&AE)
67{
68 return DS.getShaderConditionals(RenderAnemone, ARC, AE);
69}
70};
71
72template <> struct GetDisplayShaderPrefixFunction<false>
73{
74 template <class DisplayShader>
75static string call(const DisplayShader&DS,
76 Anemone&RenderAnemone,
77 const FieldAnemone::AnemoneCreationContext&ARC,
78 const RefPtr<FieldAnemone::AnemoneExplorer>&AE)
79{
80 return "";
81}
82};
83*/
84#endif
85
86template <class DisplayShader>
87inline string getShaderConditionals(const DisplayShader&DS,
88 Anemone&RenderAnemone,
89 const FieldAnemone::AnemoneCreationContext&ARC,
90 const RefPtr<FieldAnemone::AnemoneExplorer>&AE, std::true_type)
91{
92 return DS.getShaderConditionals(RenderAnemone, ARC, AE);
93}
94
95template <class DisplayShader>
96inline string getShaderConditionals(const DisplayShader&DS,
97 Anemone&RenderAnemone,
98 const FieldAnemone::AnemoneCreationContext&ARC,
99 const RefPtr<FieldAnemone::AnemoneExplorer>&AE, std::false_type)
100{
101 return "";
102}
103
104template <class DisplayShader>
105inline string getShaderConditionals(const DisplayShader&DS,
106 Anemone&RenderAnemone,
107 const FieldAnemone::AnemoneCreationContext&ARC,
108 const RefPtr<FieldAnemone::AnemoneExplorer>&AE)
109{
110/*
111 static_assert(has_getShaderConditionals<DisplayShader>::value, "Has NOT shader conditional.");
112
113 return getShaderConditionals(DS, RenderAnemone, ARC, AE,
114 std::integral_constant<bool, has_getShaderConditionals<DisplayShader>::value>());
115*/
116
117// static_assert(DisplayShader::hasShaderConditionals , "Has NOT shader conditional.");
118 return getShaderConditionals(DS, RenderAnemone, ARC, AE,
120}
121
123{
124 template <class T, int EL = VSlotContainer::InvalidExpertLevel >
125 using in = VObject::in<T, EL>;
126};
127
128template <class PrimaryType>
130{
131 typedef PrimaryType FieldType;
132};
133
134
153template <class DisplayShader, int RenderCategory = HEAVY_OBJECT>
154class VertexFieldShader : public TypedFieldAnemone< typename DisplayShader::FieldType >
155 , public DisplayShader
156 , public FloatingAnemone
157{
158public:
159
160 typedef typename DisplayShader::FieldType Field_Type_t;
161
163
165
166 typedef typename TypedFieldAnemone_t::GridAnemoneState
167 GridAnemoneState;
168
169 VertexFieldShader(const string&name, int, const RefPtr<VCreationPreferences>&VP )
171 , DisplayShader(this)
172 {}
173
174
176 getAnemoneExplorer(VRenderContext&Context) const override
177 {
178 return FloatingAnemone::getAnemoneExplorer( this->self(), Context);
179 }
180
181
182
183 string getShaderAttributeName( const TypedSlot<Fiber::Field>&) const override
184 {
185 return DisplayShader::getShaderAttributeName();
186 }
187
188
189
190 GridAnemone::AnemoneRenderStatus
191 initializeAnemone(Anemone&RenderAnemone,
193 const RefPtr<FieldAnemone::AnemoneExplorer>&AE) const override
194 {
195 GridAnemone::AnemoneRenderStatus
196 InitStatus = TypedFieldAnemone_t::initializeAnemone(RenderAnemone, ARC, AE);
197 if (InitStatus != GridAnemone::AnemoneRenderStatus::AllFine)
198 return InitStatus;
199
200 /*
201 TODO: Conceive a way to allow the DisplayShader to override the getShaderPrefix
202 functions. For now, this can be done in the derived VertexFieldShader.
203 */
204 string ShaderPrefix = this->TypedFieldAnemone_t::getShaderPrefix(ARC, *AE);
205 ShaderPrefix += getShaderConditionals(*this, RenderAnemone, ARC, AE);
206
208 ShaderProgram = this->CompileShader(ARC.myContext, this->BaseName(),
209 [this, &RenderAnemone, &ARC, AE](const RenderBasin::Program::Parameters&P)
210 {
211 return this->setProgramParameters(P, RenderAnemone, ARC, AE);
212 },
213 nullptr,
214 ShaderPrefix,
215 ShaderPrefix,
216 ShaderPrefix
217 );
218
219 RenderAnemone.insert( ShaderProgram );
220
221 if (!this->initializeTranslation(RenderAnemone, ARC, AE))
222 {
223 return GridAnemone::AnemoneRenderStatus::InvalidVertexCoordinates;
224 }
225
226 RenderAnemone.insert( ARC.myContext.createViewTentacle(ShaderProgram) );
227
228 if (RefPtr<AnemoneCreator<> >AC = ARC.myAnemoneCreator)
229 {
230 this->FieldAnemone::setNamedTextures(RenderAnemone, ShaderProgram);
231
232 if (this->DisplayShader::initializeAnemone(RenderAnemone, ARC.myContext, *AC))
233 return GridAnemone::AnemoneRenderStatus::AllFine;
234 }
235
236 return GridAnemone::AnemoneRenderStatus::CouldNotInitialize;
237 }
238
248 bool isValidAnemone(const Anemone&RenderAnemone,
250 const RefPtr<FieldAnemone::AnemoneExplorer>&AE) const override
251 {
252 if (!TypedFieldAnemone_t::isValidAnemone(RenderAnemone, ARC, AE))
253 {
254 AppVerbose("Anemonia", 10) << "VertexFieldShader has invalid field Anemone.";
255 return false;
256 }
257
258 if (!ARC.myAnemoneCreator)
259 {
260 AppVerbose("Anemonia", 10) << "VertexFieldShader has NO Anemone Creator.";
261 return false;
262 }
263
264 if (!ARC.myContext.LayeredMultiViews::isValid(RenderAnemone))
265 {
266 AppVerbose("Anemonia", 10) << "VertexField Shader Anemone has invalid multiview settings, need to re-create Anemone.";
267 return false;
268 }
269
270 if (RefPtr<AnemoneCreator<> >AC = ARC.myAnemoneCreator)
271 {
272 if (!this->DisplayShader::isValidAnemone(RenderAnemone, ARC.myContext, *AC))
273 {
274 AppVerbose("Anemonia", 10) << "VertexFieldShader has display shader indicating Anemone being invalid.";
275 return false;
276 }
277 }
278 else
279 {
280 AppVerbose("Anemonia", 10) << "VertexFieldShader has invalid Anemoen Creator.";
281 return false;
282 }
283
284
285 bool validShaders = this->hasValidShaderPrograms(RenderAnemone, ARC.myContext);
286 if (!validShaders)
287 AppVerbose("Anemonia", 10) << "VertexFieldShader has invalid shader programs which invalidate the Anemone.";
288
289 return validShaders;
290 }
291
292
297 bool updateAnemone(Anemone&RenderAnemone,
299 const RefPtr<GridAnemone::AnemoneExplorer>&AE) const override
300 {
301 return updateTranslation(RenderAnemone, ARC, AE);
302 }
303
304};
305
306} // namespace
307
308#endif // __ANEMONEFISH_VERTEXFIELD_SHADER_HPP
__bool_constant< true > true_type
__bool_constant< false > false_type
auto declval() noexcept -> decltype(__declval< _Tp >(0))
An iterator with an optional DataCreator, which is just a class to intercept creation of data along a...
Definition CreativeIterator.hpp:34
MemCore::WeakPtr< Tentacle > insert(const MemCore::WeakPtr< Tentacle > &T, int OrderDeviation=0)
A field Anemone operating on a certain type.
Definition FieldAnemone.hpp:177
Apply a Shader object on a vertex field.
Definition VertexFieldShader.hpp:157
string getShaderAttributeName(const TypedSlot< Fiber::Field > &) const override
Get the name of this field as it should be called in the shader program.
Definition VertexFieldShader.hpp:183
bool isValidAnemone(const Anemone &RenderAnemone, const FieldAnemone::AnemoneCreationContext &ARC, const RefPtr< FieldAnemone::AnemoneExplorer > &AE) const override
Check the validity of the current render anemone by calling the TypedFieldAnemone's isValidAnemone() ...
Definition VertexFieldShader.hpp:248
bool updateAnemone(Anemone &RenderAnemone, const GridAnemone::AnemoneCreationContext &ARC, const RefPtr< GridAnemone::AnemoneExplorer > &AE) const override
Updating a valid Render Anemone, which is setting a possibly modified translation vector.
Definition VertexFieldShader.hpp:297
StrongPtr< Object, ObjectBase > RefPtr
note: cannot derive from FloatingSkeletonRenderer as long as independent base class TriangleRenderer ...
RenderCategory
RefPtr< AnemoneCreatorBase > myAnemoneCreator
Definition VertexFieldShader.hpp:123
Definition FloatingAnemone.hpp:57
RefPtr< GridAnemone::AnemoneExplorer > getAnemoneExplorer(const WeakPtr< GridAnemone > &theGridAnemone, VRenderContext &Context) const
Definition FloatingAnemone.cpp:364
bool initializeTranslation(Anemone &RenderAnemone, const GridAnemone::AnemoneCreationContext &ARC, const RefPtr< GridAnemone::AnemoneExplorer > &AE) const
Definition FloatingAnemone.cpp:384
The context of creating a RenderAnemone.
Definition AnemoneCreationContext.hpp:58
Definition VertexFieldShader.hpp:130