Skip to content

Commit 475564c

Browse files
committed
[gfx] Implement support for geometry filters and Geometry Filter object
1 parent aec4d56 commit 475564c

37 files changed

Lines changed: 1576 additions & 112 deletions

3rdparty/libossia

src/plugins/score-plugin-avnd/Crousti/ProcessModel.hpp

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -785,8 +785,10 @@ struct TSerializer<JSONObject, oscr::ProcessModel<Info>>
785785
[&obj,
786786
&indices]<std::size_t Idx, typename P>(avnd::field_reflection<Idx, P> field) {
787787
if constexpr(avnd::dynamic_ports_port<P>)
788-
indices[avnd::get_c_identifier<P>()]
788+
{
789+
indices[std::string(avnd::get_c_identifier<P>())]
789790
= obj.dynamic_ports.num_in_ports(avnd::field_index<Idx>{});
791+
}
790792
});
791793
s.obj["DynamicInlets"] = indices;
792794
}
@@ -797,7 +799,7 @@ struct TSerializer<JSONObject, oscr::ProcessModel<Info>>
797799
[&obj,
798800
&indices]<std::size_t Idx, typename P>(avnd::field_reflection<Idx, P> field) {
799801
if constexpr(avnd::dynamic_ports_port<P>)
800-
indices[avnd::get_c_identifier<P>()]
802+
indices[std::string(avnd::get_c_identifier<P>())]
801803
= obj.dynamic_ports.num_out_ports(avnd::field_index<Idx>{});
802804
});
803805
s.obj["DynamicOutlets"] = indices;
@@ -820,7 +822,7 @@ struct TSerializer<JSONObject, oscr::ProcessModel<Info>>
820822
avnd::field_reflection<Idx, P> field) {
821823
if constexpr(avnd::dynamic_ports_port<P>)
822824
obj.dynamic_ports.num_in_ports(avnd::field_index<Idx>{})
823-
= indices[avnd::get_c_identifier<P>()];
825+
= indices[std::string(avnd::get_c_identifier<P>())];
824826
});
825827
}
826828
}
@@ -835,7 +837,7 @@ struct TSerializer<JSONObject, oscr::ProcessModel<Info>>
835837
avnd::field_reflection<Idx, P> field) {
836838
if constexpr(avnd::dynamic_ports_port<P>)
837839
obj.dynamic_ports.num_out_ports(avnd::field_index<Idx>{})
838-
= indices[avnd::get_c_identifier<P>()];
840+
= indices[std::string(avnd::get_c_identifier<P>())];
839841
});
840842
}
841843
}

src/plugins/score-plugin-gfx/3rdparty/libisf/src/isf.cpp

Lines changed: 102 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@
22

33
#include "sajson.h"
44

5+
#include <boost/algorithm/string.hpp>
6+
57
#include <array>
68
#include <iostream>
79
#include <regex>
@@ -72,6 +74,27 @@ layout(std140, binding = 1) uniform process_t {
7274
vec4 DATE;
7375
} isf_process_uniforms;
7476
77+
float TIME = isf_process_uniforms.TIME;
78+
float TIMEDELTA = isf_process_uniforms.TIMEDELTA;
79+
float PROGRESS = isf_process_uniforms.PROGRESS;
80+
int PASSINDEX = isf_process_uniforms.PASSINDEX;
81+
int FRAMEINDEX = isf_process_uniforms.FRAMEINDEX;
82+
vec4 DATE = isf_process_uniforms.DATE;
83+
)_";
84+
85+
static constexpr auto defaultGeometryUniforms = R"_(
86+
// Time-dependent uniforms, only relevant during execution
87+
layout(std140, binding = 1) uniform process_t {
88+
float TIME;
89+
float TIMEDELTA;
90+
float PROGRESS;
91+
92+
int PASSINDEX;
93+
int FRAMEINDEX;
94+
95+
vec4 DATE;
96+
} isf_process_uniforms;
97+
7598
float TIME = isf_process_uniforms.TIME;
7699
float TIMEDELTA = isf_process_uniforms.TIMEDELTA;
77100
float PROGRESS = isf_process_uniforms.PROGRESS;
@@ -147,6 +170,12 @@ uniform int PASSINDEX;
147170
} GLSL3;
148171
}
149172

