diff --git a/Framework/Crystal/src/PeaksIntersection.cpp b/Framework/Crystal/src/PeaksIntersection.cpp
index e3a1362ee3b769e7e22bbf79a372230678ab352e..32f0e1cf1781ed975e30338475572a60f763a59f 100644
--- a/Framework/Crystal/src/PeaksIntersection.cpp
+++ b/Framework/Crystal/src/PeaksIntersection.cpp
@@ -11,6 +11,7 @@
 #include "MantidGeometry/Crystal/IPeak.h"
 #include "MantidKernel/ListValidator.h"
 
+#include <variant>
 #include <boost/function.hpp>
 
 using namespace Mantid::API;
@@ -79,14 +80,15 @@ void PeaksIntersection::executePeaksIntersection(const bool checkPeakExtents) {
 
   m_peakRadius = this->getProperty("PeakRadius");
 
-  // Find the coordinate frame to use an set up boost function for this.
-  boost::function<V3D(IPeak *)> coordFrameFunc = &IPeak::getHKL;
+
+  boost::function<V3D(Peak *)> coordFrameFunc;
+  coordFrameFunc = &Peak::getHKL;
   if (coordinateFrame == detectorSpaceFrame()) {
     coordFrameFunc = &Peak::getDetectorPosition;
   } else if (coordinateFrame == qLabFrame()) {
-    coordFrameFunc = &IPeak::getQLabFrame;
+    coordFrameFunc = &Peak::getQLabFrame;
   } else if (coordinateFrame == qSampleFrame()) {
-    coordFrameFunc = &IPeak::getQSampleFrame;
+    coordFrameFunc = &Peak::getQSampleFrame;
   }
 
   // Create the faces.
diff --git a/Framework/DataObjects/inc/MantidDataObjects/LeanElasticPeak.h b/Framework/DataObjects/inc/MantidDataObjects/LeanElasticPeak.h
index 177a1e0b5313ccbf2b182a0c3b1704c08b8a6097..70be75f466250ca230a6c7594ee2205d2bb4f6d8 100644
--- a/Framework/DataObjects/inc/MantidDataObjects/LeanElasticPeak.h
+++ b/Framework/DataObjects/inc/MantidDataObjects/LeanElasticPeak.h
@@ -86,7 +86,6 @@ public:
   void setInitialEnergy(double m_initialEnergy) override;
   void setFinalEnergy(double m_finalEnergy) override;
 
-  virtual Mantid::Kernel::V3D getDetPos() const override;
   virtual Mantid::Kernel::V3D getSamplePos() const override;
   double getL1() const override;
   double getL2() const override;
diff --git a/Framework/DataObjects/inc/MantidDataObjects/Peak.h b/Framework/DataObjects/inc/MantidDataObjects/Peak.h
index a9b0b469942a493ba54ec99045511257826dfd24..7aad8c7984a4babb970ace7ce8e2e95008e0b68a 100644
--- a/Framework/DataObjects/inc/MantidDataObjects/Peak.h
+++ b/Framework/DataObjects/inc/MantidDataObjects/Peak.h
@@ -121,7 +121,7 @@ public:
   void setInitialEnergy(double m_initialEnergy) override;
   void setFinalEnergy(double m_finalEnergy) override;
 
-  virtual Mantid::Kernel::V3D getDetPos() const override;
+  virtual Mantid::Kernel::V3D getDetPos() const;
   virtual Mantid::Kernel::V3D getSamplePos() const override;
   double getL1() const override;
   double getL2() const override;
diff --git a/Framework/DataObjects/src/LeanElasticPeak.cpp b/Framework/DataObjects/src/LeanElasticPeak.cpp
index 78ef70a7c3a53f5e3b173f275a5f76e1f0e89d9a..6496765f1d33a5e422d83881343423d582391728 100644
--- a/Framework/DataObjects/src/LeanElasticPeak.cpp
+++ b/Framework/DataObjects/src/LeanElasticPeak.cpp
@@ -256,13 +256,6 @@ void LeanElasticPeak::setInitialEnergy(double) {
   throw Exception::NotImplementedError("Use LeanElasticPeak::setWavelength");
 }
 
-// -------------------------------------------------------------------------------------
-/** Return the detector position vector */
-Mantid::Kernel::V3D LeanElasticPeak::getDetPos() const {
-  throw Exception::NotImplementedError(
-      "LeanElasticPeak has no detector information");
-}
-
 // -------------------------------------------------------------------------------------
 /** Return the sample position vector */
 Mantid::Kernel::V3D LeanElasticPeak::getSamplePos() const {
diff --git a/Framework/DataObjects/test/LeanElasticPeakTest.h b/Framework/DataObjects/test/LeanElasticPeakTest.h
index 723ad67eafaf2a63c388dbab14966c0188f1ab76..2508c532ca23be1358b58beaac3e845d63b70a74 100644
--- a/Framework/DataObjects/test/LeanElasticPeakTest.h
+++ b/Framework/DataObjects/test/LeanElasticPeakTest.h
@@ -37,8 +37,6 @@ public:
     TS_ASSERT(std::isinf(p.getFinalEnergy()))
     TS_ASSERT_EQUALS(p.getQSampleFrame(), V3D(0, 0, 0))
     TS_ASSERT_EQUALS(p.getQLabFrame(), V3D())
-
-    TS_ASSERT_THROWS(p.getDetPos(), const Exception::NotImplementedError &)
     TS_ASSERT_THROWS(p.getSamplePos(), const Exception::NotImplementedError &)
     TS_ASSERT_THROWS(p.getTOF(), const Exception::NotImplementedError &)
     TS_ASSERT_EQUALS(p.getScattering(), 0.)
diff --git a/Framework/Geometry/inc/MantidGeometry/Crystal/IPeak.h b/Framework/Geometry/inc/MantidGeometry/Crystal/IPeak.h
index e79b1f40e21f3cd5b9816d67e036821d2c92db14..341c3d9873a2cf2c788e3d9042579d29758ebe1e 100644
--- a/Framework/Geometry/inc/MantidGeometry/Crystal/IPeak.h
+++ b/Framework/Geometry/inc/MantidGeometry/Crystal/IPeak.h
@@ -94,7 +94,6 @@ public:
   virtual int getRow() const = 0;
   virtual int getCol() const = 0;
 
-  virtual Mantid::Kernel::V3D getDetPos() const = 0;
   virtual double getL1() const = 0;
   virtual double getL2() const = 0;
 
diff --git a/Framework/Geometry/test/MockObjects.h b/Framework/Geometry/test/MockObjects.h
index d3eb35d6ff01583cd2657f40d9fe67b7a1eb0fb9..33924160b206af682c3b3e10a07d0aa3dc84847b 100644
--- a/Framework/Geometry/test/MockObjects.h
+++ b/Framework/Geometry/test/MockObjects.h
@@ -122,7 +122,6 @@ public:
   MOCK_CONST_METHOD0(getBankName, std::string());
   MOCK_CONST_METHOD0(getRow, int());
   MOCK_CONST_METHOD0(getCol, int());
-  MOCK_CONST_METHOD0(getDetPos, Mantid::Kernel::V3D());
   MOCK_CONST_METHOD0(getL1, double());
   MOCK_CONST_METHOD0(getL2, double());
   MOCK_CONST_METHOD0(getPeakShape, const Mantid::Geometry::PeakShape &());
diff --git a/Framework/PythonInterface/mantid/api/src/Exports/IPeak.cpp b/Framework/PythonInterface/mantid/api/src/Exports/IPeak.cpp
index d9398e8d6d986f8b56b4da973d78e823db2d7a9c..03e4be767ee78c3a2951ca0fa23360b1de848d8e 100644
--- a/Framework/PythonInterface/mantid/api/src/Exports/IPeak.cpp
+++ b/Framework/PythonInterface/mantid/api/src/Exports/IPeak.cpp
@@ -209,8 +209,6 @@ void export_IPeak() {
            "For :class:`~mantid.geometry.RectangularDetector` s only, returns "
            "the column (x) of the pixel of the "
            ":class:`~mantid.geometry.Detector`.")
-      .def("getDetPos", &IPeak::getDetPos, arg("self"),
-           "Return the :class:`~mantid.geometry.Detector` position vector")
       .def("getL1", &IPeak::getL1, arg("self"),
            "Return the L1 flight path length (source to "
            ":class:`~mantid.api.Sample`), in meters. ")
diff --git a/Framework/PythonInterface/plugins/algorithms/SaveHKLCW.py b/Framework/PythonInterface/plugins/algorithms/SaveHKLCW.py
index 85eca56ccbe945c51cff6ca379e557922865ba7d..32f555f0c5cf5a52fd8f0b48858db7644932a3c3 100644
--- a/Framework/PythonInterface/plugins/algorithms/SaveHKLCW.py
+++ b/Framework/PythonInterface/plugins/algorithms/SaveHKLCW.py
@@ -71,17 +71,17 @@ class SaveHKLCW(PythonAlgorithm):
             if directionCosines:
                 U = peak_ws.sample().getOrientedLattice().getU()
                 sample_pos = peak_ws.getInstrument().getSample().getPos()
-                q_reverse_incident = peak_ws.getInstrument().getSource().getPos() - sample_pos
-                q_reverse_incident = np.array(q_reverse_incident) / q_reverse_incident.norm()
+                source_pos = peak_ws.getInstrument().getSource().getPos()
+                ki_n = (sample_pos - source_pos).norm()  # direction of incident wavevector
 
             for p in peak_ws:
                 if directionCosines:
                     R = p.getGoniometerMatrix()
                     RU = np.dot(R, U)
-                    q_diffracted = p.getDetPos() - sample_pos
-                    q_diffracted = np.array(q_diffracted) / q_diffracted.norm()
-                    dir_cos_1 = np.dot(RU.T, q_reverse_incident)
-                    dir_cos_2 = np.dot(RU.T, q_diffracted)
+                    ki = ki_n * (2 * np.pi / p.getWavelength())
+                    kf_n = (ki + p.getQLabFrame()).norm()  # direction of scattered wavevector
+                    dir_cos_1 = np.dot(RU.T, -ki_n)  # notice ki direction is reversed
+                    dir_cos_2 = np.dot(RU.T, kf_n)
                     f.write(
                         "{:4.0f}{:4.0f}{:4.0f}{:8.2f}{:8.2f}{:4d}{:8.5f}{:8.5f}{:8.5f}{:8.5f}{:8.5f}{:8.5f}\n"
                         .format(p.getH(), p.getK(), p.getL(), p.getIntensity(),
diff --git a/Framework/PythonInterface/test/python/mantid/geometry/IPeakTest.py b/Framework/PythonInterface/test/python/mantid/geometry/IPeakTest.py
index 43b6f2d80092ea6a4a17bf5d06c1909ebc107f82..5cbba41e5414a5122b27843304a4329bdebbaee6 100644
--- a/Framework/PythonInterface/test/python/mantid/geometry/IPeakTest.py
+++ b/Framework/PythonInterface/test/python/mantid/geometry/IPeakTest.py
@@ -152,10 +152,6 @@ class IPeakTest(unittest.TestCase):
         self.assertEqual(self._peak.getRow(), row)
         self.assertEqual(self._peak.getCol(), col)
 
-    def test_get_det_pos(self):
-        expected_det_pos = np.array([0.05962, -0.09450, -0.23786])
-        npt.assert_allclose(self._peak.getDetPos(), expected_det_pos, atol=1e-5)
-
     def test_get_l1(self):
         expected_l1 = 8.3
         self.assertEqual(self._peak.getL1(), expected_l1)
diff --git a/qt/widgets/instrumentview/src/PeakOverlay.cpp b/qt/widgets/instrumentview/src/PeakOverlay.cpp
index aa10501faed032efdeb3237eae78c97f40e176cc..29f93f4efa0d1a61fabd500620e384532fd800aa 100644
--- a/qt/widgets/instrumentview/src/PeakOverlay.cpp
+++ b/qt/widgets/instrumentview/src/PeakOverlay.cpp
@@ -7,6 +7,7 @@
 #include "MantidQtWidgets/InstrumentView/PeakOverlay.h"
 #include "MantidAPI/AlgorithmManager.h"
 #include "MantidAPI/IPeaksWorkspace.h"
+#include "MantidDataObjects/Peak.h"
 #include "MantidQtWidgets/InstrumentView/UnwrappedSurface.h"
 
 #include <QList>
@@ -15,6 +16,10 @@
 #include <cmath>
 #include <stdexcept>
 
+namespace {
+Mantid::Kernel::Logger g_log("PeakOverlay");
+}
+
 namespace MantidQt {
 namespace MantidWidgets {
 
@@ -243,7 +248,15 @@ void PeakOverlay::createMarkers(const PeakMarker2D::Style &style) {
   this->clear();
   for (int i = 0; i < nPeaks; ++i) {
     Mantid::Geometry::IPeak &peak = getPeak(i);
-    const Mantid::Kernel::V3D &pos = peak.getDetPos();
+    Mantid::Kernel::V3D pos;
+    try {
+      auto peakFull = dynamic_cast<Mantid::DataObjects::Peak &>(peak);
+      pos = peakFull.getDetPos();
+    }
+    catch(std::bad_cast) {
+      g_log.error("Cannot create markers for this type of peak");
+      return;
+    }
     // Project the peak (detector) position onto u,v coords
     double u, v, uscale, vscale;
     m_surface->project(pos, u, v, uscale, vscale);