Loading src/modules/DopingProfileReader/DopingProfileReaderModule.cpp +2 −34 Original line number Diff line number Diff line Loading @@ -58,7 +58,7 @@ void DopingProfileReaderModule::initialize() { LOG(DEBUG) << "Doping concentration map starts with offset " << offset << " to pixel boundary"; std::array<double, 2> field_offset{{model->getPixelSize().x() * offset.x(), model->getPixelSize().y() * offset.y()}}; auto field_data = read_field(field_scale); auto field_data = read_field(); detector_->setDopingProfileGrid(field_data.getData(), field_data.getDimensions(), field_data.getSize(), Loading Loading @@ -116,7 +116,7 @@ void DopingProfileReaderModule::initialize() { * The field read from the INIT format are shared between module instantiations using the static FieldParser. */ FieldParser<double> DopingProfileReaderModule::field_parser_(FieldQuantity::SCALAR); FieldData<double> DopingProfileReaderModule::read_field(std::array<double, 2> field_scale) { FieldData<double> DopingProfileReaderModule::read_field() { try { LOG(TRACE) << "Fetching doping concentration map from mesh file"; Loading @@ -124,9 +124,6 @@ FieldData<double> DopingProfileReaderModule::read_field(std::array<double, 2> fi // Get field from file auto field_data = field_parser_.getByFileName(config_.getPath("file_name", true), "/cm/cm/cm"); // Check if doping concentration profile matches chip check_detector_match(field_data.getSize(), field_scale); LOG(INFO) << "Set doping concentration map with " << field_data.getDimensions().at(0) << "x" << field_data.getDimensions().at(1) << "x" << field_data.getDimensions().at(2) << " cells"; Loading Loading @@ -273,32 +270,3 @@ void DopingProfileReaderModule::create_output_plots() { << " 1/cm3"; } /** * @brief Check if the detector matches the file header */ void DopingProfileReaderModule::check_detector_match(std::array<double, 3> dimensions, std::array<double, 2> field_scale) { auto xpixsz = dimensions[0]; auto ypixsz = dimensions[1]; auto thickness = dimensions[2]; auto model = detector_->getModel(); // Do a several checks with the detector model if(model != nullptr) { // Check field dimension in z versus the sensor thickness: if(std::fabs(thickness - model->getSensorSize().z()) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Thickness of doping concentration map is " << Units::display(thickness, "um") << " but sensor thickness is " << Units::display(model->getSensorSize().z(), "um"); } // Check the field extent along the pixel pitch in x and y: if(std::fabs(xpixsz - model->getPixelSize().x() * field_scale[0]) > std::numeric_limits<double>::epsilon() || std::fabs(ypixsz - model->getPixelSize().y() * field_scale[1]) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Doping concentration map size is (" << Units::display(xpixsz, {"um", "mm"}) << "," << Units::display(ypixsz, {"um", "mm"}) << ") but current configuration results in an map area of (" << Units::display(model->getPixelSize().x() * field_scale[0], {"um", "mm"}) << "," << Units::display(model->getPixelSize().y() * field_scale[1], {"um", "mm"}) << ")" << std::endl << "The size of the area to which the doping concentration is applied can be changes using the " "field_scale parameter."; } } } src/modules/DopingProfileReader/DopingProfileReaderModule.hpp +3 −10 Original line number Diff line number Diff line Loading @@ -50,22 +50,15 @@ namespace allpix { std::shared_ptr<Detector> detector_; /** * @brief Read field in the init format and apply it * @param field_scale Scaling parameters for the field size in x and y * @brief Read field from a file in init or apf format * @return Data of the field read from file */ FieldData<double> read_field(std::array<double, 2> field_scale); FieldData<double> read_field(); static FieldParser<double> field_parser_; /** * @brief Create output plots of the doping profile */ void create_output_plots(); /** * @brief Compare the dimensions of the detector with the field, print warnings * @param dimensions Dimensions of the field read from file * @param field_scale The configured scaling parameters of the electric field in x and y */ void check_detector_match(std::array<double, 3> dimensions, std::array<double, 2> field_scale); }; } // namespace allpix src/modules/ElectricFieldReader/ElectricFieldReaderModule.cpp +2 −42 Original line number Diff line number Diff line Loading @@ -84,8 +84,7 @@ void ElectricFieldReaderModule::initialize() { LOG(DEBUG) << "Electric field starts with offset " << offset << " to pixel boundary"; std::array<double, 2> field_offset{{model->getPixelSize().x() * offset.x(), model->getPixelSize().y() * offset.y()}}; auto field_data = read_field(thickness_domain, field_scale); auto field_data = read_field(); detector_->setElectricFieldGrid(field_data.getData(), field_data.getDimensions(), field_data.getSize(), Loading Loading @@ -294,8 +293,7 @@ ElectricFieldReaderModule::get_custom_field_function(std::pair<double, double> t * FieldParser's getByFileName method. */ FieldParser<double> ElectricFieldReaderModule::field_parser_(FieldQuantity::VECTOR); FieldData<double> ElectricFieldReaderModule::read_field(std::pair<double, double> thickness_domain, std::array<double, 2> field_scale) { FieldData<double> ElectricFieldReaderModule::read_field() { try { LOG(TRACE) << "Fetching electric field from mesh file"; Loading @@ -303,9 +301,6 @@ FieldData<double> ElectricFieldReaderModule::read_field(std::pair<double, double // Get field from file auto field_data = field_parser_.getByFileName(config_.getPath("file_name", true), "V/cm"); // Check if electric field matches chip check_detector_match(field_data.getSize(), thickness_domain, field_scale); // Warn at field values larger than 1MV/cm / 10 MV/mm. Simple lookup per vector component, not total field magnitude auto max_field = *std::max_element(std::begin(*field_data.getData()), std::end(*field_data.getData())); if(max_field > 10) { Loading Loading @@ -505,38 +500,3 @@ void ElectricFieldReaderModule::create_output_plots() { histogram_z->Write(); histogram1D->Write(); } /** * @brief Check if the detector matches the file header */ void ElectricFieldReaderModule::check_detector_match(std::array<double, 3> dimensions, std::pair<double, double> thickness_domain, std::array<double, 2> field_scale) { auto xpixsz = dimensions[0]; auto ypixsz = dimensions[1]; auto thickness = dimensions[2]; auto model = detector_->getModel(); // Do a several checks with the detector model if(model != nullptr) { // Check field dimension in z versus the requested thickness domain: auto eff_thickness = thickness_domain.second - thickness_domain.first; if(std::fabs(thickness - eff_thickness) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Thickness of electric field is " << Units::display(thickness, "um") << " but the depleted region is " << Units::display(eff_thickness, "um"); } // Check the field extent along the pixel pitch in x and y: auto pitch = model->getPixelSize(); if(std::fabs(xpixsz - field_scale[0] * pitch.x()) > std::numeric_limits<double>::epsilon() || std::fabs(ypixsz - field_scale[1] * pitch.y()) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Electric field size is (" << Units::display(xpixsz, {"um", "mm"}) << "," << Units::display(ypixsz, {"um", "mm"}) << ") but current configuration results in an field area of (" << Units::display(field_scale[0] * pitch.x(), {"um", "mm"}) << "," << Units::display(field_scale[1] * pitch.y(), {"um", "mm"}) << ")" << std::endl << "The size of the area to which the electric field is applied can be changes using the " "field_scale parameter."; } } } src/modules/ElectricFieldReader/ElectricFieldReaderModule.hpp +3 −14 Original line number Diff line number Diff line Loading @@ -78,26 +78,15 @@ namespace allpix { FieldFunction<ROOT::Math::XYZVector> get_custom_field_function(std::pair<double, double> thickness_domain); /** * @brief Read field from a file in init or apf format and apply it * @param thickness_domain Domain of the thickness where the field is defined * @param field_scale Scaling parameters for the field size in x and y * @brief Read field from a file in init or apf format * @return Data of the field read from file */ FieldData<double> read_field(std::pair<double, double> thickness_domain, std::array<double, 2> field_scale); FieldData<double> read_field(); static FieldParser<double> field_parser_; /** * @brief Create output plots of the electric field profile */ void create_output_plots(); /** * @brief Compare the dimensions of the detector with the field, print warnings * @param dimensions Dimensions of the field read from file * @param thickness_domain Domain of the thickness where the field is defined * @param field_scale The configured scaling parameters of the electric field in x and y */ void check_detector_match(std::array<double, 3> dimensions, std::pair<double, double> thickness_domain, std::array<double, 2> field_scale); }; } // namespace allpix src/modules/WeightingPotentialReader/WeightingPotentialReaderModule.cpp +2 −40 Original line number Diff line number Diff line Loading @@ -46,7 +46,7 @@ void WeightingPotentialReaderModule::initialize() { // Calculate the potential depending on the configuration if(field_model == WeightingPotential::MESH) { auto field_data = read_field(thickness_domain); auto field_data = read_field(); // Set the field grid, provide scale factors as fraction of the pixel pitch for correct scaling: detector_->setWeightingPotentialGrid(field_data.getData(), Loading Loading @@ -194,7 +194,7 @@ void WeightingPotentialReaderModule::create_output_plots() { * using the static FieldParser's getByFileName method. */ FieldParser<double> WeightingPotentialReaderModule::field_parser_(FieldQuantity::SCALAR); FieldData<double> WeightingPotentialReaderModule::read_field(std::pair<double, double> thickness_domain) { FieldData<double> WeightingPotentialReaderModule::read_field() { using namespace ROOT::Math; try { Loading Loading @@ -229,9 +229,6 @@ FieldData<double> WeightingPotentialReaderModule::read_field(std::pair<double, d } } // Check if weigthing potential matches chip check_detector_match(field_data.getSize(), thickness_domain); LOG(INFO) << "Set weighting field with " << field_data.getDimensions()[0] << "x" << field_data.getDimensions()[1] << "x" << field_data.getDimensions()[2] << " cells"; Loading @@ -245,38 +242,3 @@ FieldData<double> WeightingPotentialReaderModule::read_field(std::pair<double, d throw InvalidValueError(config_, "file_name", "file too large"); } } /** * @brief Check if the detector matches the file header */ void WeightingPotentialReaderModule::check_detector_match(std::array<double, 3> dimensions, std::pair<double, double> thickness_domain) { auto xpixsz = dimensions[0]; auto ypixsz = dimensions[1]; auto thickness = dimensions[2]; auto model = detector_->getModel(); // Do a several checks with the detector model if(model != nullptr) { // Check field dimension in z versus the requested thickness domain: auto eff_thickness = thickness_domain.second - thickness_domain.first; if(std::fabs(thickness - eff_thickness) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Thickness of weighting potential is " << Units::display(thickness, "um") << " but the depleted region is " << Units::display(eff_thickness, "um"); } // Check that the total field size is n*pitch: if(std::fabs(std::remainder(xpixsz, model->getPixelSize().x())) > std::numeric_limits<double>::epsilon() || std::fabs(std::remainder(ypixsz, model->getPixelSize().y())) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Potential map size is (" << Units::display(xpixsz, {"um", "mm"}) << "," << Units::display(ypixsz, {"um", "mm"}) << ") but expecting a multiple of the pixel pitch (" << Units::display(model->getPixelSize().x(), {"um", "mm"}) << ", " << Units::display(model->getPixelSize().y(), {"um", "mm"}) << ")"; } else { LOG(INFO) << "Potential map size is (" << Units::display(xpixsz, {"um", "mm"}) << "," << Units::display(ypixsz, {"um", "mm"}) << "), matching detector model with pixel pitch (" << Units::display(model->getPixelSize().x(), {"um", "mm"}) << ", " << Units::display(model->getPixelSize().y(), {"um", "mm"}) << ")"; } } } Loading
src/modules/DopingProfileReader/DopingProfileReaderModule.cpp +2 −34 Original line number Diff line number Diff line Loading @@ -58,7 +58,7 @@ void DopingProfileReaderModule::initialize() { LOG(DEBUG) << "Doping concentration map starts with offset " << offset << " to pixel boundary"; std::array<double, 2> field_offset{{model->getPixelSize().x() * offset.x(), model->getPixelSize().y() * offset.y()}}; auto field_data = read_field(field_scale); auto field_data = read_field(); detector_->setDopingProfileGrid(field_data.getData(), field_data.getDimensions(), field_data.getSize(), Loading Loading @@ -116,7 +116,7 @@ void DopingProfileReaderModule::initialize() { * The field read from the INIT format are shared between module instantiations using the static FieldParser. */ FieldParser<double> DopingProfileReaderModule::field_parser_(FieldQuantity::SCALAR); FieldData<double> DopingProfileReaderModule::read_field(std::array<double, 2> field_scale) { FieldData<double> DopingProfileReaderModule::read_field() { try { LOG(TRACE) << "Fetching doping concentration map from mesh file"; Loading @@ -124,9 +124,6 @@ FieldData<double> DopingProfileReaderModule::read_field(std::array<double, 2> fi // Get field from file auto field_data = field_parser_.getByFileName(config_.getPath("file_name", true), "/cm/cm/cm"); // Check if doping concentration profile matches chip check_detector_match(field_data.getSize(), field_scale); LOG(INFO) << "Set doping concentration map with " << field_data.getDimensions().at(0) << "x" << field_data.getDimensions().at(1) << "x" << field_data.getDimensions().at(2) << " cells"; Loading Loading @@ -273,32 +270,3 @@ void DopingProfileReaderModule::create_output_plots() { << " 1/cm3"; } /** * @brief Check if the detector matches the file header */ void DopingProfileReaderModule::check_detector_match(std::array<double, 3> dimensions, std::array<double, 2> field_scale) { auto xpixsz = dimensions[0]; auto ypixsz = dimensions[1]; auto thickness = dimensions[2]; auto model = detector_->getModel(); // Do a several checks with the detector model if(model != nullptr) { // Check field dimension in z versus the sensor thickness: if(std::fabs(thickness - model->getSensorSize().z()) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Thickness of doping concentration map is " << Units::display(thickness, "um") << " but sensor thickness is " << Units::display(model->getSensorSize().z(), "um"); } // Check the field extent along the pixel pitch in x and y: if(std::fabs(xpixsz - model->getPixelSize().x() * field_scale[0]) > std::numeric_limits<double>::epsilon() || std::fabs(ypixsz - model->getPixelSize().y() * field_scale[1]) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Doping concentration map size is (" << Units::display(xpixsz, {"um", "mm"}) << "," << Units::display(ypixsz, {"um", "mm"}) << ") but current configuration results in an map area of (" << Units::display(model->getPixelSize().x() * field_scale[0], {"um", "mm"}) << "," << Units::display(model->getPixelSize().y() * field_scale[1], {"um", "mm"}) << ")" << std::endl << "The size of the area to which the doping concentration is applied can be changes using the " "field_scale parameter."; } } }
src/modules/DopingProfileReader/DopingProfileReaderModule.hpp +3 −10 Original line number Diff line number Diff line Loading @@ -50,22 +50,15 @@ namespace allpix { std::shared_ptr<Detector> detector_; /** * @brief Read field in the init format and apply it * @param field_scale Scaling parameters for the field size in x and y * @brief Read field from a file in init or apf format * @return Data of the field read from file */ FieldData<double> read_field(std::array<double, 2> field_scale); FieldData<double> read_field(); static FieldParser<double> field_parser_; /** * @brief Create output plots of the doping profile */ void create_output_plots(); /** * @brief Compare the dimensions of the detector with the field, print warnings * @param dimensions Dimensions of the field read from file * @param field_scale The configured scaling parameters of the electric field in x and y */ void check_detector_match(std::array<double, 3> dimensions, std::array<double, 2> field_scale); }; } // namespace allpix
src/modules/ElectricFieldReader/ElectricFieldReaderModule.cpp +2 −42 Original line number Diff line number Diff line Loading @@ -84,8 +84,7 @@ void ElectricFieldReaderModule::initialize() { LOG(DEBUG) << "Electric field starts with offset " << offset << " to pixel boundary"; std::array<double, 2> field_offset{{model->getPixelSize().x() * offset.x(), model->getPixelSize().y() * offset.y()}}; auto field_data = read_field(thickness_domain, field_scale); auto field_data = read_field(); detector_->setElectricFieldGrid(field_data.getData(), field_data.getDimensions(), field_data.getSize(), Loading Loading @@ -294,8 +293,7 @@ ElectricFieldReaderModule::get_custom_field_function(std::pair<double, double> t * FieldParser's getByFileName method. */ FieldParser<double> ElectricFieldReaderModule::field_parser_(FieldQuantity::VECTOR); FieldData<double> ElectricFieldReaderModule::read_field(std::pair<double, double> thickness_domain, std::array<double, 2> field_scale) { FieldData<double> ElectricFieldReaderModule::read_field() { try { LOG(TRACE) << "Fetching electric field from mesh file"; Loading @@ -303,9 +301,6 @@ FieldData<double> ElectricFieldReaderModule::read_field(std::pair<double, double // Get field from file auto field_data = field_parser_.getByFileName(config_.getPath("file_name", true), "V/cm"); // Check if electric field matches chip check_detector_match(field_data.getSize(), thickness_domain, field_scale); // Warn at field values larger than 1MV/cm / 10 MV/mm. Simple lookup per vector component, not total field magnitude auto max_field = *std::max_element(std::begin(*field_data.getData()), std::end(*field_data.getData())); if(max_field > 10) { Loading Loading @@ -505,38 +500,3 @@ void ElectricFieldReaderModule::create_output_plots() { histogram_z->Write(); histogram1D->Write(); } /** * @brief Check if the detector matches the file header */ void ElectricFieldReaderModule::check_detector_match(std::array<double, 3> dimensions, std::pair<double, double> thickness_domain, std::array<double, 2> field_scale) { auto xpixsz = dimensions[0]; auto ypixsz = dimensions[1]; auto thickness = dimensions[2]; auto model = detector_->getModel(); // Do a several checks with the detector model if(model != nullptr) { // Check field dimension in z versus the requested thickness domain: auto eff_thickness = thickness_domain.second - thickness_domain.first; if(std::fabs(thickness - eff_thickness) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Thickness of electric field is " << Units::display(thickness, "um") << " but the depleted region is " << Units::display(eff_thickness, "um"); } // Check the field extent along the pixel pitch in x and y: auto pitch = model->getPixelSize(); if(std::fabs(xpixsz - field_scale[0] * pitch.x()) > std::numeric_limits<double>::epsilon() || std::fabs(ypixsz - field_scale[1] * pitch.y()) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Electric field size is (" << Units::display(xpixsz, {"um", "mm"}) << "," << Units::display(ypixsz, {"um", "mm"}) << ") but current configuration results in an field area of (" << Units::display(field_scale[0] * pitch.x(), {"um", "mm"}) << "," << Units::display(field_scale[1] * pitch.y(), {"um", "mm"}) << ")" << std::endl << "The size of the area to which the electric field is applied can be changes using the " "field_scale parameter."; } } }
src/modules/ElectricFieldReader/ElectricFieldReaderModule.hpp +3 −14 Original line number Diff line number Diff line Loading @@ -78,26 +78,15 @@ namespace allpix { FieldFunction<ROOT::Math::XYZVector> get_custom_field_function(std::pair<double, double> thickness_domain); /** * @brief Read field from a file in init or apf format and apply it * @param thickness_domain Domain of the thickness where the field is defined * @param field_scale Scaling parameters for the field size in x and y * @brief Read field from a file in init or apf format * @return Data of the field read from file */ FieldData<double> read_field(std::pair<double, double> thickness_domain, std::array<double, 2> field_scale); FieldData<double> read_field(); static FieldParser<double> field_parser_; /** * @brief Create output plots of the electric field profile */ void create_output_plots(); /** * @brief Compare the dimensions of the detector with the field, print warnings * @param dimensions Dimensions of the field read from file * @param thickness_domain Domain of the thickness where the field is defined * @param field_scale The configured scaling parameters of the electric field in x and y */ void check_detector_match(std::array<double, 3> dimensions, std::pair<double, double> thickness_domain, std::array<double, 2> field_scale); }; } // namespace allpix
src/modules/WeightingPotentialReader/WeightingPotentialReaderModule.cpp +2 −40 Original line number Diff line number Diff line Loading @@ -46,7 +46,7 @@ void WeightingPotentialReaderModule::initialize() { // Calculate the potential depending on the configuration if(field_model == WeightingPotential::MESH) { auto field_data = read_field(thickness_domain); auto field_data = read_field(); // Set the field grid, provide scale factors as fraction of the pixel pitch for correct scaling: detector_->setWeightingPotentialGrid(field_data.getData(), Loading Loading @@ -194,7 +194,7 @@ void WeightingPotentialReaderModule::create_output_plots() { * using the static FieldParser's getByFileName method. */ FieldParser<double> WeightingPotentialReaderModule::field_parser_(FieldQuantity::SCALAR); FieldData<double> WeightingPotentialReaderModule::read_field(std::pair<double, double> thickness_domain) { FieldData<double> WeightingPotentialReaderModule::read_field() { using namespace ROOT::Math; try { Loading Loading @@ -229,9 +229,6 @@ FieldData<double> WeightingPotentialReaderModule::read_field(std::pair<double, d } } // Check if weigthing potential matches chip check_detector_match(field_data.getSize(), thickness_domain); LOG(INFO) << "Set weighting field with " << field_data.getDimensions()[0] << "x" << field_data.getDimensions()[1] << "x" << field_data.getDimensions()[2] << " cells"; Loading @@ -245,38 +242,3 @@ FieldData<double> WeightingPotentialReaderModule::read_field(std::pair<double, d throw InvalidValueError(config_, "file_name", "file too large"); } } /** * @brief Check if the detector matches the file header */ void WeightingPotentialReaderModule::check_detector_match(std::array<double, 3> dimensions, std::pair<double, double> thickness_domain) { auto xpixsz = dimensions[0]; auto ypixsz = dimensions[1]; auto thickness = dimensions[2]; auto model = detector_->getModel(); // Do a several checks with the detector model if(model != nullptr) { // Check field dimension in z versus the requested thickness domain: auto eff_thickness = thickness_domain.second - thickness_domain.first; if(std::fabs(thickness - eff_thickness) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Thickness of weighting potential is " << Units::display(thickness, "um") << " but the depleted region is " << Units::display(eff_thickness, "um"); } // Check that the total field size is n*pitch: if(std::fabs(std::remainder(xpixsz, model->getPixelSize().x())) > std::numeric_limits<double>::epsilon() || std::fabs(std::remainder(ypixsz, model->getPixelSize().y())) > std::numeric_limits<double>::epsilon()) { LOG(WARNING) << "Potential map size is (" << Units::display(xpixsz, {"um", "mm"}) << "," << Units::display(ypixsz, {"um", "mm"}) << ") but expecting a multiple of the pixel pitch (" << Units::display(model->getPixelSize().x(), {"um", "mm"}) << ", " << Units::display(model->getPixelSize().y(), {"um", "mm"}) << ")"; } else { LOG(INFO) << "Potential map size is (" << Units::display(xpixsz, {"um", "mm"}) << "," << Units::display(ypixsz, {"um", "mm"}) << "), matching detector model with pixel pitch (" << Units::display(model->getPixelSize().x(), {"um", "mm"}) << ", " << Units::display(model->getPixelSize().y(), {"um", "mm"}) << ")"; } } }