5#ifndef INKSCAPE_UTIL_CAST_H
6#define INKSCAPE_UTIL_CAST_H
20template <
typename T>
inline constexpr int first_tag = std::enable_if<!
sizeof(T),
void>::value;
21template <
typename T>
inline constexpr int last_tag = std::enable_if<!
sizeof(T),
void>::value;
26template <
typename T>
inline constexpr int tag_of = first_tag<std::remove_cv_t<std::remove_reference_t<T>>>;
36template<
typename T,
typename S>
40 if constexpr (std::is_base_of_v<T, S>) {
41 static_assert(!
sizeof(T),
"check is always true");
43 }
else if constexpr (std::is_base_of_v<S, T>) {
44 auto const s_tag = s->tag();
45 return first_tag<T> <= s_tag && s_tag <= last_tag<T>;
47 static_assert(!
sizeof(T),
"check is always false");
55template<
typename T,
typename S>
58 return static_cast<T*
>(s);
61template<
typename T,
typename S>
64 return static_cast<T const*
>(s);
75template<
typename T,
typename S>
78 if constexpr (std::is_base_of_v<T, S>) {
81 return cast_unsafe<T>(s);
82 }
else if constexpr (std::is_base_of_v<S, T>) {
83 return is<T>(s) ? cast_unsafe<T>(s) :
nullptr;
85 static_assert(!
sizeof(T),
"cast is impossible");
auto cast(S *s)
Equivalent to dynamic_cast<T [const]*>(...) where the const is deduced.
bool is(S const *s)
Equivalent to the boolean value of dynamic_cast<T const*>(...).
auto cast_unsafe(S *s)
Equivalent to static_cast<T [const]*>(...) where the const is deduced.
constexpr int tag_of
Convenience function to retrieve the tag (class id) of a given type.