107 lines
2.7 KiB
C++
107 lines
2.7 KiB
C++
/*
|
|
This file is part of KDBindings.
|
|
|
|
SPDX-FileCopyrightText: 2021 Klarälvdalens Datakonsult AB, a KDAB Group company <info@kdab.com>
|
|
Author: Sean Harmer <sean.harmer@kdab.com>
|
|
|
|
SPDX-License-Identifier: MIT
|
|
|
|
Contact KDAB at <info@kdab.com> for commercial licensing options.
|
|
*/
|
|
|
|
#pragma once
|
|
|
|
#include <kdbindings/node.h>
|
|
#include <type_traits>
|
|
|
|
namespace KDBindings {
|
|
|
|
namespace Private {
|
|
|
|
template<typename T>
|
|
struct bindable_value_type_ {
|
|
using type = T;
|
|
};
|
|
|
|
template<typename T>
|
|
struct bindable_value_type_<Property<T>> {
|
|
using type = T;
|
|
};
|
|
|
|
template<typename T>
|
|
struct bindable_value_type_<const Property<T>> {
|
|
using type = T;
|
|
};
|
|
|
|
template<typename T>
|
|
struct bindable_value_type_<NodeInterface<T>> {
|
|
using type = T;
|
|
};
|
|
|
|
template<typename T>
|
|
struct bindable_value_type_<Node<T>> {
|
|
using type = T;
|
|
};
|
|
|
|
template<typename T>
|
|
struct bindable_value_type : bindable_value_type_<std::decay_t<T>> {
|
|
};
|
|
|
|
template<typename T>
|
|
using bindable_value_type_t = typename bindable_value_type<T>::type;
|
|
|
|
// Find the type of a Node wrapping an operator and arguments
|
|
template<typename Operator, typename... Ts>
|
|
using operator_node_result =
|
|
std::decay<
|
|
std::invoke_result_t<
|
|
std::decay_t<Operator>,
|
|
bindable_value_type_t<Ts>...>>;
|
|
|
|
template<typename Operator, typename... Ts>
|
|
using operator_node_result_t = typename operator_node_result<Operator, Ts...>::type;
|
|
|
|
// Node creation helpers
|
|
template<typename T>
|
|
inline Node<std::decay_t<T>> makeNode(T &&value)
|
|
{
|
|
return Node<std::decay_t<T>>(std::make_unique<ConstantNode<std::decay_t<T>>>(std::move(value)));
|
|
}
|
|
|
|
template<typename T>
|
|
inline Node<T> makeNode(Property<T> &property)
|
|
{
|
|
return Node<T>(std::make_unique<PropertyNode<T>>(property));
|
|
}
|
|
|
|
template<typename T>
|
|
inline Node<T> makeNode(const Property<T> &property)
|
|
{
|
|
return Node<T>(std::make_unique<PropertyNode<T>>(property));
|
|
}
|
|
|
|
template<typename T>
|
|
inline Node<T> makeNode(Node<T> &&node)
|
|
{
|
|
return std::move(node);
|
|
}
|
|
|
|
template<typename Operator, typename... Ts, typename = std::enable_if_t<sizeof...(Ts) >= 1>, typename ResultType = operator_node_result_t<Operator, Ts...>>
|
|
inline Node<ResultType> makeNode(Operator &&op, Ts &&...args)
|
|
{
|
|
return Node<ResultType>(std::make_unique<OperatorNode<ResultType, std::decay_t<Operator>, bindable_value_type_t<Ts>...>>(
|
|
std::forward<Operator>(op),
|
|
makeNode(std::forward<Ts>(args))...));
|
|
}
|
|
|
|
// Needed by function and operator helpers
|
|
template<typename T>
|
|
struct is_bindable : std::integral_constant<
|
|
bool,
|
|
is_property<T>::value || is_node<T>::value> {
|
|
};
|
|
|
|
} // namespace Private
|
|
|
|
} // namespace KDBindings
|