libcamera: utils: Add overloaded visitor helpers
std::visit() allows quite elegant type-matching implementation of the visitor pattern. The 'overloaded' type helpers allow to define a hierarchy of overloaded operator() implementations which can be used by std::visit(). Currently only the Virtual pipeline handler uses this type-matching implementation of std::visit(). To prepare to add another user in the Mali C55 pipeline handler move the 'overloaded' helper type to libcamera::utils for easier re-use. Signed-off-by: Jacopo Mondi <jacopo.mondi@ideasonboard.com> Reviewed-by: Barnabás Pőcze <barnabas.pocze@ideasonboard.com> Reviewed-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com> Signed-off-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com> Reviewed-by: Jacopo Mondi <jacopo.mondi@ideasonboard.com>
This commit is contained in:
@@ -37,6 +37,15 @@ namespace libcamera {
|
||||
|
||||
namespace utils {
|
||||
|
||||
template<class... Ts>
|
||||
struct overloaded : Ts... {
|
||||
using Ts::operator()...;
|
||||
};
|
||||
#ifndef __DOXYGEN__
|
||||
template<class... Ts>
|
||||
overloaded(Ts...) -> overloaded<Ts...>;
|
||||
#endif
|
||||
|
||||
const char *basename(const char *path);
|
||||
|
||||
char *secure_getenv(const char *name);
|
||||
|
||||
@@ -23,6 +23,36 @@ namespace libcamera {
|
||||
|
||||
namespace utils {
|
||||
|
||||
/**
|
||||
* \struct overloaded
|
||||
* \brief Helper type for type-matching std::visit() implementations
|
||||
* \tparam Ts... Template arguments pack of visitors
|
||||
*
|
||||
* Expand the template argument pack \a Ts... to provide overloaded \a
|
||||
* operator() to support type-matching implementations of the visitor design
|
||||
* pattern using std::visit().
|
||||
*
|
||||
* An example is provided by the C++ standard library documentation in the form
|
||||
* of:
|
||||
*
|
||||
* \code{.cpp}
|
||||
* template<class... Ts> struct overloaded : Ts... { using Ts::operator()...; };
|
||||
* template<class... Ts> overloaded(Ts...) -> overloaded<Ts...>;
|
||||
*
|
||||
* using var_t = std::variant<int, long, double, std::string>;
|
||||
* std::vector<var_t> vec = {10, 15l, 1.5, "hello"};
|
||||
*
|
||||
* for (auto& v: vec) {
|
||||
* std::visit(overloaded {
|
||||
* [](auto arg) { std::cout << arg << ' '; },
|
||||
* [](double arg) { std::cout << std::fixed << arg << ' '; },
|
||||
* [](const std::string& arg) { std::cout << std::quoted(arg) << ' '; },
|
||||
* }, v);
|
||||
* \endcode
|
||||
*
|
||||
* Use this helper to implement type-matching visitors using std::visit().
|
||||
*/
|
||||
|
||||
/**
|
||||
* \brief Strip the directory prefix from the path
|
||||
* \param[in] path The path to process
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
|
||||
#include <libcamera/base/flags.h>
|
||||
#include <libcamera/base/log.h>
|
||||
#include <libcamera/base/utils.h>
|
||||
|
||||
#include <libcamera/control_ids.h>
|
||||
#include <libcamera/controls.h>
|
||||
@@ -57,13 +58,6 @@ uint64_t currentTimestamp()
|
||||
|
||||
} /* namespace */
|
||||
|
||||
template<class... Ts>
|
||||
struct overloaded : Ts... {
|
||||
using Ts::operator()...;
|
||||
};
|
||||
template<class... Ts>
|
||||
overloaded(Ts...) -> overloaded<Ts...>;
|
||||
|
||||
class VirtualCameraConfiguration : public CameraConfiguration
|
||||
{
|
||||
public:
|
||||
@@ -428,7 +422,7 @@ bool PipelineHandlerVirtual::initFrameGenerator(Camera *camera)
|
||||
{
|
||||
auto data = cameraData(camera);
|
||||
auto &frame = data->config_.frame;
|
||||
std::visit(overloaded{
|
||||
std::visit(utils::overloaded{
|
||||
[&](TestPattern &testPattern) {
|
||||
for (auto &streamConfig : data->streamConfigs_) {
|
||||
if (testPattern == TestPattern::DiagonalLines)
|
||||
|
||||
Reference in New Issue
Block a user