chromium/third_party/mediapipe/src/mediapipe/framework/api2/builder.h

#ifndef MEDIAPIPE_FRAMEWORK_API2_BUILDER_H_
#define MEDIAPIPE_FRAMEWORK_API2_BUILDER_H_

#include <functional>
#include <map>
#include <memory>
#include <optional>
#include <string>
#include <type_traits>
#include <utility>
#include <vector>

#include "absl/container/btree_map.h"
#include "absl/log/absl_check.h"
#include "absl/memory/memory.h"
#include "absl/strings/str_cat.h"
#include "absl/strings/string_view.h"
#include "google/protobuf/message_lite.h"
#include "mediapipe/framework/api2/packet.h"
#include "mediapipe/framework/api2/port.h"
#include "mediapipe/framework/calculator_base.h"
#include "mediapipe/framework/calculator_contract.h"
#include "mediapipe/framework/mediapipe_options.pb.h"
#include "mediapipe/framework/port/any_proto.h"
#include "mediapipe/framework/port/ret_check.h"
#include "mediapipe/framework/stream_handler.pb.h"

namespace mediapipe {
namespace api2 {
namespace builder {

// Workaround for static_assert(false). Example:
//   dependent_false<T>::value returns false.
// For more information, see:
// https://en.cppreference.com/w/cpp/language/if#Constexpr_If
// TODO: migrate to a common utility when available.
template <class T>
struct dependent_false : std::false_type {};

template <typename T>
T& GetWithAutoGrow(std::vector<std::unique_ptr<T>>* vecp, size_t index) {}

struct TagIndexLocation {};

template <typename T>
class TagIndexMap {};

class Graph;
class NodeBase;
class PacketGenerator;

// These structs are used internally to store information about the endpoints
// of a connection.
struct SourceBase;
struct DestinationBase {};
struct SourceBase {};

// Following existing GraphConfig usage, we allow using a multiport as a single
// port as well. This is necessary for generic nodes, since we have no
// information about which ports are meant to be multiports or not, but it is
// also convenient with typed nodes.
template <typename Single>
class MultiPort : public Single {};

namespace internal_builder {

template <typename T, typename U>
using AllowCast = std::integral_constant<bool, (std::is_same_v<T, AnyType> ||
                                                std::is_same_v<U, AnyType>) &&
                                                   !std::is_same_v<T, U>>;

}  // namespace internal_builder

template <bool IsSide, typename T = internal::Generic>
class SourceImpl;

// These classes wrap references to the underlying source/destination
// endpoints, adding type information and the user-visible API.
template <bool IsSide, typename T = internal::Generic>
class DestinationImpl {};

template <bool IsSide, typename T>
class SourceImpl {};

// A source and a destination correspond to an output/input stream on a node,
// and a side source and side destination correspond to an output/input side
// packet.
// For graph inputs/outputs, however, the inputs are sources, and the outputs
// are destinations. This is because graph ports are connected "from inside"
// when building the graph.
Source;

// Represents a stream of packets of a particular type.
//
// The intended use:
// - decouple input/output streams from graph/node during graph construction
// - pass streams around and connect them as needed, extracting reusable parts
//   to utility/convenience functions or classes.
//
// For example:
//   Stream<Image> Resize(Stream<Image> image, const Size& size, Graph& graph) {
//     auto& scaler_node = graph.AddNode("GlScalerCalculator");
//     auto& opts = scaler_node.GetOptions<GlScalerCalculatorOptions>();
//     opts.set_output_width(size.width);
//     opts.set_output_height(size.height);
//     a >> scaler_node.In("IMAGE");
//     return scaler_node.Out("IMAGE").Cast<Image>();
//   }
//
// Where graph can use it as:
//   Graph graph;
//   Stream<Image> input_image = graph.In("INPUT_IMAGE").Cast<Image>();
//   Stream<Image> resized_image = Resize(input_image, {64, 64}, graph);
template <typename T>
using Stream = Source<T>;

template <typename T = internal::Generic>
using MultiSource = MultiPort<Source<T>>;

SideSource;

// Represents a side packet of a particular type.
//
// The intended use:
// - decouple input/output side packets from graph/node during graph
//   construction
// - pass side packets around and connect them as needed, extracting reusable
//   parts utility/convenience functions or classes.
//
// For example:
//   SidePacket<TfLiteModelPtr> GetModel(SidePacket<std::string> model_blob,
//                                       Graph& graph) {
//     auto& model_node = graph.AddNode("TfLiteModelCalculator");
//     model_blob >> model_node.SideIn("MODEL_BLOB");
//     return model_node.SideOut("MODEL").Cast<TfLiteModelPtr>();
//   }
//
// Where graph can use it as:
//   Graph graph;
//   SidePacket<std::string> model_blob =
//     graph.SideIn("MODEL_BLOB").Cast<std::string>();
//   SidePacket<TfLiteModelPtr> model = GetModel(model_blob, graph);
template <typename T>
using SidePacket = SideSource<T>;

template <typename T = internal::Generic>
using MultiSideSource = MultiPort<SideSource<T>>;

Destination;
SideDestination;
template <typename T = internal::Generic>
using MultiDestination = MultiPort<Destination<T>>;
template <typename T = internal::Generic>
using MultiSideDestination = MultiPort<SideDestination<T>>;

namespace internal_builder {

template <typename OptionsT>
OptionsT& GetOptions(std::optional<mediapipe::MediaPipeOptions>& options) {}

}  // namespace internal_builder

class Executor {};

class NodeBase;

class InputStreamHandler {};

class OutputStreamHandler {};

class NodeBase {};

template <class Calc = internal::Generic>
class Node;
#if __cplusplus >= 201703L
// Deduction guide to silence -Wctad-maybe-unsupported.
explicit Node() -> Node<internal::Generic>;
#endif  // C++17

template <>
class Node<internal::Generic> : public NodeBase {
 public:
  Node(std::string type) : NodeBase(std::move(type)) {}
};

using GenericNode = Node<internal::Generic>;

template <class Calc>
class Node : public NodeBase {};

// For legacy PacketGenerators.
class PacketGenerator {};

class Graph {};

}  // namespace builder
}  // namespace api2
}  // namespace mediapipe

#endif  // MEDIAPIPE_FRAMEWORK_API2_BUILDER_H_