OSSIA
Open Scenario System for Interactive Application
dataflow/safe_nodes/node.hpp
1 #pragma once
2 #include <ossia/dataflow/safe_nodes/port.hpp>
3 #include <ossia/detail/apply_type.hpp>
4 #include <ossia/detail/flat_map.hpp>
5 
6 #include <tuplet/tuple.hpp>
7 
8 #include <array>
9 #include <tuple>
10 
11 namespace ossia::safe_nodes
12 {
13 
14 template <typename T>
15 struct dummy_container
16 {
17  static constexpr bool is_event = false;
18  static constexpr auto begin() { return (T*)nullptr; }
19  static constexpr auto end() { return (T*)nullptr; }
20  static constexpr std::size_t size() { return 0; }
21 };
22 
23 struct dummy_t
24 {
25 };
26 
27 template <typename T>
28 using my_void_t = void;
29 template <typename T, typename = void>
30 struct has_state_t : std::false_type
31 {
32 };
33 template <typename T>
34 struct has_state_t<T, my_void_t<typename T::State>> : std::true_type
35 {
36 };
37 
38 template <typename T, typename = void>
39 struct get_state
40 {
41  using type = dummy_t;
42 };
43 template <typename T>
44 struct get_state<T, my_void_t<typename T::State>>
45 {
46  using type = typename T::State;
47 };
48 
49 template <typename T>
50 struct get_control_type
51 {
52  using type = typename T::type;
53 };
54 
55 template <typename>
56 struct get_type_list
57 {
58 };
59 
60 template <template <typename...> class Tuple, typename... T>
61 struct get_type_list<const Tuple<T...>>
62 {
63  using type = Tuple<typename T::type...>;
64 };
65 
66 template <typename Node_T>
67 struct info_functions
68 {
69  using controls_type = decltype(Node_T::Metadata::controls);
70  using controls_values_type = typename get_type_list<controls_type>::type;
71 
72  using control_outs_type = decltype(Node_T::Metadata::control_outs);
73  using control_outs_values_type = typename get_type_list<control_outs_type>::type;
74 
75  static constexpr auto audio_in_count = std::size(Node_T::Metadata::audio_ins);
76  static constexpr auto audio_out_count = std::size(Node_T::Metadata::audio_outs);
77  static constexpr auto midi_in_count = std::size(Node_T::Metadata::midi_ins);
78  static constexpr auto midi_out_count = std::size(Node_T::Metadata::midi_outs);
79  static constexpr auto value_in_count = std::size(Node_T::Metadata::value_ins);
80  static constexpr auto value_out_count = std::size(Node_T::Metadata::value_outs);
81  static constexpr auto address_in_count = std::size(Node_T::Metadata::address_ins);
82  static constexpr auto control_count = std::tuple_size_v<controls_type>;
83  static constexpr auto control_out_count
84  = std::tuple_size_v<decltype(Node_T::Metadata::control_outs)>;
85 
86  static constexpr auto categorize_inlet(std::size_t i)
87  {
88  if(i < audio_in_count)
89  return inlet_kind::audio_in;
90  else if(i < audio_in_count + midi_in_count)
91  return inlet_kind::midi_in;
92  else if(i < audio_in_count + midi_in_count + value_in_count)
93  return inlet_kind::value_in;
94  else if(i < audio_in_count + midi_in_count + value_in_count + address_in_count)
95  return inlet_kind::address_in;
96  else if(
97  i < audio_in_count + midi_in_count + value_in_count + address_in_count
98  + control_count)
99  return inlet_kind::control_in;
100  else
101  throw std::runtime_error("Invalid input number");
102  }
103 
104  static constexpr auto categorize_outlet(std::size_t i)
105  {
106  if(i < audio_out_count)
107  return outlet_kind::audio_out;
108  else if(i < audio_out_count + midi_out_count)
109  return outlet_kind::midi_out;
110  else if(i < audio_out_count + midi_out_count + value_out_count)
111  return outlet_kind::value_out;
112  else if(i < audio_out_count + midi_out_count + value_out_count + control_out_count)
113  return outlet_kind::control_out;
114  else
115  throw std::runtime_error("Invalid output number");
116  }
117 
118  static constexpr auto control_start
119  = audio_in_count + midi_in_count + value_in_count + address_in_count;
120 
121  static constexpr auto control_out_start
122  = audio_out_count + midi_out_count + value_out_count;
123 
124  static constexpr auto inlet_size = control_start + control_count;
125 
126  static constexpr auto outlet_size = control_out_start + control_out_count;
127 };
128 
129 struct base_metadata
130 {
131  using value_in = ossia::safe_nodes::value_in;
132  using value_out = ossia::safe_nodes::value_out;
133  using audio_in = ossia::safe_nodes::audio_in;
134  using audio_out = ossia::safe_nodes::audio_out;
135  using midi_in = ossia::safe_nodes::midi_in;
136  using midi_out = ossia::safe_nodes::midi_out;
137  using address_in = ossia::safe_nodes::address_in;
138 
139  static const constexpr dummy_container<value_in> value_ins{};
140  static const constexpr dummy_container<value_out> value_outs{};
141  static const constexpr dummy_container<audio_in> audio_ins{};
142  static const constexpr dummy_container<audio_out> audio_outs{};
143  static const constexpr dummy_container<midi_in> midi_ins{};
144  static const constexpr dummy_container<midi_out> midi_outs{};
145  static const constexpr dummy_container<address_in> address_ins{};
146  static const constexpr tuplet::tuple<> controls{};
147  static const constexpr tuplet::tuple<> control_outs{};
148 
149  static const constexpr double recommended_height{};
150 };
151 }