diff --git a/src/language/modules/WriterModule.cpp b/src/language/modules/WriterModule.cpp index c2f3a094429464fdf89e70215023e97747cd56cd..bb5ccdf3dd41c58632f3e438587e330fe5777530 100644 --- a/src/language/modules/WriterModule.cpp +++ b/src/language/modules/WriterModule.cpp @@ -12,6 +12,113 @@ #include <scheme/IDiscreteFunction.hpp> #include <scheme/IDiscreteFunctionDescriptor.hpp> +template <size_t Dimension, typename DataType> +void +WriterModule::registerDiscreteFunctionP0(const std::string& name, + const IDiscreteFunction& i_discrete_function, + OutputNamedItemValueSet& named_item_value_set) +{ + const DiscreteFunctionP0<Dimension, DataType>& discrete_function = + dynamic_cast<const DiscreteFunctionP0<Dimension, DataType>&>(i_discrete_function); + named_item_value_set.add(NamedItemValue{name, discrete_function.cellValues()}); +} + +template <size_t Dimension> +void +WriterModule::registerDiscreteFunctionP0(const std::string& name, + const IDiscreteFunction& i_discrete_function, + OutputNamedItemValueSet& named_item_value_set) +{ + const ASTNodeDataType& data_type = i_discrete_function.dataType(); + switch (data_type) { + case ASTNodeDataType::bool_t: { + registerDiscreteFunctionP0<Dimension, bool>(name, i_discrete_function, named_item_value_set); + break; + } + case ASTNodeDataType::unsigned_int_t: { + registerDiscreteFunctionP0<Dimension, uint64_t>(name, i_discrete_function, named_item_value_set); + break; + } + case ASTNodeDataType::int_t: { + registerDiscreteFunctionP0<Dimension, int64_t>(name, i_discrete_function, named_item_value_set); + break; + } + case ASTNodeDataType::double_t: { + registerDiscreteFunctionP0<Dimension, double>(name, i_discrete_function, named_item_value_set); + break; + } + case ASTNodeDataType::vector_t: { + switch (data_type.dimension()) { + case 1: { + registerDiscreteFunctionP0<Dimension, TinyVector<1, double>>(name, i_discrete_function, named_item_value_set); + break; + } + case 2: { + registerDiscreteFunctionP0<Dimension, TinyVector<2, double>>(name, i_discrete_function, named_item_value_set); + break; + } + case 3: { + registerDiscreteFunctionP0<Dimension, TinyVector<3, double>>(name, i_discrete_function, named_item_value_set); + break; + } + default: { + throw UnexpectedError("invalid vector dimension"); + } + } + break; + } + case ASTNodeDataType::matrix_t: { + Assert(data_type.nbRows() == data_type.nbColumns(), "invalid matrix dimensions"); + switch (data_type.nbRows()) { + case 1: { + registerDiscreteFunctionP0<Dimension, TinyMatrix<1, double>>(name, i_discrete_function, named_item_value_set); + break; + } + case 2: { + registerDiscreteFunctionP0<Dimension, TinyMatrix<2, double>>(name, i_discrete_function, named_item_value_set); + break; + } + case 3: { + registerDiscreteFunctionP0<Dimension, TinyMatrix<3, double>>(name, i_discrete_function, named_item_value_set); + break; + } + default: { + throw UnexpectedError("invalid matrix dimension"); + } + } + break; + } + default: { + throw UnexpectedError("invalid data type " + dataTypeName(data_type)); + } + } +} + +void +WriterModule::registerDiscreteFunctionP0(const NamedDiscreteFunction& named_discrete_function, + OutputNamedItemValueSet& named_item_value_set) +{ + const IDiscreteFunction& i_discrete_function = *named_discrete_function.discreteFunction(); + const std::string& name = named_discrete_function.name(); + switch (i_discrete_function.mesh()->dimension()) { + case 1: { + registerDiscreteFunctionP0<1>(name, i_discrete_function, named_item_value_set); + break; + } + case 2: { + registerDiscreteFunctionP0<2>(name, i_discrete_function, named_item_value_set); + break; + } + case 3: { + registerDiscreteFunctionP0<3>(name, i_discrete_function, named_item_value_set); + break; + } + default: { + throw UnexpectedError("invalid mesh dimension"); + } + } +} + WriterModule::WriterModule() { this->_addTypeDescriptor(ast_node_data_type_from<std::shared_ptr<const NamedDiscreteFunction>>); @@ -86,7 +193,7 @@ WriterModule::WriterModule() )); this->_addBuiltinFunction( - "writeVTK", + "write", std::make_shared< BuiltinFunctionEmbedder<void(std::shared_ptr<const IWriter>, const std::vector<std::shared_ptr<const NamedDiscreteFunction>>&, const double&)>>( @@ -115,10 +222,7 @@ WriterModule::WriterModule() switch (i_discrete_function.descriptor().type()) { case DiscreteFunctionType::P0: { - const DiscreteFunctionP0<2, double>& discrete_function = - dynamic_cast<const DiscreteFunctionP0<2, double>&>(i_discrete_function); - - named_item_value_set.add(NamedItemValue{named_discrete_function->name(), discrete_function.cellValues()}); + WriterModule::registerDiscreteFunctionP0(*named_discrete_function, named_item_value_set); break; } default: { diff --git a/src/language/modules/WriterModule.hpp b/src/language/modules/WriterModule.hpp index 49ad6d9fe5b0ce5a39d3b6c0322d200875d48157..08f17851e15153baa4b8cdcfb9dcec25fa7c984e 100644 --- a/src/language/modules/WriterModule.hpp +++ b/src/language/modules/WriterModule.hpp @@ -5,7 +5,12 @@ #include <language/utils/ASTNodeDataTypeTraits.hpp> #include <utils/PugsMacros.hpp> +class OutputNamedItemValueSet; class NamedDiscreteFunction; +class IDiscreteFunction; + +#include <string> + template <> inline ASTNodeDataType ast_node_data_type_from<std::shared_ptr<const NamedDiscreteFunction>> = ASTNodeDataType::build<ASTNodeDataType::type_id_t>("output"); @@ -17,6 +22,15 @@ inline ASTNodeDataType ast_node_data_type_from<std::shared_ptr<const IWriter>> = class WriterModule : public BuiltinModule { + private: + template <size_t Dimension, typename DataType> + static void registerDiscreteFunctionP0(const std::string& name, const IDiscreteFunction&, OutputNamedItemValueSet&); + + template <size_t Dimension> + static void registerDiscreteFunctionP0(const std::string& name, const IDiscreteFunction&, OutputNamedItemValueSet&); + + static void registerDiscreteFunctionP0(const NamedDiscreteFunction&, OutputNamedItemValueSet&); + public: std::string_view name() const final