QxFactory.h 7.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163
  1. /****************************************************************************
  2. **
  3. ** https://www.qxorm.com/
  4. ** Copyright (C) 2013 Lionel Marty (contact@qxorm.com)
  5. **
  6. ** This file is part of the QxOrm library
  7. **
  8. ** This software is provided 'as-is', without any express or implied
  9. ** warranty. In no event will the authors be held liable for any
  10. ** damages arising from the use of this software
  11. **
  12. ** Commercial Usage
  13. ** Licensees holding valid commercial QxOrm licenses may use this file in
  14. ** accordance with the commercial license agreement provided with the
  15. ** Software or, alternatively, in accordance with the terms contained in
  16. ** a written agreement between you and Lionel Marty
  17. **
  18. ** GNU General Public License Usage
  19. ** Alternatively, this file may be used under the terms of the GNU
  20. ** General Public License version 3.0 as published by the Free Software
  21. ** Foundation and appearing in the file 'license.gpl3.txt' included in the
  22. ** packaging of this file. Please review the following information to
  23. ** ensure the GNU General Public License version 3.0 requirements will be
  24. ** met : http://www.gnu.org/copyleft/gpl.html
  25. **
  26. ** If you are unsure which license is appropriate for your use, or
  27. ** if you have questions regarding the use of this file, please contact :
  28. ** contact@qxorm.com
  29. **
  30. ****************************************************************************/
  31. #ifndef _QX_FACTORY_H_
  32. #define _QX_FACTORY_H_
  33. #ifdef _MSC_VER
  34. #pragma once
  35. #endif
  36. /*!
  37. * \file QxFactory.h
  38. * \author Lionel Marty
  39. * \ingroup QxFactory
  40. * \brief Concrete factory class to create object dynamically using the class name
  41. */
  42. #include <QtCore/qobject.h>
  43. #include <QxFactory/IxFactory.h>
  44. #include <QxTraits/get_base_class.h>
  45. #include <QxTraits/get_class_name.h>
  46. #include <QxTraits/get_primary_key.h>
  47. #define QX_STR_CANNOT_INSTANTIATE_ABSTRACT_CLASS "[QxOrm] qx::QxFactory<T> ---> cannot instantiate abstract class '%s'"
  48. #if _QX_AUTO_REGISTER_REPOSITORY
  49. #define QX_AUTO_REGISTER_REPOSITORY(className, sKey) qx::register_repository< className >(sKey);
  50. #else // _QX_AUTO_REGISTER_REPOSITORY
  51. #define QX_AUTO_REGISTER_REPOSITORY(className, sKey) /* Nothing */
  52. #endif // _QX_AUTO_REGISTER_REPOSITORY
  53. namespace qx {
  54. class IxPersistable;
  55. template <class T> class QxClass;
  56. #ifdef _QX_ENABLE_QT_NETWORK
  57. namespace service {
  58. class IxService;
  59. class IxParameter;
  60. } // namespace service
  61. #endif // _QX_ENABLE_QT_NETWORK
  62. #if _QX_AUTO_REGISTER_REPOSITORY
  63. template <class T>
  64. inline void register_repository(const QString & sKey);
  65. #endif // _QX_AUTO_REGISTER_REPOSITORY
  66. /*!
  67. * \ingroup QxFactory
  68. * \brief qx::QxFactory<T> : concrete factory class to create object of type T dynamically using the class name
  69. */
  70. template <class T>
  71. class QxFactory : public IxFactory
  72. {
  73. public:
  74. QxFactory(const QString & sKey) : IxFactory(sKey) { QX_AUTO_REGISTER_REPOSITORY(T, sKey); }
  75. virtual ~QxFactory() { ; }
  76. #ifdef _QX_ENABLE_QT_NETWORK
  77. virtual qx::any createObject(bool bRawPointer = false) const
  78. { QxClass<T>::getSingleton(); return qxCreateInstance<std::is_abstract<T>::value, std::is_base_of<qx::IxPersistable, T>::value, std::is_base_of<qx::service::IxService, T>::value, std::is_base_of<qx::service::IxParameter, T>::value, std::is_base_of<QObject, T>::value, 0>::create(bRawPointer); }
  79. virtual void * createObjectNudePtr() const
  80. { QxClass<T>::getSingleton(); return qxCreateInstance<std::is_abstract<T>::value, std::is_base_of<qx::IxPersistable, T>::value, std::is_base_of<qx::service::IxService, T>::value, std::is_base_of<qx::service::IxParameter, T>::value, std::is_base_of<QObject, T>::value, 0>::createNudePtr(); }
  81. #else // _QX_ENABLE_QT_NETWORK
  82. virtual qx::any createObject(bool bRawPointer = false) const
  83. { QxClass<T>::getSingleton(); return qxCreateInstance<std::is_abstract<T>::value, std::is_base_of<qx::IxPersistable, T>::value, false, false, std::is_base_of<QObject, T>::value, 0>::create(bRawPointer); }
  84. virtual void * createObjectNudePtr() const
  85. { QxClass<T>::getSingleton(); return qxCreateInstance<std::is_abstract<T>::value, std::is_base_of<qx::IxPersistable, T>::value, false, false, std::is_base_of<QObject, T>::value, 0>::createNudePtr(); }
  86. #endif // _QX_ENABLE_QT_NETWORK
  87. #ifndef _QX_NO_RTTI
  88. virtual const std::type_info & typeInfo() const
  89. { return typeid(T); }
  90. #endif // _QX_NO_RTTI
  91. private:
  92. template <bool bIsAbstract /* = false */, bool bIsIxPersistable /* = false */, bool bIsIxService /* = false */, bool bIsIxParameter /* = false */, bool bIsQObject /* = false */, int dummy>
  93. struct qxCreateInstance
  94. {
  95. static inline qx::any create(bool bRawPointer) { if (bRawPointer) { T * p = new T(); return qx::any(p); }; std::shared_ptr<T> ptr = std::make_shared<T>(); return qx::any(ptr); }
  96. static inline void * createNudePtr() { return static_cast<void *>(new T()); }
  97. };
  98. template <bool bIsIxPersistable, bool bIsIxService, bool bIsIxParameter, bool bIsQObject, int dummy>
  99. struct qxCreateInstance<true, bIsIxPersistable, bIsIxService, bIsIxParameter, bIsQObject, dummy>
  100. {
  101. static inline qx::any create(bool bRawPointer) { Q_UNUSED(bRawPointer); qDebug(QX_STR_CANNOT_INSTANTIATE_ABSTRACT_CLASS, qx::trait::get_class_name<T>::get()); return qx::any(); }
  102. static inline void * createNudePtr() { qDebug(QX_STR_CANNOT_INSTANTIATE_ABSTRACT_CLASS, qx::trait::get_class_name<T>::get()); return NULL; }
  103. };
  104. template <bool bIsQObject, int dummy>
  105. struct qxCreateInstance<false, true, false, false, bIsQObject, dummy>
  106. {
  107. static inline qx::any create(bool bRawPointer) { if (bRawPointer) { T * p = new T(); return qx::any(p); }; std::shared_ptr<T> ptr = std::make_shared<T>(); return qx::any(ptr); }
  108. static inline void * createNudePtr() { return static_cast<qx::IxPersistable *>(new T()); }
  109. };
  110. #ifdef _QX_ENABLE_QT_NETWORK
  111. template <bool bIsQObject, int dummy>
  112. struct qxCreateInstance<false, false, true, false, bIsQObject, dummy>
  113. {
  114. static inline qx::any create(bool bRawPointer) { if (bRawPointer) { T * p = new T(); return qx::any(p); }; std::shared_ptr<T> ptr = std::make_shared<T>(); return qx::any(ptr); }
  115. static inline void * createNudePtr() { return static_cast<qx::service::IxService *>(new T()); }
  116. };
  117. template <bool bIsQObject, int dummy>
  118. struct qxCreateInstance<false, false, false, true, bIsQObject, dummy>
  119. {
  120. static inline qx::any create(bool bRawPointer) { if (bRawPointer) { T * p = new T(); return qx::any(p); }; std::shared_ptr<T> ptr = std::make_shared<T>(); return qx::any(ptr); }
  121. static inline void * createNudePtr() { return static_cast<qx::service::IxParameter *>(new T()); }
  122. };
  123. #endif // _QX_ENABLE_QT_NETWORK
  124. template <int dummy>
  125. struct qxCreateInstance<false, false, false, false, true, dummy>
  126. {
  127. static inline qx::any create(bool bRawPointer) { if (bRawPointer) { T * p = new T(); return qx::any(p); }; std::shared_ptr<T> ptr = std::make_shared<T>(); return qx::any(ptr); }
  128. static inline void * createNudePtr() { return static_cast<QObject *>(new T()); }
  129. };
  130. };
  131. } // namespace qx
  132. #include "../../inl/QxFactory/QxFactory.inl"
  133. #endif // _QX_FACTORY_H_