diff --git a/include/core/sensor/sensor_base.h b/include/core/sensor/sensor_base.h
index ec85b16148970e54351b3d56137636101f900072..faf359f727df4058543204a9a2e29d661e4ca96d 100644
--- a/include/core/sensor/sensor_base.h
+++ b/include/core/sensor/sensor_base.h
@@ -128,7 +128,7 @@ class SensorBase : public NodeBase, public HasStateBlocks, public std::enable_sh
         CaptureBasePtr last_capture_; // last capture of the sensor (in the WOLF tree)
 
     protected:
-        Eigen::VectorXd noise_std_; // std of sensor noise
+        //Eigen::VectorXd noise_std_; // std of sensor noise
         Eigen::MatrixXd noise_cov_; // cov matrix of noise
 
         void setProblem(ProblemPtr _problem) override final;
@@ -146,6 +146,7 @@ class SensorBase : public NodeBase, public HasStateBlocks, public std::enable_sh
          *
          **/
         SensorBase(const std::string& _type,
+                   const std::string& _unique_name,
                    const SizeEigen& _dim,
                    const Priors& _priors,
                    ParamsSensorBasePtr _params);
@@ -159,8 +160,8 @@ class SensorBase : public NodeBase, public HasStateBlocks, public std::enable_sh
          *
          **/
         SensorBase(const std::string& _type,
-                   const SizeEigen& _dim,
                    const std::string& _unique_name,
+                   const SizeEigen& _dim,
                    const ParamsServer& _server,
                    std::string _keys);
 
diff --git a/include/core/state_block/has_state_blocks.h b/include/core/state_block/has_state_blocks.h
index ac82297f5e36b5130151bd1b0464a110264b5fe7..7483ef45e2d3cd122ff094d072c9a359a34d8f8c 100644
--- a/include/core/state_block/has_state_blocks.h
+++ b/include/core/state_block/has_state_blocks.h
@@ -76,13 +76,8 @@ class HasStateBlocks
         std::unordered_map<char, StateBlockConstPtr>::const_iterator find(const StateBlockConstPtr& _sb) const;
         std::unordered_map<char, StateBlockPtr>::const_iterator find(const StateBlockPtr& _sb);
 
-        // Emplace derived state blocks (angle, quaternion, etc).
-        template<typename SB, typename ... Args>
-        std::shared_ptr<SB> emplaceStateBlock(const char& _sb_type, ProblemPtr _problem, Args&&... _args_of_derived_state_block_constructor);
-
         // Emplace base state blocks.
-        template<typename ... Args>
-        StateBlockPtr emplaceStateBlock(const char& _sb_type, ProblemPtr _problem, Args&&... _args_of_base_state_block_constructor);
+        StateBlockPtr emplaceStateBlock(const char& _sb_type, ProblemPtr _problem, const Eigen::VectorXd& _state, bool _fixed);
 
         // Register/remove state blocks to/from wolf::Problem
         virtual void registerNewStateBlocks(ProblemPtr _problem);
@@ -171,28 +166,6 @@ inline unsigned int HasStateBlocks::removeStateBlock(const char& _sb_type)
     return state_block_const_map_.erase(_sb_type);
 }
 
