#pragma once
#include <SparAIModule.h>
#ifdef USE_SPAR_GUI
  #include <SparQtGui.h>
#endif

class SparAIFactory
{
public:
  /**
   * @brief Instantiates the SPAR AI module instance and attaches the GUI to it if necessary.
   * @tparam S1 Type of sensing layer 1.
   * @tparam S2 Type of sensing layer 2.
   * @tparam S3 Type of sensing layer 3.
   * @tparam S4 Type of sensing layer4.
   * @tparam S1 Type of decision making layer 1.
   * @tparam S2 Type of decision making layer 2.
   * @tparam S3 Type of decision making layer 3.
   * @tparam S4 Type of decision making layer 4.
   * @param parent The parent process of SPAR, possibly NULL.
   * @return The SPAR instance.
   */
  template <class S1, class S2, class S3, class S4, class D1, class D2, class D3, class D4>
  SparAIModule<S1, S2, S3, S4, D1, D2, D3, D4>* instantiate(Process* parent)
  {
    SparAIModule<S1, S2, S3, S4, D1, D2, D3, D4>* spar = new SparAIModule<S1, S2, S3, S4, D1, D2, D3, D4>(parent);
  #ifdef USE_SPAR_GUI
    SparQtGUI<S1, S2, S3, S4, D1, D2, D3, D4>* gui = new SparQtGUI<S1, S2, S3, S4, D1, D2, D3, D4>(spar);
    gui->zombifyOnTerminate();
    gui->start();
  #endif
    return spar;
  }
};
