Commit a4f22264 authored by Simon Spannagel's avatar Simon Spannagel
Browse files

Detector: move check_field method from readers to Detector class

parent 1b28e423
Loading
Loading
Loading
Loading
+35 −0
Original line number Diff line number Diff line
@@ -153,9 +153,11 @@ FieldType Detector::getElectricFieldType() const {
 */
void Detector::setElectricFieldGrid(const std::shared_ptr<std::vector<double>>& field,
                                    std::array<size_t, 3> dimensions,
                                    std::array<double, 3> size,
                                    std::array<double, 2> scales,
                                    std::array<double, 2> offset,
                                    std::pair<double, double> thickness_domain) {
    check_field_match(size, scales, thickness_domain);
    electric_field_.setGrid(field, dimensions, scales, offset, thickness_domain);
}

@@ -194,9 +196,11 @@ FieldType Detector::getWeightingPotentialType() const {
 */
void Detector::setWeightingPotentialGrid(const std::shared_ptr<std::vector<double>>& potential,
                                         std::array<size_t, 3> dimensions,
                                         std::array<double, 3> size,
                                         std::array<double, 2> scales,
                                         std::array<double, 2> offset,
                                         std::pair<double, double> thickness_domain) {
    check_field_match(size, scales, thickness_domain);
    weighting_potential_.setGrid(potential, dimensions, scales, offset, thickness_domain);
}

@@ -256,9 +260,11 @@ FieldType Detector::getDopingProfileType() const {
 */
void Detector::setDopingProfileGrid(std::shared_ptr<std::vector<double>> field,
                                    std::array<size_t, 3> dimensions,
                                    std::array<double, 3> size,
                                    std::array<double, 2> scales,
                                    std::array<double, 2> offset,
                                    std::pair<double, double> thickness_domain) {
    check_field_match(size, scales, thickness_domain);
    doping_profile_.setGrid(std::move(field), dimensions, scales, offset, thickness_domain);
}

@@ -268,3 +274,32 @@ void Detector::setDopingProfileFunction(FieldFunction<double> function, FieldTyp
                                 model_->getSensorCenter().z() + model_->getSensorSize().z() / 2},
                                type);
}

void Detector::check_field_match(std::array<double, 3> size,
                                 std::array<double, 2> field_scale,
                                 std::pair<double, double> thickness_domain) const {

    // Check field dimension in z versus the requested thickness domain:
    auto eff_thickness = thickness_domain.second - thickness_domain.first;
    if(std::fabs(size[2] - eff_thickness) > std::numeric_limits<double>::epsilon()) {
        LOG(WARNING) << "Thickness of field is " << Units::display(size[2], "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(size[0], field_scale[0] * model_->getPixelSize().x())) >
           std::numeric_limits<double>::epsilon() ||
       std::fabs(std::remainder(size[1], field_scale[1] * model_->getPixelSize().y())) >
           std::numeric_limits<double>::epsilon()) {
        LOG(WARNING) << "Field map size is (" << Units::display(size[0], {"um", "mm"}) << ","
                     << Units::display(size[1], {"um", "mm"}) << ") but expecting a multiple of the pixel pitch ("
                     << Units::display(model_->getPixelSize().x(), {"um", "mm"}) << ", "
                     << Units::display(model_->getPixelSize().y(), {"um", "mm"}) << ")" << std::endl
                     << "The area to which the field is applied can be changed using the field_scale parameter.";
    } else {
        LOG(INFO) << "Field map size is (" << Units::display(size[0], {"um", "mm"}) << ","
                  << Units::display(size[1], {"um", "mm"}) << "), matching detector model with pixel pitch ("
                  << Units::display(model_->getPixelSize().x(), {"um", "mm"}) << ", "
                  << Units::display(model_->getPixelSize().y(), {"um", "mm"}) << ")";
    }
}
+16 −1
Original line number Diff line number Diff line
@@ -24,7 +24,6 @@
#include <Math/Rotation3D.h>
#include <Math/Transform3D.h>

#include "Detector.hpp"
#include "DetectorField.hpp"
#include "DetectorModel.hpp"

@@ -123,12 +122,14 @@ namespace allpix {
         * @brief Set the electric field in a single pixel in the detector using a grid
         * @param field Flat array of the field vectors (see detailed description)
         * @param dimensions The dimensions of the flat electric field array
         * @param size Size of the electric field along the three dimensions of the field map
         * @param scales Scaling factors for the field size, given in fractions of a pixel unit cell in x and y
         * @param offset Offset of the field from the pixel border
         * @param thickness_domain Domain in local coordinates in the thickness direction where the field holds
         */
        void setElectricFieldGrid(const std::shared_ptr<std::vector<double>>& field,
                                  std::array<size_t, 3> dimensions,
                                  std::array<double, 3> size,
                                  std::array<double, 2> scales,
                                  std::array<double, 2> offset,
                                  std::pair<double, double> thickness_domain);
@@ -163,12 +164,14 @@ namespace allpix {
         * @brief Set the doping profile in a single pixel in the detector using a grid
         * @param field Flat array of the field (see detailed description)
         * @param dimensions The dimensions of the flat doping profile array
         * @param size Size of the doping profile along the three dimensions of the field map
         * @param scales Scaling factors for the field size, given in fractions of a pixel unit cell in x and y
         * @param offset Offset of the field from the pixel border
         * @param thickness_domain Domain in local coordinates in the thickness direction where the profile holds
         */
        void setDopingProfileGrid(std::shared_ptr<std::vector<double>> field,
                                  std::array<size_t, 3> dimensions,
                                  std::array<double, 3> size,
                                  std::array<double, 2> scales,
                                  std::array<double, 2> offset,
                                  std::pair<double, double> thickness_domain);
@@ -202,12 +205,14 @@ namespace allpix {
         * @brief Set the weighting potential in a single pixel in the detector using a grid
         * @param potential Flat array of the potential vectors (see detailed description)
         * @param dimensions The dimensions of the flat weighting potential array
         * @param size Size of the weighting potential along the three dimensions of the field map
         * @param scales Scaling factors for the field size, given in fractions of a pixel unit cell in x and y
         * @param offset Offset of the field from the pixel border
         * @param thickness_domain Domain in local coordinates in the thickness direction where the potential holds
         */
        void setWeightingPotentialGrid(const std::shared_ptr<std::vector<double>>& potential,
                                       std::array<size_t, 3> dimensions,
                                       std::array<double, 3> size,
                                       std::array<double, 2> scales,
                                       std::array<double, 2> offset,
                                       std::pair<double, double> thickness_domain);
@@ -265,6 +270,16 @@ namespace allpix {
         */
        void build_transform();

        /**
         * @brief Check validity of the field map for this detector
         * @param size Size of the field in the three dimensions
         * @param field_scale Scaling factors for the field
         * @param thickness_domain Thickness domain in which the field is defined in
         */
        void check_field_match(std::array<double, 3> size,
                               std::array<double, 2> field_scale,
                               std::pair<double, double> thickness_domain) const;

        std::string name_;
        std::shared_ptr<DetectorModel> model_;

+6 −2
Original line number Diff line number Diff line
@@ -59,8 +59,12 @@ void DopingProfileReaderModule::initialize() {
        std::array<double, 2> field_offset{{model->getPixelSize().x() * offset.x(), model->getPixelSize().y() * offset.y()}};

        auto field_data = read_field(field_scale);
        detector_->setDopingProfileGrid(
            field_data.getData(), field_data.getDimensions(), field_scale, field_offset, thickness_domain);
        detector_->setDopingProfileGrid(field_data.getData(),
                                        field_data.getDimensions(),
                                        field_data.getSize(),
                                        field_scale,
                                        field_offset,
                                        thickness_domain);

    } else if(field_model == DopingProfile::CONSTANT) {
        LOG(TRACE) << "Adding constant doping concentration";
+6 −2
Original line number Diff line number Diff line
@@ -86,8 +86,12 @@ void ElectricFieldReaderModule::initialize() {

        auto field_data = read_field(thickness_domain, field_scale);

        detector_->setElectricFieldGrid(
            field_data.getData(), field_data.getDimensions(), field_scale, field_offset, thickness_domain);
        detector_->setElectricFieldGrid(field_data.getData(),
                                        field_data.getDimensions(),
                                        field_data.getSize(),
                                        field_scale,
                                        field_offset,
                                        thickness_domain);
    } else if(field_model == ElectricField::CONSTANT) {
        LOG(TRACE) << "Adding constant electric field";
        auto field_z = config_.get<double>("bias_voltage") / getDetector()->getModel()->getSensorSize().z();
+1 −0
Original line number Diff line number Diff line
@@ -51,6 +51,7 @@ void WeightingPotentialReaderModule::initialize() {
        // Set the field grid, provide scale factors as fraction of the pixel pitch for correct scaling:
        detector_->setWeightingPotentialGrid(field_data.getData(),
                                             field_data.getDimensions(),
                                             field_data.getSize(),
                                             std::array<double, 2>{{field_data.getSize()[0] / model->getPixelSize().x(),
                                                                    field_data.getSize()[1] / model->getPixelSize().y()}},
                                             std::array<double, 2>{{0, 0}},