-template<typename SB, typename ... Args>
-inline std::shared_ptr<SB> HasStateBlocks::emplaceStateBlock(const char& _sb_type, ProblemPtr _problem, Args&&... _args_of_derived_state_block_constructor)
-{
-    assert(state_block_map_.count(_sb_type) == 0 && state_block_const_map_.count(_sb_type) == 0 && "Trying to add a state block with an existing type! Use setStateBlock instead.");
-    std::shared_ptr<SB> sb = std::make_shared<SB>(std::forward<Args>(_args_of_derived_state_block_constructor)...);
-
-    addStateBlock(_sb_type, sb, _problem);
-
-    return sb;
-}
-
-template<typename ... Args>
-inline StateBlockPtr HasStateBlocks::emplaceStateBlock(const char& _sb_type, ProblemPtr _problem, Args&&... _args_of_base_state_block_constructor)
-{
-    assert(state_block_map_.count(_sb_type) == 0 && state_block_const_map_.count(_sb_type) == 0 && "Trying to add a state block with an existing type! Use setStateBlock instead.");
-    auto sb = std::make_shared<StateBlock>(std::forward<Args>(_args_of_base_state_block_constructor)...);
-
-    addStateBlock(_sb_type, sb, _problem);
-
-    return sb;
-}
-
 inline bool HasStateBlocks::setStateBlock(const char _sb_type, const StateBlockPtr& _sb)
 {
     assert (structure_.find(_sb_type) > 0 && "Cannot set a state block out of the state structure! Use addStateBlock instead.");
diff --git a/include/core/state_block/prior.h b/include/core/state_block/prior.h
index 3ee8835f0c8309dd9ce56c7136ffad06412b7ac1..b246ed47a1f99187ee27615269bbc7f681cadb97 100644
--- a/include/core/state_block/prior.h
+++ b/include/core/state_block/prior.h
@@ -42,36 +42,14 @@ class Prior
 
   public:
     Prior() = default;
-    Prior(const std::string& _prefix, char _key, const ParamsServer& _server)
-    {
-      mode   = _server.getParam<double>(_prefix + _key + "/mode");
-
-      if (mode != "nothing" and mode != "initial_guess" and mode != "fix" and mode == "factor") 
-        throw std::runtime_error("wrong mode value, it should be: 'nothing', 'initial_guess', 'fix' or 'factor'");
-
-      if ( mode == "nothing" and (key == 'P' or key == 'O'))
-        throw std::runtime_error("For P and O keys, mode 'nothing' is not valid");
+    Prior(char _key, 
+          const std::string& _mode,  
+          const Eigen::VectorXd& _state, 
+          const Eigen::VectorXd& _sigma, 
+          bool _dynamic, 
+          const Eigen::VectorXd& _sigma_drift);
 
-      if (mode != "nothing")
-        state = _server.getParam<Eigen::VectorXd>(_prefix + _key + "/state");
-      else
-        state = Eigen::VectorXd(0);
-
-      if (mode == "factor")
-        sigma = _server.getParam<Eigen::VectorXd>(_prefix + _key + "/sigma");
-      else
-        sigma = Eigen::VectorXd(0);
-
-      if ( key == 'P' or key == 'O')
-        dynamic = false;
-      else
-        dynamic = _server.getParam<bool>(_prefix + _key + "/dynamic");
-
-      if (dynamic)
-        sigma_drift = _server.getParam<Eigen::VectorXd>(_prefix + _key + "/sigma_drift");
-      else
-        sigma_drift = Eigen::VectorXd(0);
-    }
+    Prior(const std::string& _prefix, char _key, const ParamsServer& _server);
 
     virtual ~Prior() = default;
 
@@ -120,9 +98,21 @@ class Prior
       return sigma_drift;
     }
 
+    void check() const
+    {
+      if (mode != "nothing" and mode != "initial_guess" and mode != "fix" and mode == "factor") 
+        throw std::runtime_error("wrong mode value, it should be: 'nothing', 'initial_guess', 'fix' or 'factor'");
+
+      if ( mode == "nothing" and (key == 'P' or key == 'O'))
+        throw std::runtime_error("For P and O keys, mode 'nothing' is not valid");
+
+      if (dynamic and (key == 'P' or key == 'O') )
+        throw std::runtime_error("Dynamic state blocks not implemented for extrinsics");
+    }
+
     virtual std::string print() const final
     {
-      return "Prior "       + _key + "\n"
+      return "Prior " + key + "\n"
           + "mode: " + std::to_string(mode)  + "\n"
           + "state: "      + std::to_string(state)       + "\n"
           + (mode == "factor" ? "sigma: "      + std::to_string(sigma)       + "\n" : "")
@@ -131,5 +121,45 @@ class Prior
     }
 };
 
+inline Prior::Prior(char _key, 
+                    const std::string& _mode,  
+                    const Eigen::VectorXd& _state, 
+                    const Eigen::VectorXd& _sigma, 
+                    bool _dynamic, 
+                    const Eigen::VectorXd& _sigma_drift) : 
+  key(_key),
+  mode(_mode),
+  state(_state),
+  sigma(_sigma),
+  dynamic(_dynamic),
+  sigma_drift(_sigma_drift)
+{
+  check();
+}
+
+inline Prior::Prior(const std::string& _prefix, char _key, const ParamsServer& _server)
+{
+  mode   = _server.getParam<double>(_prefix + _key + "/mode");
+
+  if (mode != "nothing")
+    state = _server.getParam<Eigen::VectorXd>(_prefix + _key + "/state");
+  else
+    state = Eigen::VectorXd(0);
+
+  if (mode == "factor")
+    sigma = _server.getParam<Eigen::VectorXd>(_prefix + _key + "/sigma");
+  else
+    sigma = Eigen::VectorXd(0);
+
+  dynamic = _server.getParam<bool>(_prefix + _key + "/dynamic");
+
+  if (dynamic)
+    sigma_drift = _server.getParam<Eigen::VectorXd>(_prefix + _key + "/sigma_drift");
+  else
+    sigma_drift = Eigen::VectorXd(0);
+
+  check();
+}
+
 }
 #endif
diff --git a/src/sensor/sensor_base.cpp b/src/sensor/sensor_base.cpp
index c195c3fcab2eaadde379655355ea4a59382ac0ee..954af1f0de9042172c4e46802004adb7ef6bca8e 100644
--- a/src/sensor/sensor_base.cpp
+++ b/src/sensor/sensor_base.cpp
@@ -22,6 +22,7 @@
 #include "core/sensor/sensor_base.h"
 #include "core/utils/params_server.h"
 #include "core/state_block/prior.h"
+#include "core/state_block/factory_state_block.h"
 #include "core/state_block/state_block.h"
 #include "core/state_block/state_quaternion.h"
 #include "core/factor/factor_block_absolute.h"
