/******************************************************************************
** Copyright (c) 2023 MAK Technologies, Inc.
** All rights reserved.
******************************************************************************/
//! \file DtElementDefinitionRecord.h
//! \ingroup makArchives

#pragma once

#include <makArchives/makArchives.h>
#include <makArchives/DtSerialize.h>
#include <makArchives/UnicodeStringRecord.h>
#include <makArchives/DtVisualizerDefinitionRecord.h>

#define MODEL_SET_3D (0)
#define MODEL_SET_XR (1)
#define MODEL_SET_2D (5)

namespace makArchives
{
   //! \brief Record for a visualization definition
   //! \ingroup makArchives
   class DT_DLL_MAKARCHIVES DtVisualizerDefinitionSetRecords
   {
   public:
      typedef std::vector<DtVisualizerDefinitionRecord> VisualizerDefinitionSet;

      DtVisualizerDefinitionSetRecords()
         : myModelSet(0)
         , myVisualizerDefinitions()
      {

      }

      DtVisualizerDefinitionSetRecords(int modelSet)
         : myModelSet(modelSet)
         , myVisualizerDefinitions()
      {

      }

      VisualizerDefinitionSet& visualizerDefinitions()
      {
         return myVisualizerDefinitions;
      }

      const VisualizerDefinitionSet& visualizerDefinitions() const
      {
         return myVisualizerDefinitions;
      }

      unsigned int numVisualizerDefinitions() const
      {
         return myVisualizerDefinitions.size();
      }

      bool isEmpty() const
      {
         return myVisualizerDefinitions.empty();
      }

      int modelSet() const
      {
         return myModelSet;
      }

      void setModelSet(int set)
      {
         myModelSet = set;
      }

   protected:
      friend class boost::serialization::access;

      template<class Archive>
      void serialize(Archive & ar, const unsigned int version)
      {
         ar & BOOST_SERIALIZATION_NVP(myModelSet);
         ar & BOOST_SERIALIZATION_NVP(myVisualizerDefinitions);
      }

   protected:
      int myModelSet;
      VisualizerDefinitionSet myVisualizerDefinitions;

   };

   //! \brief Record for an element definition (new type)
   //! \ingroup makArchives
   class DT_DLL_MAKARCHIVES DtElementDefinitionRecord
   {
   public:
      //! CTOR
      DtElementDefinitionRecord();

      //! Set the definition's name
      //! Name must be unique
      void setName(const Utf8String& name);

      //! Set the definition's file location
      void setFileName(const Utf8String& fileName);

      //! Set the name of the definition's parent
      //! Set to "" to specify no parent (meaning a root definition)
      void setParentName(const Utf8String& parentName);

      //! Set if this element go in the .hier file?
      void setIsHier(bool isHier);

      DtVisualizerDefinitionSetRecords& visualizerDefinitions3D()
      {
         return myModelSet3D;
      }

      const DtVisualizerDefinitionSetRecords& visualizerDefinitions3D() const
      {
         return myModelSet3D;
      }

      DtVisualizerDefinitionSetRecords& visualizerDefinitionsXR()
      {
         return myModelSetXR;
      }

      const DtVisualizerDefinitionSetRecords& visualizerDefinitionsXR() const
      {
         return myModelSetXR;
      }

      DtVisualizerDefinitionSetRecords& visualizerDefinitions2D()
      {
         return myModelSet2D;
      }

      const DtVisualizerDefinitionSetRecords& visualizerDefinitions2D() const
      {
         return myModelSet2D;
      }

      //! definition name accessor
      const Utf8String& name() const;




      //! definition parent name accessor
      //! a value of "" indicates no parent
      const Utf8String& parentName() const;

      //! Should this element go in the .hier file?
      bool isHier(void) const;

      //! Not serialized
      const Utf8String& fileName() const;
   protected:
      friend class boost::serialization::access;

      template<class Archive>
      void serialize(Archive & ar, const unsigned int version)
      {
         //! myIsHier and fileName are not serialized

         ar & BOOST_SERIALIZATION_NVP(myName);
         ar & BOOST_SERIALIZATION_NVP(myParentName);
         if ( version == 1)
         {
            ar & BOOST_SERIALIZATION_NVP(myVisualizerDefinitionSets);

            // Migrate version 1 -> 2
            myModelSet3D.visualizerDefinitions() = myVisualizerDefinitionSets[MODEL_SET_3D];
            myModelSetXR.visualizerDefinitions() = myVisualizerDefinitionSets[MODEL_SET_XR];
            myModelSet2D.visualizerDefinitions() = myVisualizerDefinitionSets[MODEL_SET_2D];
         }

         if (version >= 2)
         {
            ar & BOOST_SERIALIZATION_NVP(myModelSet3D);
            ar & BOOST_SERIALIZATION_NVP(myModelSetXR);
            ar & BOOST_SERIALIZATION_NVP(myModelSet2D);
         }
         
      }

      Utf8String myName;
      Utf8String myParentName;
      Utf8String myFileName;

      // Not serialized, calculated at load
      // Should this element go into the .hier file?
      bool myIsHier;

      DtVisualizerDefinitionSetRecords myModelSet3D;
      DtVisualizerDefinitionSetRecords myModelSetXR;
      DtVisualizerDefinitionSetRecords myModelSet2D;

      // Deprecated
      std::vector< std::vector< DtVisualizerDefinitionRecord > > myVisualizerDefinitionSets;
   };
}

BOOST_CLASS_VERSION(makArchives::DtVisualizerDefinitionSetRecords, 1)
BOOST_CLASS_VERSION(makArchives::DtElementDefinitionRecord, 2)
