#pragma once

#include <frostbite2D/base/RefObject.h>
#include <frostbite2D/core/RefBasePtr.hpp>

namespace frostbite2D {

struct DefaultRefPtrPolicy {
  void Retain(RefObject* ptr) {
    if (ptr) {
      ptr->Retain();
    }
  }

  void Release(RefObject* ptr) {
    if (ptr) {
      ptr->Release();
    }
  }
};

template <typename T>
using RefPtr = RefBasePtr<T, DefaultRefPtrPolicy>;

template <typename T, typename... Args>
RefPtr<T> MakePtr(Args&&... args) {
  static_assert(std::is_base_of<RefObject, T>::value, 
                "T must be derived from RefObject");
  return RefPtr<T>(new T(std::forward<Args>(args)...));
}

template <typename T>
RefPtr<T> MakePtr(T* ptr) {
  static_assert(std::is_base_of<RefObject, T>::value, 
                "T must be derived from RefObject");
  return RefPtr<T>(ptr);
}

}
