You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
109 lines
3.2 KiB
109 lines
3.2 KiB
#pragma once |
|
#include "actions.h" |
|
#include "data.h" |
|
#include <array> |
|
|
|
template<class A, class D> struct CompatTableS; |
|
|
|
template<template<class...> class A, template<class...> class D, class... Acts, class... Datas> struct CompatTableS<A<Acts...>, D<Datas...>> |
|
{ |
|
size_t static consteval StrLen(const char* str) { return *str ? 1 + StrLen(str + 1) : 0; } |
|
|
|
template<class D1, class... Dd> static consteval size_t MaxNameLen() |
|
{ |
|
if constexpr(sizeof...(Dd) == 0) |
|
return StrLen(D1::name); |
|
else |
|
return std::max(StrLen(D1::name), MaxNameLen<Dd...>()); |
|
} |
|
|
|
static constexpr size_t W = MaxNameLen<Datas...>(); |
|
|
|
template<size_t N> static consteval auto C2A(const char (&s)[N]) |
|
{ |
|
std::array<char, N> out; |
|
for(size_t i = 0; i < N; i++) out[i] = s[i]; |
|
return out; |
|
} |
|
|
|
static constexpr auto em = C2A(""); |
|
static constexpr auto sp = C2A(" "); |
|
static constexpr auto nd = C2A("\n"); |
|
|
|
template<class T> static consteval auto N2A() |
|
{ |
|
std::array<char, StrLen(T::name) + 1> out; |
|
for(size_t i = 0; i <= StrLen(T::name); i++) out[i] = T::name[i]; |
|
return out; |
|
} |
|
template<class T> static constexpr auto name = N2A<T>(); |
|
|
|
template<size_t N, size_t M, class... T> static consteval auto Merge(const std::array<char, N>& arg1, const std::array<char, M>& arg2, const T&... args) |
|
{ |
|
if constexpr(sizeof...(T) == 0) |
|
{ |
|
std::array<char, N + M - 1> out; |
|
for(size_t i = 0; i < N - 1; i++) out[i] = arg1[i]; |
|
for(size_t i = 0; i < M; i++) out[i + N - 1] = arg2[i]; |
|
return out; |
|
} |
|
else |
|
return Merge(arg1, Merge(arg2, args...)); |
|
} |
|
|
|
template<size_t n> static consteval auto Spaces() |
|
{ |
|
if constexpr(n == 0) |
|
return em; |
|
else |
|
return Merge(sp, Spaces<n - 1>()); |
|
} |
|
|
|
template<size_t n, class T> static consteval auto AlignR(const T& s) |
|
{ |
|
constexpr size_t len = std::tuple_size_v<T> - 1; |
|
if constexpr(len > n) return s; |
|
return Merge(Spaces<n - len>(), s); |
|
} |
|
|
|
template<size_t n, class T> static consteval auto AlignL(const T& s) |
|
{ |
|
constexpr size_t len = std::tuple_size_v<T> - 1; |
|
if constexpr(len > n) return s; |
|
return Merge(s, Spaces<n - len>()); |
|
} |
|
|
|
template<class A1, class... Aa> static consteval auto MergeNames() |
|
{ |
|
if constexpr(sizeof...(Aa) == 0) |
|
return name<A1>; |
|
else |
|
return Merge(name<A1>, sp, MergeNames<Aa...>()); |
|
} |
|
|
|
static constexpr auto header = Merge(Spaces<W>(), MergeNames<Acts...>()); |
|
|
|
template<class Dat, class A1, class... Aa> static consteval auto MergeSup() |
|
{ |
|
constexpr bool issup = A1::template IsSupported<Dat> && !IsDisabled<A1, Dat>(); |
|
constexpr auto v = Merge(Spaces<StrLen(A1::name) - 1>(), C2A(issup ? "\033[32mY\033[0m" : "\033[31mN\033[0m")); |
|
//constexpr auto v = AlignR<StrLen(A1::name)>(C2A(issup ? "X" : " ")); |
|
if constexpr(sizeof...(Aa) == 0) |
|
return v; |
|
else |
|
return Merge(v, sp, MergeSup<Dat, Aa...>()); |
|
} |
|
|
|
template<class D1, class... Dd> static consteval auto MergeRows() |
|
{ |
|
constexpr auto r = Merge(AlignL<W>(name<D1>), MergeSup<D1, Acts...>()); |
|
if constexpr(sizeof...(Dd) == 0) |
|
return r; |
|
else |
|
return Merge(r, nd, MergeRows<Dd...>()); |
|
} |
|
|
|
static constexpr auto value = Merge(header, nd, MergeRows<Datas...>()); |
|
}; |
|
|
|
static constexpr auto CompatTable = CompatTableS<ActionVariants, DataVariants>::value.data();
|
|
|