173+
parser::parser(std::string geom)
174+
: m_source_geometry_filter{std::move(geom)}
175+
{
176+
parse_geometry_filter();
177+
}
178+
150179
parser::parser(std::string vert, std::string frag, int glslVersion, ShaderType t)
151180
: m_sourceVertex{std::move(vert)}
152181
, m_sourceFragment{std::move(frag)}
@@ -198,6 +227,8 @@ parser::parser(std::string vert, std::string frag, int glslVersion, ShaderType t
198227
parse_glsl_sandbox();
199228
break;
200229
}
230+
default:
231+
break;
201232
}
202233
}
203234

@@ -216,6 +247,11 @@ std::string parser::fragment() const
216247
return m_fragment;
217248
}
218249

250+
std::string parser::geometry_filter() const
251+
{
252+
return m_geometry_filter;
253+
}
254+
219255
static bool is_number(sajson::value& v)
220256
{
221257
auto t = v.get_type();
@@ -612,24 +648,24 @@ struct create_val_visitor_450
612648
return_type operator()(const audioFFT_input&) { return {"uniform sampler2D", true}; }
613649
};
614650

615-
void parser::parse_isf()
651+
std::string parser::parse_isf_header(std::string_view source)
616652
{
617653
using namespace std::literals;
618654

619-
auto start = m_sourceFragment.find("/*");
655+
auto start = source.find("/*");
620656
if(start == std::string::npos)
621657
throw invalid_file{"Missing start comment"};
622-
auto end = m_sourceFragment.find("*/", start);
658+
auto end = source.find("*/", start);
623659
if(end == std::string::npos)
624660
throw invalid_file{"Unfinished comment"};
625-
auto fragWithoutISF = m_sourceFragment;
661+
std::string fragWithoutISF = std::string(source);
626662
fragWithoutISF.erase(0, end + 2);
627663

628664
// First comes the json part
629665
auto doc = sajson::parse(
630666
sajson::dynamic_allocation(),
631667
sajson::mutable_string_view(
632-
(end - start - 2), const_cast<char*>(m_sourceFragment.data()) + start + 2));
668+
(end - start - 2), const_cast<char*>(source.data()) + start + 2));
633669
if(!doc.is_valid())
634670
{
635671
std::stringstream err;
@@ -658,12 +694,73 @@ void parser::parse_isf()
658694
}
659695
m_desc = d;
660696