@@ -32,10 +33,11 @@ namespace wolf {
 unsigned int SensorBase::sensor_id_count_ = 0;
 
 SensorBase::SensorBase(const std::string& _type,
+                       const std::string& _unique_name,
                        const SizeEigen& _dim,
                        const Priors& _priors,
                        ParamsSensorBasePtr _params) :
-        NodeBase("SENSOR", _type),
+        NodeBase("SENSOR", _type, _unique_name),
         HasStateBlocks(""),
         hardware_ptr_(),
         sensor_id_(++sensor_id_count_), // simple ID factory
@@ -53,11 +55,11 @@ SensorBase::SensorBase(const std::string& _type,
 }
 
 SensorBase::SensorBase(const std::string& _type,
-                       const SizeEigen& _dim,
                        const std::string& _unique_name,
+                       const SizeEigen& _dim,
                        const ParamsServer& _server,
                        std::string _keys) :
-        NodeBase("SENSOR", _type),
+        NodeBase("SENSOR", _type, _unique_name),
         HasStateBlocks(""),
         hardware_ptr_(),
         sensor_id_(++sensor_id_count_), // simple ID factory
@@ -93,6 +95,8 @@ void SensorBase::loadParams(ParamsSensorBasePtr _params)
 
 void SensorBase::loadPriors(Priors _priors, SizeEigen _dim)
 {
+    assert(_dim == 2 or _dim == 3);
+
     for (auto&& prior_pair : _priors)
     {
         const Prior& prior = prior_pair.second;
@@ -104,11 +108,7 @@ void SensorBase::loadPriors(Priors _priors, SizeEigen _dim)
             throw std::runtime_error("Prior state for O has wrong size");
 
         // create state block
-        StateBlockPtr sb;
-        if (prior.getKey() == 'O' and prior.getState().size() == 4)
-            sb = std::make_shared<StateQuaternion>(prior.getState(), prior.isFixed());
-        else
-            sb = std::make_shared<StateBlock>(prior.getState(), prior.isFixed());
+        auto sb = FactoryStateBlock::create(std::string(1, prior.getKey()), prior.getState(), prior.isFixed());
 
         // Add state block
         addStateBlock(prior.getKey(), sb, prior.isDynamic());
@@ -116,7 +116,6 @@ void SensorBase::loadPriors(Priors _priors, SizeEigen _dim)
         // Factor
         if (prior.isFactor())
             addPriorParameter(prior.getKey(), prior.getState(), prior.getSigma());
-
     }
 }
 
diff --git a/src/state_block/has_state_blocks.cpp b/src/state_block/has_state_blocks.cpp
index 047469dc899a8973b7bdf07df318b2079c155ef9..181188658a4776bf657ba7acb6c86f88775c92e4 100644
--- a/src/state_block/has_state_blocks.cpp
+++ b/src/state_block/has_state_blocks.cpp
@@ -21,10 +21,25 @@
 //--------LICENSE_END--------
 
 #include "core/state_block/has_state_blocks.h"
+#include "core/state_block/factory_state_block.h"
 
 namespace wolf
 {
 
+StateBlockPtr HasStateBlocks::emplaceStateBlock(const char& _sb_type, 
+                                                ProblemPtr _problem, 
+                                                const Eigen::VectorXd& _state, 
+                                                bool _fixed)
+{
+    assert(state_block_map_.count(_sb_type) == 0 && state_block_const_map_.count(_sb_type) == 0 && "Trying to add a state block with an existing type! Use setStateBlock instead.");
+    
+    auto sb = FactoryStateBlock::create(std::string(1,_sb_type), _state, _fixed);
+
+    addStateBlock(_sb_type, sb, _problem);
+
+    return sb;
+}
+
 StateBlockPtr HasStateBlocks::addStateBlock(const char& _sb_type, const StateBlockPtr& _sb, ProblemPtr _problem)
 {
     assert(state_block_map_.count(_sb_type) == 0 && state_block_const_map_.count(_sb_type) == 0 && "Trying to add a state block with an existing type! Use setStateBlock instead.");
diff --git a/src/state_block/state_block.cpp b/src/state_block/state_block.cpp
index 513d6d4627627a029e3ebe61bab550497d369634..f3ade24eb4156d07ae445895dfe8c5af90419e6e 100644
--- a/src/state_block/state_block.cpp
+++ b/src/state_block/state_block.cpp
@@ -87,7 +87,7 @@ StateBlockPtr create_orientation(const Eigen::VectorXd& _state, bool _fixed)
     if (_state.size() == 4)
         return StateQuaternion::create(_state, _fixed);
 
-    throw std::length_error("Wrong vector size for orientation. Must be 4 for a quaternion in 3D, or 1 for an angle in 2D.");
+    throw std::runtime_error("Wrong vector size for orientation. Must be 4 for a quaternion in 3D, or 1 for an angle in 2D.");
 
     return nullptr;
 }