3#include <macros/labels.hpp>
4#include <io/button_presser.hpp>
12concept has_color = std::is_aggregate_v<typename Tp::color>;
16 <
decltype(Tp::palette())>;
21 { Tp::palette()[0].first } -> std::same_as<unsigned long&>;
27 || std::same_as<Tp, char*>
28 || std::same_as<Tp, std::string_view>;
32 <
decltype(Tp::grid::ids()[0][0])>>
35 Tp::grid::ids().size() > 2;
36 Tp::grid::ids()[0].size() > 2;
40concept has_buttons = (std::is_aggregate_v<typename Tp::buttons>
42 <
typename Tp::buttons::id_type>);
46 <
decltype(Tp::sysex_prefix())>
48 <
decltype(Tp::sysex_sufix())>;
51concept has_init = !std::is_void_v<
decltype(Tp::init())>;
54concept has_clear = !std::is_void_v<
decltype(Tp::clear())>;
56#define has_button(L) \
57template <typename Device> \
58concept device_##L##_button = \
59is_valid_id<decltype(Device::buttons::L##_id())>; \
61template <typename Controller> \
62concept controller_##L##_button = \
63requires(Controller c, button_presser p) \
64{ std::is_void_v<decltype(c.on_##L(p))>; }; \
66template <typename Device, typename Controller> \
68device_##L##_button<Device> \
69&& controller_##L##_button<Controller>;
71#define CALL_MACRO(r, data, elem) has_button(elem)
72FOR_EACH_LABEL(CALL_MACRO)