697+
return fragWithoutISF;
698+
}
699+
700+
void parser::parse_geometry_filter()
701+
{
702+
using namespace std::literals;
703+
704+
auto geomWithoutISF = parse_isf_header(m_source_geometry_filter);
705+
661706
// There is always one pass at least
662707
if(m_desc.passes.empty())
663708
{
664709
m_desc.passes.push_back(isf::pass{});
665710
}
666711

712+
boost::algorithm::trim(geomWithoutISF);
713+
boost::algorithm::replace_all(geomWithoutISF, "this_filter", "filter_%node%");
714+
715+
std::string filter_ubo;
716+
if(!m_desc.inputs.empty())
717+
{
718+
std::string globalvars;
719+
filter_ubo += "layout(std140, binding = %next%) uniform filter_%node%_t {\n";
720+
for(const isf::input& val : m_desc.inputs)
721+
{
722+
auto [type, isSampler] = ossia::visit(create_val_visitor_450{}, val.data);
723+
724+
{
725+
filter_ubo += " ";
726+
filter_ubo += type;
727+
filter_ubo += ' ';
728+
filter_ubo += val.name;
729+
filter_ubo += ";\n";
730+
731+
// // See comment above regarding little dance to make spirv-cross happy
732+
// globalvars += type;
733+
// globalvars += ' ';
734+
// globalvars += val.name;
735+
// globalvars += " = filter_%node%.";
736+
// globalvars += val.name;
737+
// globalvars += ";\n";
738+
}
739+
}
740+
741+
filter_ubo += "} filter_%node%;\n";
742+
filter_ubo += "\n";
743+
// filter_ubo += globalvars;
744+
// filter_ubo += "\n";
745+
}
746+
m_geometry_filter
747+
= glsl45_t::defaultGeometryUniforms + filter_ubo + geomWithoutISF + "\n";
748+
}
749+
750+
void parser::parse_isf()
751+
{
752+
using namespace std::literals;
753+
754+
auto fragWithoutISF = parse_isf_header(m_sourceFragment);
755+
756+
// There is always one pass at least
757+
if(m_desc.passes.empty())
758+
{
759+
m_desc.passes.push_back(isf::pass{});
760+
}
761+
762+
auto& d = m_desc;
763+
667764
// We start from empty strings.
668765

669766
bool simpleVS = false;

src/plugins/score-plugin-gfx/3rdparty/libisf/src/isf.hpp

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -120,10 +120,12 @@ class parser
120120
{
121121
std::string m_sourceVertex;
122122
std::string m_sourceFragment;
123+
std::string m_source_geometry_filter;
123124
int m_version{450};
124125

125126
std::string m_vertex;
126127
std::string m_fragment;
128+
std::string m_geometry_filter;
127129

128130
descriptor m_desc;
129131

@@ -133,19 +135,25 @@ class parser
133135
Autodetect,
134136
ISF,
135137
ShaderToy,
136-
GLSLSandBox
138+
GLSLSandBox,
139+
GeometryFilter
137140
};
138141
parser(
139142
std::string vert, std::string frag, int glslVersion = 450,
140143
ShaderType = ShaderType::Autodetect);
144+
explicit parser(std::string isf_geom_filter);
141145

142146
descriptor data() const;
143147
std::string vertex() const;
144148
std::string fragment() const;
149+
std::string geometry_filter() const;
145150

146151
private:
147152
void parse_isf();
148153
void parse_shadertoy();
149154
void parse_glsl_sandbox();
155+
void parse_geometry_filter();
156+
157+
std::string parse_isf_header(std::string_view source);
150158
};
151159
}

src/plugins/score-plugin-gfx/CMakeLists.txt

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -74,6 +74,11 @@ set(HDRS
7474
Gfx/Filter/Library.hpp
7575
Gfx/Filter/PreviewWidget.hpp
7676

77+
Gfx/GeometryFilter/Executor.hpp
78+
Gfx/GeometryFilter/Metadata.hpp
79+
Gfx/GeometryFilter/Process.hpp
80+
Gfx/GeometryFilter/Layer.hpp
81+
7782
Gfx/Video/Executor.hpp
7883
Gfx/Video/Inspector.hpp
7984
Gfx/Video/Metadata.hpp
@@ -95,6 +100,8 @@ set(HDRS
95100
Gfx/Graph/CommonUBOs.hpp
96101
Gfx/Graph/CustomMesh.hpp
97102
Gfx/Graph/DepthNode.hpp
103+
Gfx/Graph/GeometryFilterNode.hpp
104+
Gfx/Graph/GeometryFilterNodeRenderer.hpp
98105
Gfx/Graph/OutputNode.hpp
99106
Gfx/Graph/Scale.hpp
100107
Gfx/Graph/Window.hpp
@@ -168,6 +175,9 @@ set(SRCS
168175
Gfx/Filter/Process.cpp
169176
Gfx/Filter/PreviewWidget.cpp
170177

178+
Gfx/GeometryFilter/Executor.cpp
179+
Gfx/GeometryFilter/Process.cpp
180+
171181
Gfx/Video/Executor.cpp
172182
Gfx/Video/Inspector.cpp
173183
Gfx/Video/Presenter.cpp
@@ -183,6 +193,8 @@ set(SRCS
183193

184194
Gfx/Graph/decoders/GPUVideoDecoder.cpp
185195
Gfx/Graph/decoders/HAP.cpp
196+
Gfx/Graph/GeometryFilterNode.cpp
197+
Gfx/Graph/GeometryFilterNodeRenderer.cpp
186198
Gfx/Graph/Node.cpp
187199
Gfx/Graph/Graph.cpp
188200
Gfx/Graph/RenderList.cpp

0 commit comments

Comments
 (0)