diff --git a/src/modules/AnalysisEfficiency/AnalysisEfficiency.cpp b/src/modules/AnalysisEfficiency/AnalysisEfficiency.cpp
index 52f01028170e560f35df0b3cf0e722299955298b..fdf1f4a9839fed3215a8e482d5843dc5fdf28682 100644
--- a/src/modules/AnalysisEfficiency/AnalysisEfficiency.cpp
+++ b/src/modules/AnalysisEfficiency/AnalysisEfficiency.cpp
@@ -23,8 +23,8 @@ AnalysisEfficiency::AnalysisEfficiency(Configuration& config, std::shared_ptr<De
 
     config_.setDefault<double>("time_cut_frameedge", Units::get<double>(20, "ns"));
     config_.setDefault<double>("chi2ndof_cut", 3.);
-    config_.setDefault<double>("inpixel_bin_size", Units::get<double>(1.0, "um"));
-    config_.setDefault<XYVector>("inpixel_cut_edge", {Units::get(5.0, "um"), Units::get(5.0, "um")});
+    config_.setDefault<ROOT::Math::XYPoint>("inpixel_bin_size", {Units::get(1.0, "um"), Units::get(1.0, "um")});
+    config_.setDefault<ROOT::Math::XYPoint>("inpixel_cut_edge", {Units::get(5.0, "um"), Units::get(5.0, "um")});
     config_.setDefault<double>("masked_pixel_distance_cut", 1.);
     config_.setDefault<double>("spatial_cut_sensoredge", 1.);
     config_.setDefault<FakeRateMethod>("fake_rate_method", FakeRateMethod::RADIUS);
@@ -34,15 +34,27 @@ AnalysisEfficiency::AnalysisEfficiency(Configuration& config, std::shared_ptr<De
 
     m_timeCutFrameEdge = config_.get<double>("time_cut_frameedge");
     m_chi2ndofCut = config_.get<double>("chi2ndof_cut");
-    m_inpixelBinSize = config_.get<double>("inpixel_bin_size");
     require_associated_cluster_on_ = config_.getArray<std::string>("require_associated_cluster_on", {});
-    m_inpixelEdgeCut = config_.get<XYVector>("inpixel_cut_edge");
     m_maskedPixelDistanceCut = config_.get<int>("masked_pixel_distance_cut");
     spatial_cut_sensoredge = config_.get<double>("spatial_cut_sensoredge");
     m_fake_rate_method = config_.get<FakeRateMethod>("fake_rate_method");
     m_fake_rate_distance = config_.get<double>("fake_rate_distance");
     m_n_charge_bins = config_.get<int>("n_charge_bins");
     m_charge_histo_range = config_.get<double>("charge_histo_range");
+
+    if(config_.getArray<double>("inpixel_bin_size").size() == 2) {
+        m_inpixelBinSize = config_.get<ROOT::Math::XYPoint>("inpixel_bin_size");
+    } else {
+        auto binsize = config_.get<double>("inpixel_bin_size");
+        m_inpixelBinSize = ROOT::Math::XYPoint(binsize, binsize);
+    }
+
+    if(config_.getArray<double>("inpixel_cut_edge").size() == 2) {
+        m_inpixelEdgeCut = config_.get<ROOT::Math::XYPoint>("inpixel_cut_edge");
+    } else {
+        auto edgecut = config_.get<double>("inpixel_cut_edge");
+        m_inpixelEdgeCut = ROOT::Math::XYPoint(edgecut, edgecut);
+    }
 }
 void AnalysisEfficiency::initialize() {
 
@@ -58,8 +70,8 @@ void AnalysisEfficiency::initialize() {
     auto pitch_x = static_cast<double>(Units::convert(m_detector->getPitch().X(), "um"));
     auto pitch_y = static_cast<double>(Units::convert(m_detector->getPitch().Y(), "um"));
 
-    auto nbins_x = static_cast<int>(std::ceil(m_detector->getPitch().X() / m_inpixelBinSize));
-    auto nbins_y = static_cast<int>(std::ceil(m_detector->getPitch().Y() / m_inpixelBinSize));
+    auto nbins_x = static_cast<int>(std::ceil(m_detector->getPitch().X() / m_inpixelBinSize.x()));
+    auto nbins_y = static_cast<int>(std::ceil(m_detector->getPitch().Y() / m_inpixelBinSize.y()));
     if(nbins_x > 1e4 || nbins_y > 1e4) {
         throw InvalidValueError(config_, "inpixel_bin_size", "Too many bins for in-pixel histograms.");
     }
diff --git a/src/modules/AnalysisEfficiency/AnalysisEfficiency.h b/src/modules/AnalysisEfficiency/AnalysisEfficiency.h
index 5617709cb46c0dc1e9f9163455b9adb246198553..43e8fc0e72efb07a4e60d5ddb8b4bb422c9bd556 100644
--- a/src/modules/AnalysisEfficiency/AnalysisEfficiency.h
+++ b/src/modules/AnalysisEfficiency/AnalysisEfficiency.h
@@ -101,10 +101,9 @@ namespace corryvreckan {
             EDGE,
         } m_fake_rate_method;
 
-        double m_chi2ndofCut, m_timeCutFrameEdge, m_inpixelBinSize, spatial_cut_sensoredge, m_fake_rate_distance,
-            m_charge_histo_range;
+        double m_chi2ndofCut, m_timeCutFrameEdge, spatial_cut_sensoredge, m_fake_rate_distance, m_charge_histo_range;
         int m_n_charge_bins;
-        XYVector m_inpixelEdgeCut;
+        ROOT::Math::XYPoint m_inpixelEdgeCut, m_inpixelBinSize;
         int m_maskedPixelDistanceCut = 1;
         int total_tracks = 0;
         int matched_tracks = 0;
diff --git a/src/modules/AnalysisEfficiency/README.md b/src/modules/AnalysisEfficiency/README.md
index ff4f28b6b4c4115cfed7aff1d02b84f28f5487ac..e0e7762d72e204eaeb67b3d71e19deaa4b5ad74b 100644
--- a/src/modules/AnalysisEfficiency/README.md
+++ b/src/modules/AnalysisEfficiency/README.md
@@ -22,8 +22,8 @@ More information can be found in the ROOT `TEfficiency` class reference, section
 ### Parameters
 * `time_cut_frameedge`: Parameter to discard telescope tracks at the frame edges (start and end of the current event window). Defaults to `20ns`.
 * `chi2ndof_cut`: Acceptance criterion for telescope tracks, defaults to a value of `3`.
-* `inpixel_bin_size`: Parameter to set the bin size of the in-pixel 2D efficiency histogram. This should be given in units of distance and the same value is used in both axes. Defaults to `1.0um`.
-* `inpixel_cut_edge`: Parameter to exclude tracks going within a cut-distance to the pixel edge. Effectively defines an in-pixel ROI. Defaults to `5um`.
+* `inpixel_bin_size`: Parameter to set the bin size of the in-pixel 2D efficiency histogram. This should be given in units of distance. Different bin sizes can be set for the x and y axis. Defaults to `1.0um`, `1.0um`.
+* `inpixel_cut_edge`: Parameter to exclude tracks going within a cut-distance to the pixel edge. Effectively defines an in-pixel ROI. Different cuts can be set for the x and y axis. Defaults to `5um`, `5um`.
 * `masked_pixel_distance_cut`: Distance (in pixels) to exclude tracks passing close to masked pixel. Defaults to `1`.
 * `require_associated_cluster_on`: Names of detectors which are required to have an associated cluster to the telescope tracks. Detectors listed here must be marked as `role = DUT` in the detector configuration file. Only tracks satisfying this requirement are accepted for the efficiency measurement. If empty, no detector is required. Default is empty.
 * `spatial_cut_sensoredge`: Parameter to discard telescope tracks at the sensor edges in fractions of pixel pitch. Defaults to `1`.