Compare commits
2 Commits
174385e40f
...
79772c4b49
| Author | SHA1 | Date |
|---|---|---|
|
|
79772c4b49 | |
|
|
3962de715f |
|
|
@ -131,7 +131,7 @@ public:
|
|||
* @brief 进入场景
|
||||
* @param scene 场景指针
|
||||
*/
|
||||
void enterScene(Ptr<class Scene> scene);
|
||||
void enterScene(SharedPtr<class Scene> scene);
|
||||
|
||||
/**
|
||||
* @brief 获取帧间隔时间
|
||||
|
|
|
|||
|
|
@ -0,0 +1,675 @@
|
|||
#pragma once
|
||||
|
||||
#include <extra2d/core/types.h>
|
||||
|
||||
#include <atomic>
|
||||
#include <condition_variable>
|
||||
#include <deque>
|
||||
#include <functional>
|
||||
#include <memory>
|
||||
#include <mutex>
|
||||
#include <type_traits>
|
||||
#include <unordered_map>
|
||||
#include <vector>
|
||||
|
||||
namespace extra2d {
|
||||
|
||||
// ============================================================================
|
||||
// IPoolable - 可池化对象接口
|
||||
// 实现此接口的对象在归还对象池时会自动调用 reset() 方法
|
||||
// ============================================================================
|
||||
class IPoolable {
|
||||
public:
|
||||
/**
|
||||
* @brief 虚析构函数
|
||||
*/
|
||||
virtual ~IPoolable() = default;
|
||||
|
||||
/**
|
||||
* @brief 重置对象状态
|
||||
* 当对象归还到对象池时自动调用,用于清理对象状态以便复用
|
||||
*/
|
||||
virtual void reset() = 0;
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// is_poolable_v - 类型特征,检测类型是否实现 IPoolable 接口
|
||||
// ============================================================================
|
||||
template <typename T>
|
||||
struct is_poolable : std::is_base_of<IPoolable, T> {};
|
||||
|
||||
template <typename T>
|
||||
inline constexpr bool is_poolable_v = is_poolable<T>::value;
|
||||
|
||||
// ============================================================================
|
||||
// ObjectPoolStats - 对象池统计信息
|
||||
// ============================================================================
|
||||
struct ObjectPoolStats {
|
||||
size_t totalCapacity = 0; // 总容量(已分配对象数)
|
||||
size_t activeCount = 0; // 活跃对象数(正在使用)
|
||||
size_t freeCount = 0; // 空闲对象数(可用于分配)
|
||||
size_t peakUsage = 0; // 峰值使用量
|
||||
size_t totalAcquires = 0; // 总获取次数
|
||||
size_t totalReleases = 0; // 总归还次数
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// ControlBlock - PooledPtr 的控制块,管理引用计数
|
||||
// ============================================================================
|
||||
struct ControlBlock {
|
||||
std::atomic<int32> refCount{1}; // 引用计数
|
||||
void* pool = nullptr; // 所属对象池指针
|
||||
void* object = nullptr; // 对象指针
|
||||
|
||||
/**
|
||||
* @brief 增加引用计数
|
||||
* @return 增加后的引用计数
|
||||
*/
|
||||
int32 addRef() {
|
||||
return refCount.fetch_add(1, std::memory_order_relaxed) + 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 减少引用计数
|
||||
* @return 减少后的引用计数
|
||||
*/
|
||||
int32 release() {
|
||||
return refCount.fetch_sub(1, std::memory_order_acq_rel) - 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 获取当前引用计数
|
||||
* @return 当前引用计数
|
||||
*/
|
||||
int32 getRefCount() const {
|
||||
return refCount.load(std::memory_order_relaxed);
|
||||
}
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// ObjectPool<T> - 线程安全的通用对象池模板
|
||||
// ============================================================================
|
||||
template <typename T>
|
||||
class ObjectPool {
|
||||
public:
|
||||
// ========================================================================
|
||||
// 构造和析构
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 默认构造函数
|
||||
*/
|
||||
ObjectPool() = default;
|
||||
|
||||
/**
|
||||
* @brief 析构函数
|
||||
*/
|
||||
~ObjectPool() {
|
||||
clear();
|
||||
}
|
||||
|
||||
// 禁止拷贝
|
||||
ObjectPool(const ObjectPool&) = delete;
|
||||
ObjectPool& operator=(const ObjectPool&) = delete;
|
||||
|
||||
// 允许移动
|
||||
ObjectPool(ObjectPool&& other) noexcept {
|
||||
std::lock_guard<std::mutex> lock(other.mutex_);
|
||||
freeList_ = std::move(other.freeList_);
|
||||
allObjects_ = std::move(other.allObjects_);
|
||||
stats_ = other.stats_;
|
||||
other.stats_ = ObjectPoolStats{};
|
||||
}
|
||||
|
||||
ObjectPool& operator=(ObjectPool&& other) noexcept {
|
||||
if (this != &other) {
|
||||
std::scoped_lock lock(mutex_, other.mutex_);
|
||||
clearUnsafe();
|
||||
freeList_ = std::move(other.freeList_);
|
||||
allObjects_ = std::move(other.allObjects_);
|
||||
stats_ = other.stats_;
|
||||
other.stats_ = ObjectPoolStats{};
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 对象获取和归还
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 从对象池获取一个对象
|
||||
* 如果池中有空闲对象则复用,否则创建新对象
|
||||
* @param args 构造参数
|
||||
* @return 对象指针和控制块
|
||||
*/
|
||||
template <typename... Args>
|
||||
std::pair<T*, ControlBlock*> acquire(Args&&... args) {
|
||||
std::lock_guard<std::mutex> lock(mutex_);
|
||||
|
||||
T* obj = nullptr;
|
||||
ControlBlock* cb = nullptr;
|
||||
|
||||
if (!freeList_.empty()) {
|
||||
// 从空闲列表获取
|
||||
auto& front = freeList_.front();
|
||||
obj = front.first;
|
||||
cb = front.second;
|
||||
freeList_.pop_front();
|
||||
|
||||
// 重新构造对象(placement new)
|
||||
new (obj) T(std::forward<Args>(args)...);
|
||||
} else {
|
||||
// 创建新对象
|
||||
obj = new T(std::forward<Args>(args)...);
|
||||
cb = new ControlBlock();
|
||||
cb->pool = this;
|
||||
cb->object = obj;
|
||||
allObjects_.push_back({obj, cb});
|
||||
stats_.totalCapacity++;
|
||||
}
|
||||
|
||||
stats_.activeCount++;
|
||||
stats_.freeCount = freeList_.size();
|
||||
stats_.totalAcquires++;
|
||||
stats_.peakUsage = std::max(stats_.peakUsage, stats_.activeCount);
|
||||
|
||||
return {obj, cb};
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 归还对象到对象池
|
||||
* @param cb 控制块指针
|
||||
*/
|
||||
void release(ControlBlock* cb) {
|
||||
if (!cb) return;
|
||||
|
||||
T* obj = static_cast<T*>(cb->object);
|
||||
|
||||
std::lock_guard<std::mutex> lock(mutex_);
|
||||
|
||||
// 如果对象实现了 IPoolable,调用 reset()
|
||||
if constexpr (is_poolable_v<T>) {
|
||||
static_cast<IPoolable*>(obj)->reset();
|
||||
} else {
|
||||
// 显式调用析构函数
|
||||
obj->~T();
|
||||
}
|
||||
|
||||
// 重置控制块
|
||||
cb->refCount.store(1, std::memory_order_relaxed);
|
||||
|
||||
// 加入空闲列表
|
||||
freeList_.push_back({obj, cb});
|
||||
|
||||
stats_.activeCount--;
|
||||
stats_.freeCount = freeList_.size();
|
||||
stats_.totalReleases++;
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 预分配和内存管理
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 预分配指定数量的对象
|
||||
* @param count 预分配数量
|
||||
*/
|
||||
void preallocate(size_t count) {
|
||||
std::lock_guard<std::mutex> lock(mutex_);
|
||||
|
||||
for (size_t i = 0; i < count; ++i) {
|
||||
T* obj = new T();
|
||||
ControlBlock* cb = new ControlBlock();
|
||||
cb->pool = this;
|
||||
cb->object = obj;
|
||||
freeList_.push_back({obj, cb});
|
||||
allObjects_.push_back({obj, cb});
|
||||
}
|
||||
|
||||
stats_.totalCapacity += count;
|
||||
stats_.freeCount = freeList_.size();
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 清空所有对象
|
||||
*/
|
||||
void clear() {
|
||||
std::lock_guard<std::mutex> lock(mutex_);
|
||||
clearUnsafe();
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 收缩空闲列表,释放多余的空闲对象
|
||||
* @param keepCount 保留的空闲对象数量
|
||||
* @return 释放的对象数量
|
||||
*/
|
||||
size_t shrink(size_t keepCount = 0) {
|
||||
std::lock_guard<std::mutex> lock(mutex_);
|
||||
|
||||
size_t released = 0;
|
||||
while (freeList_.size() > keepCount) {
|
||||
auto& back = freeList_.back();
|
||||
T* obj = back.first;
|
||||
ControlBlock* cb = back.second;
|
||||
|
||||
// 从 allObjects_ 中移除
|
||||
allObjects_.erase(
|
||||
std::remove(allObjects_.begin(), allObjects_.end(), back),
|
||||
allObjects_.end());
|
||||
|
||||
delete obj;
|
||||
delete cb;
|
||||
freeList_.pop_back();
|
||||
released++;
|
||||
stats_.totalCapacity--;
|
||||
}
|
||||
|
||||
stats_.freeCount = freeList_.size();
|
||||
return released;
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 统计信息
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 获取统计信息
|
||||
* @return 统计信息结构
|
||||
*/
|
||||
ObjectPoolStats getStats() const {
|
||||
std::lock_guard<std::mutex> lock(mutex_);
|
||||
return stats_;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 获取当前活跃对象数
|
||||
* @return 活跃对象数
|
||||
*/
|
||||
size_t activeCount() const {
|
||||
std::lock_guard<std::mutex> lock(mutex_);
|
||||
return stats_.activeCount;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 获取当前空闲对象数
|
||||
* @return 空闲对象数
|
||||
*/
|
||||
size_t freeCount() const {
|
||||
std::lock_guard<std::mutex> lock(mutex_);
|
||||
return stats_.freeCount;
|
||||
}
|
||||
|
||||
private:
|
||||
/**
|
||||
* @brief 无锁清空(内部使用)
|
||||
*/
|
||||
void clearUnsafe() {
|
||||
for (auto& pair : allObjects_) {
|
||||
delete pair.first;
|
||||
delete pair.second;
|
||||
}
|
||||
allObjects_.clear();
|
||||
freeList_.clear();
|
||||
stats_ = ObjectPoolStats{};
|
||||
}
|
||||
|
||||
mutable std::mutex mutex_;
|
||||
std::deque<std::pair<T*, ControlBlock*>> freeList_; // 空闲列表
|
||||
std::vector<std::pair<T*, ControlBlock*>> allObjects_; // 所有对象(用于析构)
|
||||
mutable ObjectPoolStats stats_;
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// PooledPtr<T> - 池化智能指针,行为与 shared_ptr 兼容
|
||||
// ============================================================================
|
||||
template <typename T>
|
||||
class PooledPtr {
|
||||
public:
|
||||
// ========================================================================
|
||||
// 构造和析构
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 默认构造函数(空指针)
|
||||
*/
|
||||
PooledPtr() : ptr_(nullptr), controlBlock_(nullptr) {}
|
||||
|
||||
/**
|
||||
* @brief 从 nullptr 构造
|
||||
*/
|
||||
PooledPtr(std::nullptr_t) : ptr_(nullptr), controlBlock_(nullptr) {}
|
||||
|
||||
/**
|
||||
* @brief 从对象指针和控制块构造
|
||||
* @param ptr 对象指针
|
||||
* @param cb 控制块
|
||||
*/
|
||||
PooledPtr(T* ptr, ControlBlock* cb) : ptr_(ptr), controlBlock_(cb) {}
|
||||
|
||||
/**
|
||||
* @brief 析构函数,引用计数归零时归还对象池
|
||||
*/
|
||||
~PooledPtr() {
|
||||
releaseRef();
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 拷贝语义
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 拷贝构造函数
|
||||
* @param other 另一个 PooledPtr
|
||||
*/
|
||||
PooledPtr(const PooledPtr& other)
|
||||
: ptr_(other.ptr_), controlBlock_(other.controlBlock_) {
|
||||
if (controlBlock_) {
|
||||
controlBlock_->addRef();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 拷贝赋值运算符
|
||||
* @param other 另一个 PooledPtr
|
||||
* @return 引用
|
||||
*/
|
||||
PooledPtr& operator=(const PooledPtr& other) {
|
||||
if (this != &other) {
|
||||
releaseRef();
|
||||
ptr_ = other.ptr_;
|
||||
controlBlock_ = other.controlBlock_;
|
||||
if (controlBlock_) {
|
||||
controlBlock_->addRef();
|
||||
}
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 移动语义
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 移动构造函数
|
||||
* @param other 另一个 PooledPtr
|
||||
*/
|
||||
PooledPtr(PooledPtr&& other) noexcept
|
||||
: ptr_(other.ptr_), controlBlock_(other.controlBlock_) {
|
||||
other.ptr_ = nullptr;
|
||||
other.controlBlock_ = nullptr;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 移动赋值运算符
|
||||
* @param other 另一个 PooledPtr
|
||||
* @return 引用
|
||||
*/
|
||||
PooledPtr& operator=(PooledPtr&& other) noexcept {
|
||||
if (this != &other) {
|
||||
releaseRef();
|
||||
ptr_ = other.ptr_;
|
||||
controlBlock_ = other.controlBlock_;
|
||||
other.ptr_ = nullptr;
|
||||
other.controlBlock_ = nullptr;
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 类型转换构造(支持多态)
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 从其他类型的 PooledPtr 构造(支持向上转型)
|
||||
*/
|
||||
template <typename U, typename = std::enable_if_t<std::is_convertible_v<U*, T*>>>
|
||||
PooledPtr(const PooledPtr<U>& other)
|
||||
: ptr_(other.get()), controlBlock_(other.controlBlock()) {
|
||||
if (controlBlock_) {
|
||||
controlBlock_->addRef();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 从其他类型的 PooledPtr 移动构造(支持向上转型)
|
||||
*/
|
||||
template <typename U, typename = std::enable_if_t<std::is_convertible_v<U*, T*>>>
|
||||
PooledPtr(PooledPtr<U>&& other) noexcept
|
||||
: ptr_(other.get()), controlBlock_(other.controlBlock()) {
|
||||
other.reset();
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 访问器
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 获取原始指针
|
||||
* @return 原始指针
|
||||
*/
|
||||
T* get() const { return ptr_; }
|
||||
|
||||
/**
|
||||
* @brief 获取控制块
|
||||
* @return 控制块指针
|
||||
*/
|
||||
ControlBlock* controlBlock() const { return controlBlock_; }
|
||||
|
||||
/**
|
||||
* @brief 获取引用计数
|
||||
* @return 引用计数
|
||||
*/
|
||||
int32 useCount() const {
|
||||
return controlBlock_ ? controlBlock_->getRefCount() : 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 检查是否唯一引用
|
||||
* @return 是否唯一引用
|
||||
*/
|
||||
bool unique() const {
|
||||
return useCount() == 1;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 检查是否有效
|
||||
* @return 是否有效
|
||||
*/
|
||||
bool valid() const { return ptr_ != nullptr; }
|
||||
|
||||
// ========================================================================
|
||||
// 运算符重载
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 箭头运算符
|
||||
*/
|
||||
T* operator->() const { return ptr_; }
|
||||
|
||||
/**
|
||||
* @brief 解引用运算符
|
||||
*/
|
||||
T& operator*() const { return *ptr_; }
|
||||
|
||||
/**
|
||||
* @brief 布尔转换运算符
|
||||
*/
|
||||
explicit operator bool() const { return valid(); }
|
||||
|
||||
/**
|
||||
* @brief 取反运算符
|
||||
*/
|
||||
bool operator!() const { return !valid(); }
|
||||
|
||||
// ========================================================================
|
||||
// 重置
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 重置为空指针
|
||||
*/
|
||||
void reset() {
|
||||
releaseRef();
|
||||
ptr_ = nullptr;
|
||||
controlBlock_ = nullptr;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 重置为新的对象
|
||||
* @param ptr 新对象指针
|
||||
* @param cb 新控制块
|
||||
*/
|
||||
void reset(T* ptr, ControlBlock* cb) {
|
||||
releaseRef();
|
||||
ptr_ = ptr;
|
||||
controlBlock_ = cb;
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 比较运算符
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 相等比较
|
||||
*/
|
||||
bool operator==(const PooledPtr& other) const {
|
||||
return ptr_ == other.ptr_;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 不等比较
|
||||
*/
|
||||
bool operator!=(const PooledPtr& other) const {
|
||||
return ptr_ != other.ptr_;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 与 nullptr 比较
|
||||
*/
|
||||
bool operator==(std::nullptr_t) const {
|
||||
return ptr_ == nullptr;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 与 nullptr 比较
|
||||
*/
|
||||
bool operator!=(std::nullptr_t) const {
|
||||
return ptr_ != nullptr;
|
||||
}
|
||||
|
||||
private:
|
||||
/**
|
||||
* @brief 释放引用
|
||||
*/
|
||||
void releaseRef() {
|
||||
if (controlBlock_ && controlBlock_->release() == 0) {
|
||||
// 引用计数归零,归还对象池
|
||||
auto* pool = static_cast<ObjectPool<T>*>(controlBlock_->pool);
|
||||
if (pool) {
|
||||
pool->release(controlBlock_);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
T* ptr_;
|
||||
ControlBlock* controlBlock_;
|
||||
|
||||
// 允许其他类型的 PooledPtr 访问私有成员
|
||||
template <typename U>
|
||||
friend class PooledPtr;
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// ObjectPoolManager - 全局对象池管理器
|
||||
// ============================================================================
|
||||
class ObjectPoolManager {
|
||||
public:
|
||||
/**
|
||||
* @brief 获取单例实例
|
||||
* @return 单例引用
|
||||
*/
|
||||
static ObjectPoolManager& instance() {
|
||||
static ObjectPoolManager instance;
|
||||
return instance;
|
||||
}
|
||||
|
||||
// 禁止拷贝和移动
|
||||
ObjectPoolManager(const ObjectPoolManager&) = delete;
|
||||
ObjectPoolManager& operator=(const ObjectPoolManager&) = delete;
|
||||
|
||||
// ========================================================================
|
||||
// 类型池访问
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 获取指定类型的对象池
|
||||
* @return 对象池引用
|
||||
*/
|
||||
template <typename T>
|
||||
ObjectPool<T>& getPool() {
|
||||
std::lock_guard<std::mutex> lock(mutex_);
|
||||
|
||||
using PoolPtr = UniquePtr<ObjectPool<T>>;
|
||||
static PoolPtr pool = makeUnique<ObjectPool<T>>();
|
||||
return *pool;
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 预分配
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 预分配指定类型的对象
|
||||
* @param count 预分配数量
|
||||
*/
|
||||
template <typename T>
|
||||
void preallocate(size_t count) {
|
||||
getPool<T>().preallocate(count);
|
||||
}
|
||||
|
||||
// ========================================================================
|
||||
// 统计信息
|
||||
// ========================================================================
|
||||
|
||||
/**
|
||||
* @brief 获取指定类型的统计信息
|
||||
* @return 统计信息
|
||||
*/
|
||||
template <typename T>
|
||||
ObjectPoolStats getStats() {
|
||||
return getPool<T>().getStats();
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief 收缩指定类型的对象池
|
||||
* @param keepCount 保留的空闲对象数量
|
||||
* @return 释放的对象数量
|
||||
*/
|
||||
template <typename T>
|
||||
size_t shrink(size_t keepCount = 0) {
|
||||
return getPool<T>().shrink(keepCount);
|
||||
}
|
||||
|
||||
private:
|
||||
ObjectPoolManager() = default;
|
||||
mutable std::mutex mutex_;
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// 辅助函数 - 从对象池创建对象
|
||||
// ============================================================================
|
||||
|
||||
/**
|
||||
* @brief 从对象池获取对象
|
||||
* @param args 构造参数
|
||||
* @return PooledPtr 智能指针
|
||||
*/
|
||||
template <typename T, typename... Args>
|
||||
PooledPtr<T> makePooled(Args&&... args) {
|
||||
auto& pool = ObjectPoolManager::instance().getPool<T>();
|
||||
auto [ptr, cb] = pool.acquire(std::forward<Args>(args)...);
|
||||
return PooledPtr<T>(ptr, cb);
|
||||
}
|
||||
|
||||
} // namespace extra2d
|
||||
|
|
@ -5,6 +5,15 @@
|
|||
#include <memory>
|
||||
#include <string>
|
||||
|
||||
// 前向声明
|
||||
namespace extra2d {
|
||||
template <typename T> class PooledPtr;
|
||||
template <typename T> class ObjectPool;
|
||||
struct ControlBlock;
|
||||
class ObjectPoolManager;
|
||||
template <typename T, typename... Args> PooledPtr<T> makePooled(Args&&...);
|
||||
}
|
||||
|
||||
namespace extra2d {
|
||||
|
||||
// ---------------------------------------------------------------------------
|
||||
|
|
@ -16,18 +25,20 @@ namespace extra2d {
|
|||
// ---------------------------------------------------------------------------
|
||||
// 智能指针别名
|
||||
// ---------------------------------------------------------------------------
|
||||
template <typename T> using Ptr = std::shared_ptr<T>;
|
||||
// Ptr<T> 使用对象池支持的智能指针(透明替换原有 shared_ptr)
|
||||
template <typename T> using Ptr = PooledPtr<T>;
|
||||
|
||||
// SharedPtr<T> 保留为 std::shared_ptr(兼容旧代码)
|
||||
template <typename T> using SharedPtr = std::shared_ptr<T>;
|
||||
|
||||
template <typename T> using UniquePtr = std::unique_ptr<T>;
|
||||
|
||||
template <typename T> using WeakPtr = std::weak_ptr<T>;
|
||||
|
||||
/// 创建 shared_ptr 的便捷函数
|
||||
template <typename T, typename... Args> inline Ptr<T> makePtr(Args &&...args) {
|
||||
return std::make_shared<T>(std::forward<Args>(args)...);
|
||||
}
|
||||
/// 创建 Ptr<T> 的便捷函数(使用对象池)
|
||||
template <typename T, typename... Args> inline Ptr<T> makePtr(Args &&...args);
|
||||
|
||||
/// 创建 shared_ptr 的便捷函数(兼容旧代码)
|
||||
template <typename T, typename... Args> inline SharedPtr<T> makeShared(Args &&...args) {
|
||||
return std::make_shared<T>(std::forward<Args>(args)...);
|
||||
}
|
||||
|
|
@ -56,3 +67,15 @@ using uint32 = std::uint32_t;
|
|||
using uint64 = std::uint64_t;
|
||||
|
||||
} // namespace extra2d
|
||||
|
||||
// 包含对象池实现(需要完整类型定义)
|
||||
#include <extra2d/core/object_pool.h>
|
||||
|
||||
namespace extra2d {
|
||||
|
||||
// makePtr 实现(放在 include 之后,因为需要完整的 PooledPtr 定义)
|
||||
template <typename T, typename... Args> inline Ptr<T> makePtr(Args &&...args) {
|
||||
return makePooled<T>(std::forward<Args>(args)...);
|
||||
}
|
||||
|
||||
} // namespace extra2d
|
||||
|
|
|
|||
|
|
@ -90,7 +90,7 @@ private:
|
|||
|
||||
IWindow* window_;
|
||||
GLSpriteBatch spriteBatch_;
|
||||
Ptr<IShader> shapeShader_;
|
||||
SharedPtr<IShader> shapeShader_;
|
||||
|
||||
GLuint shapeVao_;
|
||||
GLuint shapeVbo_;
|
||||
|
|
|
|||
|
|
@ -174,7 +174,7 @@ public:
|
|||
* @param fragSource 片段着色器源码
|
||||
* @return 创建的Shader实例
|
||||
*/
|
||||
Ptr<IShader> createFromSource(
|
||||
SharedPtr<IShader> createFromSource(
|
||||
const std::string& name,
|
||||
const std::string& vertSource,
|
||||
const std::string& fragSource) override;
|
||||
|
|
@ -185,7 +185,7 @@ public:
|
|||
* @param binary 编译后的二进制数据
|
||||
* @return 创建的Shader实例
|
||||
*/
|
||||
Ptr<IShader> createFromBinary(
|
||||
SharedPtr<IShader> createFromBinary(
|
||||
const std::string& name,
|
||||
const std::vector<uint8_t>& binary) override;
|
||||
|
||||
|
|
|
|||
|
|
@ -150,7 +150,7 @@ public:
|
|||
/**
|
||||
* @brief 创建渲染目标的静态工厂方法
|
||||
*/
|
||||
static Ptr<RenderTarget> createFromConfig(const RenderTargetConfig &config);
|
||||
static SharedPtr<RenderTarget> createFromConfig(const RenderTargetConfig &config);
|
||||
|
||||
/**
|
||||
* @brief 获取当前绑定的渲染目标ID
|
||||
|
|
@ -274,7 +274,7 @@ public:
|
|||
/**
|
||||
* @brief 创建新的渲染目标
|
||||
*/
|
||||
Ptr<RenderTarget> createRenderTarget(const RenderTargetConfig &config);
|
||||
SharedPtr<RenderTarget> createRenderTarget(const RenderTargetConfig &config);
|
||||
|
||||
/**
|
||||
* @brief 获取默认渲染目标
|
||||
|
|
@ -299,8 +299,8 @@ private:
|
|||
RenderTargetMgr(const RenderTargetMgr &) = delete;
|
||||
RenderTargetMgr &operator=(const RenderTargetMgr &) = delete;
|
||||
|
||||
Ptr<RenderTarget> defaultRenderTarget_;
|
||||
std::vector<Ptr<RenderTarget>> renderTargets_;
|
||||
SharedPtr<RenderTarget> defaultRenderTarget_;
|
||||
std::vector<SharedPtr<RenderTarget>> renderTargets_;
|
||||
bool initialized_ = false;
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -54,7 +54,7 @@ public:
|
|||
* @param name Shader名称
|
||||
* @return 缓存条目指针,不存在返回nullptr
|
||||
*/
|
||||
Ptr<ShaderCacheEntry> loadCache(const std::string& name);
|
||||
SharedPtr<ShaderCacheEntry> loadCache(const std::string& name);
|
||||
|
||||
/**
|
||||
* @brief 保存编译结果到缓存
|
||||
|
|
|
|||
|
|
@ -124,7 +124,7 @@ public:
|
|||
* @param fragSource 片段着色器源码
|
||||
* @return 创建的Shader实例
|
||||
*/
|
||||
virtual Ptr<IShader> createFromSource(
|
||||
virtual SharedPtr<IShader> createFromSource(
|
||||
const std::string& name,
|
||||
const std::string& vertSource,
|
||||
const std::string& fragSource) = 0;
|
||||
|
|
@ -135,7 +135,7 @@ public:
|
|||
* @param binary 编译后的二进制数据
|
||||
* @return 创建的Shader实例
|
||||
*/
|
||||
virtual Ptr<IShader> createFromBinary(
|
||||
virtual SharedPtr<IShader> createFromBinary(
|
||||
const std::string& name,
|
||||
const std::vector<uint8_t>& binary) = 0;
|
||||
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ namespace extra2d {
|
|||
// ============================================================================
|
||||
// Shader重载回调
|
||||
// ============================================================================
|
||||
using ShaderReloadCallback = std::function<void(Ptr<IShader> newShader)>;
|
||||
using ShaderReloadCallback = std::function<void(SharedPtr<IShader> newShader)>;
|
||||
|
||||
// ============================================================================
|
||||
// Shader管理器 - 统一入口
|
||||
|
|
@ -37,7 +37,7 @@ public:
|
|||
* @param appName 应用名称(用于缓存目录)
|
||||
* @return 初始化成功返回true,失败返回false
|
||||
*/
|
||||
bool init(Ptr<IShaderFactory> factory, const std::string& appName = "extra2d");
|
||||
bool init(SharedPtr<IShaderFactory> factory, const std::string& appName = "extra2d");
|
||||
|
||||
/**
|
||||
* @brief 初始化Shader系统
|
||||
|
|
@ -48,7 +48,7 @@ public:
|
|||
*/
|
||||
bool init(const std::string& shaderDir,
|
||||
const std::string& cacheDir,
|
||||
Ptr<IShaderFactory> factory);
|
||||
SharedPtr<IShaderFactory> factory);
|
||||
|
||||
/**
|
||||
* @brief 关闭Shader系统
|
||||
|
|
@ -79,7 +79,7 @@ public:
|
|||
* @param fragPath 片段着色器文件路径
|
||||
* @return 加载的Shader实例
|
||||
*/
|
||||
Ptr<IShader> loadFromFiles(const std::string& name,
|
||||
SharedPtr<IShader> loadFromFiles(const std::string& name,
|
||||
const std::string& vertPath,
|
||||
const std::string& fragPath);
|
||||
|
||||
|
|
@ -88,7 +88,7 @@ public:
|
|||
* @param path 组合Shader文件路径
|
||||
* @return 加载的Shader实例
|
||||
*/
|
||||
Ptr<IShader> loadFromCombinedFile(const std::string& path);
|
||||
SharedPtr<IShader> loadFromCombinedFile(const std::string& path);
|
||||
|
||||
/**
|
||||
* @brief 从源码加载Shader
|
||||
|
|
@ -97,7 +97,7 @@ public:
|
|||
* @param fragSource 片段着色器源码
|
||||
* @return 加载的Shader实例
|
||||
*/
|
||||
Ptr<IShader> loadFromSource(const std::string& name,
|
||||
SharedPtr<IShader> loadFromSource(const std::string& name,
|
||||
const std::string& vertSource,
|
||||
const std::string& fragSource);
|
||||
|
||||
|
|
@ -106,7 +106,7 @@ public:
|
|||
* @param name Shader名称
|
||||
* @return Shader实例,不存在返回nullptr
|
||||
*/
|
||||
Ptr<IShader> get(const std::string& name) const;
|
||||
SharedPtr<IShader> get(const std::string& name) const;
|
||||
|
||||
/**
|
||||
* @brief 检查Shader是否存在
|
||||
|
|
@ -170,7 +170,7 @@ public:
|
|||
* @param name 内置Shader名称
|
||||
* @return Shader实例
|
||||
*/
|
||||
Ptr<IShader> getBuiltin(const std::string& name);
|
||||
SharedPtr<IShader> getBuiltin(const std::string& name);
|
||||
|
||||
/**
|
||||
* @brief 加载所有内置Shader
|
||||
|
|
@ -202,11 +202,11 @@ private:
|
|||
|
||||
std::string shaderDir_;
|
||||
std::string cacheDir_;
|
||||
Ptr<IShaderFactory> factory_;
|
||||
SharedPtr<IShaderFactory> factory_;
|
||||
ShaderLoader loader_;
|
||||
|
||||
struct ShaderInfo {
|
||||
Ptr<IShader> shader;
|
||||
SharedPtr<IShader> shader;
|
||||
ShaderMetadata metadata;
|
||||
ShaderReloadCallback reloadCallback;
|
||||
std::string vertSource;
|
||||
|
|
@ -227,7 +227,7 @@ private:
|
|||
* @param fragSource 片段着色器源码
|
||||
* @return Shader实例
|
||||
*/
|
||||
Ptr<IShader> loadFromCache(const std::string& name,
|
||||
SharedPtr<IShader> loadFromCache(const std::string& name,
|
||||
const std::string& sourceHash,
|
||||
const std::string& vertSource,
|
||||
const std::string& fragSource);
|
||||
|
|
|
|||
|
|
@ -46,49 +46,49 @@ public:
|
|||
* @param params 水波纹效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
static Ptr<IShader> Water(const WaterParams& params = {});
|
||||
static SharedPtr<IShader> Water(const WaterParams& params = {});
|
||||
|
||||
/**
|
||||
* @brief 创建描边效果着色器
|
||||
* @param params 描边效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
static Ptr<IShader> Outline(const OutlineParams& params = {});
|
||||
static SharedPtr<IShader> Outline(const OutlineParams& params = {});
|
||||
|
||||
/**
|
||||
* @brief 创建扭曲效果着色器
|
||||
* @param params 扭曲效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
static Ptr<IShader> Distortion(const DistortionParams& params = {});
|
||||
static SharedPtr<IShader> Distortion(const DistortionParams& params = {});
|
||||
|
||||
/**
|
||||
* @brief 创建像素化效果着色器
|
||||
* @param params 像素化效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
static Ptr<IShader> Pixelate(const PixelateParams& params = {});
|
||||
static SharedPtr<IShader> Pixelate(const PixelateParams& params = {});
|
||||
|
||||
/**
|
||||
* @brief 创建反相效果着色器
|
||||
* @param params 反相效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
static Ptr<IShader> Invert(const InvertParams& params = {});
|
||||
static SharedPtr<IShader> Invert(const InvertParams& params = {});
|
||||
|
||||
/**
|
||||
* @brief 创建灰度效果着色器
|
||||
* @param params 灰度效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
static Ptr<IShader> Grayscale(const GrayscaleParams& params = {});
|
||||
static SharedPtr<IShader> Grayscale(const GrayscaleParams& params = {});
|
||||
|
||||
/**
|
||||
* @brief 创建模糊效果着色器
|
||||
* @param params 模糊效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
static Ptr<IShader> Blur(const BlurParams& params = {});
|
||||
static SharedPtr<IShader> Blur(const BlurParams& params = {});
|
||||
|
||||
/**
|
||||
* @brief 创建灰度+描边组合效果着色器
|
||||
|
|
@ -96,7 +96,7 @@ public:
|
|||
* @param outlineParams 描边效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
static Ptr<IShader> GrayscaleOutline(const GrayscaleParams& grayParams,
|
||||
static SharedPtr<IShader> GrayscaleOutline(const GrayscaleParams& grayParams,
|
||||
const OutlineParams& outlineParams);
|
||||
|
||||
/**
|
||||
|
|
@ -105,8 +105,8 @@ public:
|
|||
* @param invParams 反相效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
static Ptr<IShader> PixelateInvert(const PixelateParams& pixParams,
|
||||
static SharedPtr<IShader> PixelateInvert(const PixelateParams& pixParams,
|
||||
const InvertParams& invParams);
|
||||
};
|
||||
|
||||
} // namespace extra2d
|
||||
}
|
||||
|
|
|
|||
|
|
@ -18,6 +18,7 @@ struct RenderCommand;
|
|||
|
||||
// ============================================================================
|
||||
// 节点基类 - 场景图的基础
|
||||
// 注意:Node 使用 SharedPtr 而非 Ptr,因为需要 enable_shared_from_this 支持
|
||||
// ============================================================================
|
||||
class Node : public std::enable_shared_from_this<Node> {
|
||||
public:
|
||||
|
|
@ -27,23 +28,23 @@ public:
|
|||
// ------------------------------------------------------------------------
|
||||
// 层级管理
|
||||
// ------------------------------------------------------------------------
|
||||
void addChild(Ptr<Node> child);
|
||||
void addChild(SharedPtr<Node> child);
|
||||
|
||||
/**
|
||||
* @brief 批量添加子节点
|
||||
* @param children 子节点列表
|
||||
*/
|
||||
void addChildren(std::vector<Ptr<Node>> &&children);
|
||||
void addChildren(std::vector<SharedPtr<Node>> &&children);
|
||||
|
||||
void removeChild(Ptr<Node> child);
|
||||
void removeChild(SharedPtr<Node> child);
|
||||
void removeChildByName(const std::string &name);
|
||||
void detach();
|
||||
void clearChildren();
|
||||
|
||||
Ptr<Node> getParent() const { return parent_.lock(); }
|
||||
const std::vector<Ptr<Node>> &getChildren() const { return children_; }
|
||||
Ptr<Node> findChild(const std::string &name) const;
|
||||
Ptr<Node> findChildByTag(int tag) const;
|
||||
SharedPtr<Node> getParent() const { return parent_.lock(); }
|
||||
const std::vector<SharedPtr<Node>> &getChildren() const { return children_; }
|
||||
SharedPtr<Node> findChild(const std::string &name) const;
|
||||
SharedPtr<Node> findChildByTag(int tag) const;
|
||||
|
||||
// ------------------------------------------------------------------------
|
||||
// 变换属性
|
||||
|
|
@ -191,18 +192,18 @@ private:
|
|||
mutable glm::mat4 worldTransform_; // 64 bytes
|
||||
|
||||
// 2. 字符串和容器(24-32字节)
|
||||
std::string name_; // 32 bytes
|
||||
std::vector<Ptr<Node>> children_; // 24 bytes
|
||||
std::string name_; // 32 bytes
|
||||
std::vector<SharedPtr<Node>> children_; // 24 bytes
|
||||
|
||||
// 3. 子节点索引(加速查找)
|
||||
std::unordered_map<std::string, WeakPtr<Node>> nameIndex_; // 56 bytes
|
||||
std::unordered_map<int, WeakPtr<Node>> tagIndex_; // 56 bytes
|
||||
std::unordered_map<std::string, std::weak_ptr<Node>> nameIndex_; // 56 bytes
|
||||
std::unordered_map<int, std::weak_ptr<Node>> tagIndex_; // 56 bytes
|
||||
|
||||
// 4. 事件分发器
|
||||
EventDispatcher eventDispatcher_; // 大小取决于实现
|
||||
|
||||
// 5. 父节点引用
|
||||
WeakPtr<Node> parent_; // 16 bytes
|
||||
std::weak_ptr<Node> parent_; // 16 bytes
|
||||
|
||||
// 7. 变换属性(按访问频率分组)
|
||||
Vec2 position_ = Vec2::Zero(); // 8 bytes
|
||||
|
|
|
|||
|
|
@ -12,6 +12,7 @@ struct RenderCommand;
|
|||
|
||||
// ============================================================================
|
||||
// 场景类 - 节点容器,管理整个场景图
|
||||
// 注意:Scene 继承自 Node,使用 SharedPtr 因为需要 enable_shared_from_this
|
||||
// ============================================================================
|
||||
class Scene : public Node {
|
||||
public:
|
||||
|
|
@ -27,8 +28,8 @@ public:
|
|||
// ------------------------------------------------------------------------
|
||||
// 摄像机
|
||||
// ------------------------------------------------------------------------
|
||||
void setCamera(Ptr<Camera> camera);
|
||||
Ptr<Camera> getCamera() const { return camera_; }
|
||||
void setCamera(SharedPtr<Camera> camera);
|
||||
SharedPtr<Camera> getCamera() const { return camera_; }
|
||||
|
||||
Camera *getActiveCamera() const {
|
||||
return camera_ ? camera_.get() : defaultCamera_.get();
|
||||
|
|
@ -63,7 +64,7 @@ public:
|
|||
// ------------------------------------------------------------------------
|
||||
// 静态创建方法
|
||||
// ------------------------------------------------------------------------
|
||||
static Ptr<Scene> create();
|
||||
static SharedPtr<Scene> create();
|
||||
|
||||
protected:
|
||||
void onEnter() override;
|
||||
|
|
@ -80,8 +81,8 @@ private:
|
|||
Color backgroundColor_ = Colors::Black;
|
||||
Size viewportSize_ = Size::Zero();
|
||||
|
||||
Ptr<Camera> camera_;
|
||||
Ptr<Camera> defaultCamera_;
|
||||
SharedPtr<Camera> camera_;
|
||||
SharedPtr<Camera> defaultCamera_;
|
||||
|
||||
bool paused_ = false;
|
||||
};
|
||||
|
|
|
|||
|
|
@ -22,17 +22,17 @@ public:
|
|||
|
||||
static SceneManager &get();
|
||||
|
||||
void runWithScene(Ptr<Scene> scene);
|
||||
void replaceScene(Ptr<Scene> scene);
|
||||
void pushScene(Ptr<Scene> scene);
|
||||
void runWithScene(SharedPtr<Scene> scene);
|
||||
void replaceScene(SharedPtr<Scene> scene);
|
||||
void pushScene(SharedPtr<Scene> scene);
|
||||
void popScene();
|
||||
void popToRootScene();
|
||||
void popToScene(const std::string &name);
|
||||
|
||||
Ptr<Scene> getCurrentScene() const;
|
||||
Ptr<Scene> getPreviousScene() const;
|
||||
Ptr<Scene> getRootScene() const;
|
||||
Ptr<Scene> getSceneByName(const std::string &name) const;
|
||||
SharedPtr<Scene> getCurrentScene() const;
|
||||
SharedPtr<Scene> getPreviousScene() const;
|
||||
SharedPtr<Scene> getRootScene() const;
|
||||
SharedPtr<Scene> getSceneByName(const std::string &name) const;
|
||||
|
||||
size_t getSceneCount() const { return sceneStack_.size(); }
|
||||
bool isEmpty() const { return sceneStack_.empty(); }
|
||||
|
|
@ -56,19 +56,19 @@ public:
|
|||
SceneManager(const SceneManager &) = delete;
|
||||
SceneManager &operator=(const SceneManager &) = delete;
|
||||
|
||||
void enterScene(Ptr<Scene> scene);
|
||||
void enterScene(SharedPtr<Scene> scene);
|
||||
|
||||
private:
|
||||
void doSceneSwitch();
|
||||
void dispatchPointerEvents(Scene &scene);
|
||||
|
||||
std::stack<Ptr<Scene>> sceneStack_;
|
||||
std::unordered_map<std::string, Ptr<Scene>> namedScenes_;
|
||||
std::stack<SharedPtr<Scene>> sceneStack_;
|
||||
std::unordered_map<std::string, SharedPtr<Scene>> namedScenes_;
|
||||
|
||||
bool isTransitioning_ = false;
|
||||
TransitionCallback transitionCallback_;
|
||||
|
||||
Ptr<Scene> nextScene_;
|
||||
SharedPtr<Scene> nextScene_;
|
||||
bool sendCleanupToScene_ = false;
|
||||
|
||||
Node *hoverTarget_ = nullptr;
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ enum class ShapeType { Point, Line, Rect, Circle, Triangle, Polygon };
|
|||
|
||||
// ============================================================================
|
||||
// 形状节点 - 用于绘制几何形状
|
||||
// 注意:ShapeNode 继承自 Node,使用 SharedPtr 因为需要 enable_shared_from_this
|
||||
// ============================================================================
|
||||
class ShapeNode : public Node {
|
||||
public:
|
||||
|
|
@ -23,41 +24,47 @@ public:
|
|||
// ------------------------------------------------------------------------
|
||||
// 静态创建方法
|
||||
// ------------------------------------------------------------------------
|
||||
static Ptr<ShapeNode> create();
|
||||
static SharedPtr<ShapeNode> create();
|
||||
|
||||
// 点
|
||||
static Ptr<ShapeNode> createPoint(const Vec2 &pos, const Color &color);
|
||||
static SharedPtr<ShapeNode> createPoint(const Vec2 &pos, const Color &color);
|
||||
|
||||
// 线
|
||||
static Ptr<ShapeNode> createLine(const Vec2 &start, const Vec2 &end,
|
||||
const Color &color, float width = 1.0f);
|
||||
static SharedPtr<ShapeNode> createLine(const Vec2 &start, const Vec2 &end,
|
||||
const Color &color,
|
||||
float width = 1.0f);
|
||||
|
||||
// 矩形
|
||||
static Ptr<ShapeNode> createRect(const Rect &rect, const Color &color,
|
||||
float width = 1.0f);
|
||||
static Ptr<ShapeNode> createFilledRect(const Rect &rect, const Color &color);
|
||||
static SharedPtr<ShapeNode> createRect(const Rect &rect, const Color &color,
|
||||
float width = 1.0f);
|
||||
static SharedPtr<ShapeNode> createFilledRect(const Rect &rect,
|
||||
const Color &color);
|
||||
|
||||
// 圆形
|
||||
static Ptr<ShapeNode> createCircle(const Vec2 ¢er, float radius,
|
||||
const Color &color, int segments = 32,
|
||||
float width = 1.0f);
|
||||
static Ptr<ShapeNode> createFilledCircle(const Vec2 ¢er, float radius,
|
||||
static SharedPtr<ShapeNode> createCircle(const Vec2 ¢er, float radius,
|
||||
const Color &color,
|
||||
int segments = 32);
|
||||
int segments = 32,
|
||||
float width = 1.0f);
|
||||
static SharedPtr<ShapeNode> createFilledCircle(const Vec2 ¢er,
|
||||
float radius,
|
||||
const Color &color,
|
||||
int segments = 32);
|
||||
|
||||
// 三角形
|
||||
static Ptr<ShapeNode> createTriangle(const Vec2 &p1, const Vec2 &p2,
|
||||
const Vec2 &p3, const Color &color,
|
||||
float width = 1.0f);
|
||||
static Ptr<ShapeNode> createFilledTriangle(const Vec2 &p1, const Vec2 &p2,
|
||||
const Vec2 &p3,
|
||||
const Color &color);
|
||||
static SharedPtr<ShapeNode> createTriangle(const Vec2 &p1, const Vec2 &p2,
|
||||
const Vec2 &p3, const Color &color,
|
||||
float width = 1.0f);
|
||||
static SharedPtr<ShapeNode> createFilledTriangle(const Vec2 &p1,
|
||||
const Vec2 &p2,
|
||||
const Vec2 &p3,
|
||||
const Color &color);
|
||||
|
||||
// 多边形
|
||||
static Ptr<ShapeNode> createPolygon(const std::vector<Vec2> &points,
|
||||
const Color &color, float width = 1.0f);
|
||||
static Ptr<ShapeNode> createFilledPolygon(const std::vector<Vec2> &points,
|
||||
const Color &color);
|
||||
static SharedPtr<ShapeNode> createPolygon(const std::vector<Vec2> &points,
|
||||
const Color &color,
|
||||
float width = 1.0f);
|
||||
static SharedPtr<ShapeNode>
|
||||
createFilledPolygon(const std::vector<Vec2> &points, const Color &color);
|
||||
|
||||
// ------------------------------------------------------------------------
|
||||
// 属性设置
|
||||
|
|
|
|||
|
|
@ -7,6 +7,7 @@ namespace extra2d {
|
|||
|
||||
// ============================================================================
|
||||
// 精灵节点
|
||||
// 注意:Sprite 继承自 Node,使用 SharedPtr 因为需要 enable_shared_from_this
|
||||
// ============================================================================
|
||||
class Sprite : public Node {
|
||||
public:
|
||||
|
|
@ -33,9 +34,9 @@ public:
|
|||
bool isFlipY() const { return flipY_; }
|
||||
|
||||
// 静态创建方法
|
||||
static Ptr<Sprite> create();
|
||||
static Ptr<Sprite> create(Ptr<Texture> texture);
|
||||
static Ptr<Sprite> create(Ptr<Texture> texture, const Rect &rect);
|
||||
static SharedPtr<Sprite> create();
|
||||
static SharedPtr<Sprite> create(Ptr<Texture> texture);
|
||||
static SharedPtr<Sprite> create(Ptr<Texture> texture, const Rect &rect);
|
||||
|
||||
Rect getBounds() const override;
|
||||
|
||||
|
|
@ -52,4 +53,4 @@ private:
|
|||
bool flipY_ = false;
|
||||
};
|
||||
|
||||
} // namespace extra2d
|
||||
}
|
||||
|
|
|
|||
|
|
@ -13,17 +13,17 @@ class ISceneService : public IService {
|
|||
public:
|
||||
virtual ~ISceneService() = default;
|
||||
|
||||
virtual void runWithScene(Ptr<Scene> scene) = 0;
|
||||
virtual void replaceScene(Ptr<Scene> scene) = 0;
|
||||
virtual void pushScene(Ptr<Scene> scene) = 0;
|
||||
virtual void runWithScene(SharedPtr<Scene> scene) = 0;
|
||||
virtual void replaceScene(SharedPtr<Scene> scene) = 0;
|
||||
virtual void pushScene(SharedPtr<Scene> scene) = 0;
|
||||
virtual void popScene() = 0;
|
||||
virtual void popToRootScene() = 0;
|
||||
virtual void popToScene(const std::string& name) = 0;
|
||||
|
||||
virtual Ptr<Scene> getCurrentScene() const = 0;
|
||||
virtual Ptr<Scene> getPreviousScene() const = 0;
|
||||
virtual Ptr<Scene> getRootScene() const = 0;
|
||||
virtual Ptr<Scene> getSceneByName(const std::string& name) const = 0;
|
||||
virtual SharedPtr<Scene> getCurrentScene() const = 0;
|
||||
virtual SharedPtr<Scene> getPreviousScene() const = 0;
|
||||
virtual SharedPtr<Scene> getRootScene() const = 0;
|
||||
virtual SharedPtr<Scene> getSceneByName(const std::string& name) const = 0;
|
||||
|
||||
virtual size_t getSceneCount() const = 0;
|
||||
virtual bool isEmpty() const = 0;
|
||||
|
|
@ -37,7 +37,7 @@ public:
|
|||
|
||||
virtual void end() = 0;
|
||||
virtual void purgeCachedScenes() = 0;
|
||||
virtual void enterScene(Ptr<Scene> scene) = 0;
|
||||
virtual void enterScene(SharedPtr<Scene> scene) = 0;
|
||||
};
|
||||
|
||||
/**
|
||||
|
|
@ -55,17 +55,17 @@ public:
|
|||
void shutdown() override;
|
||||
void update(float deltaTime) override;
|
||||
|
||||
void runWithScene(Ptr<Scene> scene) override;
|
||||
void replaceScene(Ptr<Scene> scene) override;
|
||||
void pushScene(Ptr<Scene> scene) override;
|
||||
void runWithScene(SharedPtr<Scene> scene) override;
|
||||
void replaceScene(SharedPtr<Scene> scene) override;
|
||||
void pushScene(SharedPtr<Scene> scene) override;
|
||||
void popScene() override;
|
||||
void popToRootScene() override;
|
||||
void popToScene(const std::string& name) override;
|
||||
|
||||
Ptr<Scene> getCurrentScene() const override;
|
||||
Ptr<Scene> getPreviousScene() const override;
|
||||
Ptr<Scene> getRootScene() const override;
|
||||
Ptr<Scene> getSceneByName(const std::string& name) const override;
|
||||
SharedPtr<Scene> getCurrentScene() const override;
|
||||
SharedPtr<Scene> getPreviousScene() const override;
|
||||
SharedPtr<Scene> getRootScene() const override;
|
||||
SharedPtr<Scene> getSceneByName(const std::string& name) const override;
|
||||
|
||||
size_t getSceneCount() const override;
|
||||
bool isEmpty() const override;
|
||||
|
|
@ -79,7 +79,7 @@ public:
|
|||
|
||||
void end() override;
|
||||
void purgeCachedScenes() override;
|
||||
void enterScene(Ptr<Scene> scene) override;
|
||||
void enterScene(SharedPtr<Scene> scene) override;
|
||||
|
||||
SceneManager& getManager() { return manager_; }
|
||||
const SceneManager& getManager() const { return manager_; }
|
||||
|
|
|
|||
|
|
@ -383,7 +383,7 @@ SharedPtr<ICameraService> Application::camera() {
|
|||
return ServiceLocator::instance().getService<ICameraService>();
|
||||
}
|
||||
|
||||
void Application::enterScene(Ptr<Scene> scene) {
|
||||
void Application::enterScene(SharedPtr<Scene> scene) {
|
||||
auto sceneService = ServiceLocator::instance().getService<ISceneService>();
|
||||
if (sceneService && scene) {
|
||||
scene->setViewportSize(static_cast<float>(window_->width()),
|
||||
|
|
|
|||
|
|
@ -269,7 +269,7 @@ GLint GLShaderNew::getUniformLocation(const std::string& name) {
|
|||
* @param fragSource 片段着色器源码
|
||||
* @return 创建的Shader实例
|
||||
*/
|
||||
Ptr<IShader> GLShaderFactory::createFromSource(
|
||||
SharedPtr<IShader> GLShaderFactory::createFromSource(
|
||||
const std::string& name,
|
||||
const std::string& vertSource,
|
||||
const std::string& fragSource) {
|
||||
|
|
@ -291,7 +291,7 @@ Ptr<IShader> GLShaderFactory::createFromSource(
|
|||
* @param binary 编译后的二进制数据
|
||||
* @return 创建的Shader实例
|
||||
*/
|
||||
Ptr<IShader> GLShaderFactory::createFromBinary(
|
||||
SharedPtr<IShader> GLShaderFactory::createFromBinary(
|
||||
const std::string& name,
|
||||
const std::vector<uint8_t>& binary) {
|
||||
|
||||
|
|
|
|||
|
|
@ -383,9 +383,9 @@ bool RenderTarget::saveToFile(const std::string &filepath) {
|
|||
*
|
||||
* 静态工厂方法,创建并初始化渲染目标
|
||||
*/
|
||||
Ptr<RenderTarget>
|
||||
SharedPtr<RenderTarget>
|
||||
RenderTarget::createFromConfig(const RenderTargetConfig &config) {
|
||||
auto rt = std::make_shared<RenderTarget>();
|
||||
auto rt = makeShared<RenderTarget>();
|
||||
if (rt->create(config)) {
|
||||
return rt;
|
||||
}
|
||||
|
|
@ -741,7 +741,7 @@ void RenderTargetMgr::shutdown() {
|
|||
*
|
||||
* 创建新的渲染目标并由管理器管理
|
||||
*/
|
||||
Ptr<RenderTarget>
|
||||
SharedPtr<RenderTarget>
|
||||
RenderTargetMgr::createRenderTarget(const RenderTargetConfig &config) {
|
||||
if (!initialized_) {
|
||||
E2D_ERROR("渲染目标管理器未初始化");
|
||||
|
|
|
|||
|
|
@ -74,7 +74,7 @@ bool ShaderCache::hasValidCache(const std::string& name, const std::string& sour
|
|||
* @param name Shader名称
|
||||
* @return 缓存条目指针,不存在返回nullptr
|
||||
*/
|
||||
Ptr<ShaderCacheEntry> ShaderCache::loadCache(const std::string& name) {
|
||||
SharedPtr<ShaderCacheEntry> ShaderCache::loadCache(const std::string& name) {
|
||||
auto it = cacheMap_.find(name);
|
||||
if (it == cacheMap_.end()) {
|
||||
return nullptr;
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@ ShaderManager& ShaderManager::getInstance() {
|
|||
* @param appName 应用名称(用于缓存目录)
|
||||
* @return 初始化成功返回true,失败返回false
|
||||
*/
|
||||
bool ShaderManager::init(Ptr<IShaderFactory> factory, const std::string& appName) {
|
||||
bool ShaderManager::init(SharedPtr<IShaderFactory> factory, const std::string& appName) {
|
||||
std::string shaderDir = PlatformDetector::getShaderPath(appName);
|
||||
std::string cacheDir = PlatformDetector::getShaderCachePath(appName);
|
||||
|
||||
|
|
@ -41,7 +41,7 @@ bool ShaderManager::init(Ptr<IShaderFactory> factory, const std::string& appName
|
|||
*/
|
||||
bool ShaderManager::init(const std::string& shaderDir,
|
||||
const std::string& cacheDir,
|
||||
Ptr<IShaderFactory> factory) {
|
||||
SharedPtr<IShaderFactory> factory) {
|
||||
if (initialized_) {
|
||||
E2D_LOG_WARN("ShaderManager already initialized");
|
||||
return true;
|
||||
|
|
@ -112,7 +112,7 @@ void ShaderManager::shutdown() {
|
|||
* @param fragPath 片段着色器文件路径
|
||||
* @return 加载的Shader实例
|
||||
*/
|
||||
Ptr<IShader> ShaderManager::loadFromFiles(const std::string& name,
|
||||
SharedPtr<IShader> ShaderManager::loadFromFiles(const std::string& name,
|
||||
const std::string& vertPath,
|
||||
const std::string& fragPath) {
|
||||
if (!initialized_) {
|
||||
|
|
@ -132,7 +132,7 @@ Ptr<IShader> ShaderManager::loadFromFiles(const std::string& name,
|
|||
}
|
||||
|
||||
std::string sourceHash = ShaderCache::computeHash(result.vertSource, result.fragSource);
|
||||
Ptr<IShader> shader = loadFromCache(name, sourceHash, result.vertSource, result.fragSource);
|
||||
SharedPtr<IShader> shader = loadFromCache(name, sourceHash, result.vertSource, result.fragSource);
|
||||
|
||||
if (!shader) {
|
||||
shader = factory_->createFromSource(name, result.vertSource, result.fragSource);
|
||||
|
|
@ -181,7 +181,7 @@ Ptr<IShader> ShaderManager::loadFromFiles(const std::string& name,
|
|||
* @param path 组合Shader文件路径
|
||||
* @return 加载的Shader实例
|
||||
*/
|
||||
Ptr<IShader> ShaderManager::loadFromCombinedFile(const std::string& path) {
|
||||
SharedPtr<IShader> ShaderManager::loadFromCombinedFile(const std::string& path) {
|
||||
if (!initialized_) {
|
||||
E2D_LOG_ERROR("ShaderManager not initialized");
|
||||
return nullptr;
|
||||
|
|
@ -202,7 +202,7 @@ Ptr<IShader> ShaderManager::loadFromCombinedFile(const std::string& path) {
|
|||
}
|
||||
|
||||
std::string sourceHash = ShaderCache::computeHash(result.vertSource, result.fragSource);
|
||||
Ptr<IShader> shader = loadFromCache(name, sourceHash, result.vertSource, result.fragSource);
|
||||
SharedPtr<IShader> shader = loadFromCache(name, sourceHash, result.vertSource, result.fragSource);
|
||||
|
||||
if (!shader) {
|
||||
shader = factory_->createFromSource(name, result.vertSource, result.fragSource);
|
||||
|
|
@ -250,7 +250,7 @@ Ptr<IShader> ShaderManager::loadFromCombinedFile(const std::string& path) {
|
|||
* @param fragSource 片段着色器源码
|
||||
* @return 加载的Shader实例
|
||||
*/
|
||||
Ptr<IShader> ShaderManager::loadFromSource(const std::string& name,
|
||||
SharedPtr<IShader> ShaderManager::loadFromSource(const std::string& name,
|
||||
const std::string& vertSource,
|
||||
const std::string& fragSource) {
|
||||
if (!initialized_) {
|
||||
|
|
@ -263,7 +263,7 @@ Ptr<IShader> ShaderManager::loadFromSource(const std::string& name,
|
|||
return it->second.shader;
|
||||
}
|
||||
|
||||
Ptr<IShader> shader = factory_->createFromSource(name, vertSource, fragSource);
|
||||
SharedPtr<IShader> shader = factory_->createFromSource(name, vertSource, fragSource);
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to create shader from source: {}", name);
|
||||
return nullptr;
|
||||
|
|
@ -286,7 +286,7 @@ Ptr<IShader> ShaderManager::loadFromSource(const std::string& name,
|
|||
* @param name Shader名称
|
||||
* @return Shader实例,不存在返回nullptr
|
||||
*/
|
||||
Ptr<IShader> ShaderManager::get(const std::string& name) const {
|
||||
SharedPtr<IShader> ShaderManager::get(const std::string& name) const {
|
||||
auto it = shaders_.find(name);
|
||||
if (it != shaders_.end()) {
|
||||
return it->second.shader;
|
||||
|
|
@ -403,7 +403,7 @@ bool ShaderManager::reload(const std::string& name) {
|
|||
}
|
||||
}
|
||||
|
||||
Ptr<IShader> newShader = factory_->createFromSource(name, vertSource, fragSource);
|
||||
SharedPtr<IShader> newShader = factory_->createFromSource(name, vertSource, fragSource);
|
||||
if (!newShader) {
|
||||
E2D_LOG_ERROR("Failed to reload shader: {}", name);
|
||||
return false;
|
||||
|
|
@ -426,8 +426,8 @@ bool ShaderManager::reload(const std::string& name) {
|
|||
* @param name 内置Shader名称
|
||||
* @return Shader实例
|
||||
*/
|
||||
Ptr<IShader> ShaderManager::getBuiltin(const std::string& name) {
|
||||
Ptr<IShader> shader = get(name);
|
||||
SharedPtr<IShader> ShaderManager::getBuiltin(const std::string& name) {
|
||||
SharedPtr<IShader> shader = get(name);
|
||||
if (shader) {
|
||||
return shader;
|
||||
}
|
||||
|
|
@ -487,7 +487,7 @@ bool ShaderManager::loadBuiltinShaders() {
|
|||
* @param fragSource 片段着色器源码
|
||||
* @return Shader实例
|
||||
*/
|
||||
Ptr<IShader> ShaderManager::loadFromCache(const std::string& name,
|
||||
SharedPtr<IShader> ShaderManager::loadFromCache(const std::string& name,
|
||||
const std::string& sourceHash,
|
||||
const std::string& vertSource,
|
||||
const std::string& fragSource) {
|
||||
|
|
@ -499,12 +499,12 @@ Ptr<IShader> ShaderManager::loadFromCache(const std::string& name,
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
Ptr<ShaderCacheEntry> entry = ShaderCache::getInstance().loadCache(name);
|
||||
SharedPtr<ShaderCacheEntry> entry = ShaderCache::getInstance().loadCache(name);
|
||||
if (!entry || entry->binary.empty()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Ptr<IShader> shader = factory_->createFromBinary(name, entry->binary);
|
||||
SharedPtr<IShader> shader = factory_->createFromBinary(name, entry->binary);
|
||||
if (shader) {
|
||||
E2D_LOG_DEBUG("Shader loaded from cache: {}", name);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -9,8 +9,8 @@ namespace extra2d {
|
|||
* @param params 水波纹效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
Ptr<IShader> ShaderPreset::Water(const WaterParams ¶ms) {
|
||||
Ptr<IShader> shader = ShaderManager::getInstance().get("water");
|
||||
SharedPtr<IShader> ShaderPreset::Water(const WaterParams ¶ms) {
|
||||
SharedPtr<IShader> shader = ShaderManager::getInstance().get("water");
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to get water shader");
|
||||
return nullptr;
|
||||
|
|
@ -28,8 +28,8 @@ Ptr<IShader> ShaderPreset::Water(const WaterParams ¶ms) {
|
|||
* @param params 描边效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
Ptr<IShader> ShaderPreset::Outline(const OutlineParams ¶ms) {
|
||||
Ptr<IShader> shader = ShaderManager::getInstance().get("outline");
|
||||
SharedPtr<IShader> ShaderPreset::Outline(const OutlineParams ¶ms) {
|
||||
SharedPtr<IShader> shader = ShaderManager::getInstance().get("outline");
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to get outline shader");
|
||||
return nullptr;
|
||||
|
|
@ -47,8 +47,8 @@ Ptr<IShader> ShaderPreset::Outline(const OutlineParams ¶ms) {
|
|||
* @param params 扭曲效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
Ptr<IShader> ShaderPreset::Distortion(const DistortionParams ¶ms) {
|
||||
Ptr<IShader> shader = ShaderManager::getInstance().get("distortion");
|
||||
SharedPtr<IShader> ShaderPreset::Distortion(const DistortionParams ¶ms) {
|
||||
SharedPtr<IShader> shader = ShaderManager::getInstance().get("distortion");
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to get distortion shader");
|
||||
return nullptr;
|
||||
|
|
@ -65,8 +65,8 @@ Ptr<IShader> ShaderPreset::Distortion(const DistortionParams ¶ms) {
|
|||
* @param params 像素化效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
Ptr<IShader> ShaderPreset::Pixelate(const PixelateParams ¶ms) {
|
||||
Ptr<IShader> shader = ShaderManager::getInstance().get("pixelate");
|
||||
SharedPtr<IShader> ShaderPreset::Pixelate(const PixelateParams ¶ms) {
|
||||
SharedPtr<IShader> shader = ShaderManager::getInstance().get("pixelate");
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to get pixelate shader");
|
||||
return nullptr;
|
||||
|
|
@ -82,8 +82,8 @@ Ptr<IShader> ShaderPreset::Pixelate(const PixelateParams ¶ms) {
|
|||
* @param params 反相效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
Ptr<IShader> ShaderPreset::Invert(const InvertParams ¶ms) {
|
||||
Ptr<IShader> shader = ShaderManager::getInstance().get("invert");
|
||||
SharedPtr<IShader> ShaderPreset::Invert(const InvertParams ¶ms) {
|
||||
SharedPtr<IShader> shader = ShaderManager::getInstance().get("invert");
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to get invert shader");
|
||||
return nullptr;
|
||||
|
|
@ -99,8 +99,8 @@ Ptr<IShader> ShaderPreset::Invert(const InvertParams ¶ms) {
|
|||
* @param params 灰度效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
Ptr<IShader> ShaderPreset::Grayscale(const GrayscaleParams ¶ms) {
|
||||
Ptr<IShader> shader = ShaderManager::getInstance().get("grayscale");
|
||||
SharedPtr<IShader> ShaderPreset::Grayscale(const GrayscaleParams ¶ms) {
|
||||
SharedPtr<IShader> shader = ShaderManager::getInstance().get("grayscale");
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to get grayscale shader");
|
||||
return nullptr;
|
||||
|
|
@ -116,8 +116,8 @@ Ptr<IShader> ShaderPreset::Grayscale(const GrayscaleParams ¶ms) {
|
|||
* @param params 模糊效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
Ptr<IShader> ShaderPreset::Blur(const BlurParams ¶ms) {
|
||||
Ptr<IShader> shader = ShaderManager::getInstance().get("blur");
|
||||
SharedPtr<IShader> ShaderPreset::Blur(const BlurParams ¶ms) {
|
||||
SharedPtr<IShader> shader = ShaderManager::getInstance().get("blur");
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to get blur shader");
|
||||
return nullptr;
|
||||
|
|
@ -134,13 +134,13 @@ Ptr<IShader> ShaderPreset::Blur(const BlurParams ¶ms) {
|
|||
* @param outlineParams 描边效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
Ptr<IShader>
|
||||
SharedPtr<IShader>
|
||||
ShaderPreset::GrayscaleOutline(const GrayscaleParams &grayParams,
|
||||
const OutlineParams &outlineParams) {
|
||||
std::string shaderDir = ShaderManager::getInstance().getShaderDir();
|
||||
std::string shaderPath = shaderDir + "effects/grayscale_outline.shader";
|
||||
|
||||
Ptr<IShader> shader =
|
||||
SharedPtr<IShader> shader =
|
||||
ShaderManager::getInstance().loadFromCombinedFile(shaderPath);
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to load grayscale_outline shader from: {}",
|
||||
|
|
@ -163,12 +163,12 @@ ShaderPreset::GrayscaleOutline(const GrayscaleParams &grayParams,
|
|||
* @param invParams 反相效果参数
|
||||
* @return 配置好的着色器
|
||||
*/
|
||||
Ptr<IShader> ShaderPreset::PixelateInvert(const PixelateParams &pixParams,
|
||||
SharedPtr<IShader> ShaderPreset::PixelateInvert(const PixelateParams &pixParams,
|
||||
const InvertParams &invParams) {
|
||||
std::string shaderDir = ShaderManager::getInstance().getShaderDir();
|
||||
std::string shaderPath = shaderDir + "effects/pixelate_invert.shader";
|
||||
|
||||
Ptr<IShader> shader =
|
||||
SharedPtr<IShader> shader =
|
||||
ShaderManager::getInstance().loadFromCombinedFile(shaderPath);
|
||||
if (!shader) {
|
||||
E2D_LOG_ERROR("Failed to load pixelate_invert shader from: {}", shaderPath);
|
||||
|
|
|
|||
|
|
@ -27,7 +27,7 @@ Node::~Node() { clearChildren(); }
|
|||
*
|
||||
* 将子节点添加到当前节点的子节点列表中,自动从原父节点分离
|
||||
*/
|
||||
void Node::addChild(Ptr<Node> child) {
|
||||
void Node::addChild(SharedPtr<Node> child) {
|
||||
if (!child || child.get() == this) {
|
||||
return;
|
||||
}
|
||||
|
|
@ -59,7 +59,7 @@ void Node::addChild(Ptr<Node> child) {
|
|||
*
|
||||
* 高效地批量添加多个子节点,预分配内存以减少扩容次数
|
||||
*/
|
||||
void Node::addChildren(std::vector<Ptr<Node>> &&children) {
|
||||
void Node::addChildren(std::vector<SharedPtr<Node>> &&children) {
|
||||
// 预留空间,避免多次扩容
|
||||
size_t newSize = children_.size() + children.size();
|
||||
if (newSize > children_.capacity()) {
|
||||
|
|
@ -102,7 +102,7 @@ void Node::addChildren(std::vector<Ptr<Node>> &&children) {
|
|||
*
|
||||
* 从子节点列表中移除指定节点,并触发相应的退出回调
|
||||
*/
|
||||
void Node::removeChild(Ptr<Node> child) {
|
||||
void Node::removeChild(SharedPtr<Node> child) {
|
||||
if (!child)
|
||||
return;
|
||||
|
||||
|
|
@ -146,7 +146,7 @@ void Node::detach() {
|
|||
auto p = parent_.lock();
|
||||
if (p) {
|
||||
// 安全获取 shared_ptr,避免在对象未由 shared_ptr 管理时崩溃
|
||||
Ptr<Node> self;
|
||||
SharedPtr<Node> self;
|
||||
try {
|
||||
self = shared_from_this();
|
||||
} catch (const std::bad_weak_ptr &) {
|
||||
|
|
@ -183,7 +183,7 @@ void Node::clearChildren() {
|
|||
*
|
||||
* 使用哈希索引进行O(1)时间复杂度查找
|
||||
*/
|
||||
Ptr<Node> Node::findChild(const std::string &name) const {
|
||||
SharedPtr<Node> Node::findChild(const std::string &name) const {
|
||||
// 使用哈希索引,O(1) 查找
|
||||
auto it = nameIndex_.find(name);
|
||||
if (it != nameIndex_.end()) {
|
||||
|
|
@ -199,7 +199,7 @@ Ptr<Node> Node::findChild(const std::string &name) const {
|
|||
*
|
||||
* 使用哈希索引进行O(1)时间复杂度查找
|
||||
*/
|
||||
Ptr<Node> Node::findChildByTag(int tag) const {
|
||||
SharedPtr<Node> Node::findChildByTag(int tag) const {
|
||||
// 使用哈希索引,O(1) 查找
|
||||
auto it = tagIndex_.find(tag);
|
||||
if (it != tagIndex_.end()) {
|
||||
|
|
@ -617,7 +617,7 @@ void Node::sortChildren() {
|
|||
} else {
|
||||
// 大数组使用标准排序
|
||||
std::sort(children_.begin(), children_.end(),
|
||||
[](const Ptr<Node> &a, const Ptr<Node> &b) {
|
||||
[](const SharedPtr<Node> &a, const SharedPtr<Node> &b) {
|
||||
return a->getZOrder() < b->getZOrder();
|
||||
});
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,13 +10,13 @@ namespace extra2d {
|
|||
*
|
||||
* 创建默认相机实例
|
||||
*/
|
||||
Scene::Scene() { defaultCamera_ = makePtr<Camera>(); }
|
||||
Scene::Scene() { defaultCamera_ = makeShared<Camera>(); }
|
||||
|
||||
/**
|
||||
* @brief 设置场景相机
|
||||
* @param camera 要设置的相机智能指针
|
||||
*/
|
||||
void Scene::setCamera(Ptr<Camera> camera) { camera_ = camera; }
|
||||
void Scene::setCamera(SharedPtr<Camera> camera) { camera_ = camera; }
|
||||
|
||||
/**
|
||||
* @brief 设置视口大小
|
||||
|
|
@ -122,6 +122,6 @@ void Scene::collectRenderCommands(std::vector<RenderCommand> &commands,
|
|||
* @brief 创建场景对象
|
||||
* @return 新创建的场景智能指针
|
||||
*/
|
||||
Ptr<Scene> Scene::create() { return makePtr<Scene>(); }
|
||||
SharedPtr<Scene> Scene::create() { return makeShared<Scene>(); }
|
||||
|
||||
} // namespace extra2d
|
||||
|
|
|
|||
|
|
@ -16,14 +16,14 @@ namespace {
|
|||
* @param worldPos 世界坐标位置
|
||||
* @return 命中的节点指针,未命中返回nullptr
|
||||
*/
|
||||
Node *hitTestTopmost(const Ptr<Node> &node, const Vec2 &worldPos) {
|
||||
Node *hitTestTopmost(const SharedPtr<Node> &node, const Vec2 &worldPos) {
|
||||
if (!node || !node->isVisible()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
std::vector<Ptr<Node>> children = node->getChildren();
|
||||
std::vector<SharedPtr<Node>> children = node->getChildren();
|
||||
std::stable_sort(children.begin(), children.end(),
|
||||
[](const Ptr<Node> &a, const Ptr<Node> &b) {
|
||||
[](const SharedPtr<Node> &a, const SharedPtr<Node> &b) {
|
||||
return a->getZOrder() < b->getZOrder();
|
||||
});
|
||||
|
||||
|
|
@ -74,7 +74,7 @@ SceneManager &SceneManager::get() {
|
|||
*
|
||||
* 此方法应在应用启动时调用一次,设置初始场景
|
||||
*/
|
||||
void SceneManager::runWithScene(Ptr<Scene> scene) {
|
||||
void SceneManager::runWithScene(SharedPtr<Scene> scene) {
|
||||
if (!scene) {
|
||||
return;
|
||||
}
|
||||
|
|
@ -95,7 +95,7 @@ void SceneManager::runWithScene(Ptr<Scene> scene) {
|
|||
*
|
||||
* 移除当前场景并替换为新场景,场景栈大小保持不变
|
||||
*/
|
||||
void SceneManager::replaceScene(Ptr<Scene> scene) {
|
||||
void SceneManager::replaceScene(SharedPtr<Scene> scene) {
|
||||
if (!scene || isTransitioning_) {
|
||||
return;
|
||||
}
|
||||
|
|
@ -121,7 +121,7 @@ void SceneManager::replaceScene(Ptr<Scene> scene) {
|
|||
*
|
||||
* 如果场景栈为空则运行场景,否则替换当前场景
|
||||
*/
|
||||
void SceneManager::enterScene(Ptr<Scene> scene) {
|
||||
void SceneManager::enterScene(SharedPtr<Scene> scene) {
|
||||
if (!scene || isTransitioning_) {
|
||||
return;
|
||||
}
|
||||
|
|
@ -139,7 +139,7 @@ void SceneManager::enterScene(Ptr<Scene> scene) {
|
|||
*
|
||||
* 将新场景压入栈顶,暂停当前场景
|
||||
*/
|
||||
void SceneManager::pushScene(Ptr<Scene> scene) {
|
||||
void SceneManager::pushScene(SharedPtr<Scene> scene) {
|
||||
if (!scene || isTransitioning_) {
|
||||
return;
|
||||
}
|
||||
|
|
@ -204,8 +204,8 @@ void SceneManager::popToScene(const std::string &name) {
|
|||
return;
|
||||
}
|
||||
|
||||
std::stack<Ptr<Scene>> tempStack;
|
||||
Ptr<Scene> target = nullptr;
|
||||
std::stack<SharedPtr<Scene>> tempStack;
|
||||
SharedPtr<Scene> target = nullptr;
|
||||
|
||||
while (!sceneStack_.empty()) {
|
||||
auto scene = sceneStack_.top();
|
||||
|
|
@ -227,7 +227,7 @@ void SceneManager::popToScene(const std::string &name) {
|
|||
* @brief 获取当前场景
|
||||
* @return 当前栈顶场景的智能指针,栈为空时返回nullptr
|
||||
*/
|
||||
Ptr<Scene> SceneManager::getCurrentScene() const {
|
||||
SharedPtr<Scene> SceneManager::getCurrentScene() const {
|
||||
if (sceneStack_.empty()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
|
@ -238,7 +238,7 @@ Ptr<Scene> SceneManager::getCurrentScene() const {
|
|||
* @brief 获取前一个场景
|
||||
* @return 栈顶下一个场景的智能指针,不存在时返回nullptr
|
||||
*/
|
||||
Ptr<Scene> SceneManager::getPreviousScene() const {
|
||||
SharedPtr<Scene> SceneManager::getPreviousScene() const {
|
||||
if (sceneStack_.size() < 2) {
|
||||
return nullptr;
|
||||
}
|
||||
|
|
@ -252,13 +252,13 @@ Ptr<Scene> SceneManager::getPreviousScene() const {
|
|||
* @brief 获取根场景
|
||||
* @return 栈底场景的智能指针,栈为空时返回nullptr
|
||||
*/
|
||||
Ptr<Scene> SceneManager::getRootScene() const {
|
||||
SharedPtr<Scene> SceneManager::getRootScene() const {
|
||||
if (sceneStack_.empty()) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
auto tempStack = sceneStack_;
|
||||
Ptr<Scene> root;
|
||||
SharedPtr<Scene> root;
|
||||
while (!tempStack.empty()) {
|
||||
root = tempStack.top();
|
||||
tempStack.pop();
|
||||
|
|
@ -271,7 +271,7 @@ Ptr<Scene> SceneManager::getRootScene() const {
|
|||
* @param name 场景名称
|
||||
* @return 找到的场景智能指针,未找到返回nullptr
|
||||
*/
|
||||
Ptr<Scene> SceneManager::getSceneByName(const std::string &name) const {
|
||||
SharedPtr<Scene> SceneManager::getSceneByName(const std::string &name) const {
|
||||
auto it = namedScenes_.find(name);
|
||||
if (it != namedScenes_.end()) {
|
||||
return it->second;
|
||||
|
|
@ -396,7 +396,7 @@ void SceneManager::dispatchPointerEvents(Scene &scene) {
|
|||
worldPos = camera->screenToWorld(screenPos);
|
||||
}
|
||||
|
||||
Ptr<Node> root = scene.shared_from_this();
|
||||
SharedPtr<Node> root = scene.shared_from_this();
|
||||
Node *newHover = hitTestTopmost(root, worldPos);
|
||||
|
||||
if (newHover != hoverTarget_) {
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ ShapeNode::ShapeNode() = default;
|
|||
* @brief 创建空的形状节点
|
||||
* @return 新创建的形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::create() { return makePtr<ShapeNode>(); }
|
||||
SharedPtr<ShapeNode> ShapeNode::create() { return makeShared<ShapeNode>(); }
|
||||
|
||||
/**
|
||||
* @brief 创建点形状节点
|
||||
|
|
@ -26,8 +26,8 @@ Ptr<ShapeNode> ShapeNode::create() { return makePtr<ShapeNode>(); }
|
|||
* @param color 点的颜色
|
||||
* @return 新创建的点形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createPoint(const Vec2 &pos, const Color &color) {
|
||||
auto node = makePtr<ShapeNode>();
|
||||
SharedPtr<ShapeNode> ShapeNode::createPoint(const Vec2 &pos, const Color &color) {
|
||||
auto node = makeShared<ShapeNode>();
|
||||
node->shapeType_ = ShapeType::Point;
|
||||
node->color_ = color;
|
||||
node->points_ = {pos};
|
||||
|
|
@ -42,9 +42,9 @@ Ptr<ShapeNode> ShapeNode::createPoint(const Vec2 &pos, const Color &color) {
|
|||
* @param width 线段宽度
|
||||
* @return 新创建的线段形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createLine(const Vec2 &start, const Vec2 &end,
|
||||
SharedPtr<ShapeNode> ShapeNode::createLine(const Vec2 &start, const Vec2 &end,
|
||||
const Color &color, float width) {
|
||||
auto node = makePtr<ShapeNode>();
|
||||
auto node = makeShared<ShapeNode>();
|
||||
node->shapeType_ = ShapeType::Line;
|
||||
node->color_ = color;
|
||||
node->lineWidth_ = width;
|
||||
|
|
@ -59,9 +59,9 @@ Ptr<ShapeNode> ShapeNode::createLine(const Vec2 &start, const Vec2 &end,
|
|||
* @param width 边框线宽
|
||||
* @return 新创建的矩形形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createRect(const Rect &rect, const Color &color,
|
||||
SharedPtr<ShapeNode> ShapeNode::createRect(const Rect &rect, const Color &color,
|
||||
float width) {
|
||||
auto node = makePtr<ShapeNode>();
|
||||
auto node = makeShared<ShapeNode>();
|
||||
node->shapeType_ = ShapeType::Rect;
|
||||
node->color_ = color;
|
||||
node->lineWidth_ = width;
|
||||
|
|
@ -78,7 +78,7 @@ Ptr<ShapeNode> ShapeNode::createRect(const Rect &rect, const Color &color,
|
|||
* @param color 矩形填充颜色
|
||||
* @return 新创建的填充矩形形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createFilledRect(const Rect &rect,
|
||||
SharedPtr<ShapeNode> ShapeNode::createFilledRect(const Rect &rect,
|
||||
const Color &color) {
|
||||
auto node = createRect(rect, color, 0);
|
||||
node->filled_ = true;
|
||||
|
|
@ -94,17 +94,16 @@ Ptr<ShapeNode> ShapeNode::createFilledRect(const Rect &rect,
|
|||
* @param width 边框线宽
|
||||
* @return 新创建的圆形形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createCircle(const Vec2 ¢er, float radius,
|
||||
SharedPtr<ShapeNode> ShapeNode::createCircle(const Vec2 ¢er, float radius,
|
||||
const Color &color, int segments,
|
||||
float width) {
|
||||
auto node = makePtr<ShapeNode>();
|
||||
auto node = makeShared<ShapeNode>();
|
||||
node->shapeType_ = ShapeType::Circle;
|
||||
node->color_ = color;
|
||||
node->lineWidth_ = width;
|
||||
node->segments_ = segments;
|
||||
node->filled_ = false;
|
||||
node->points_ = {center};
|
||||
// Store radius in a point for simplicity
|
||||
node->addPoint(Vec2(radius, 0));
|
||||
return node;
|
||||
}
|
||||
|
|
@ -117,7 +116,7 @@ Ptr<ShapeNode> ShapeNode::createCircle(const Vec2 ¢er, float radius,
|
|||
* @param segments 圆的分段数(边数)
|
||||
* @return 新创建的填充圆形形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createFilledCircle(const Vec2 ¢er, float radius,
|
||||
SharedPtr<ShapeNode> ShapeNode::createFilledCircle(const Vec2 ¢er, float radius,
|
||||
const Color &color, int segments) {
|
||||
auto node = createCircle(center, radius, color, segments, 0);
|
||||
node->filled_ = true;
|
||||
|
|
@ -133,10 +132,10 @@ Ptr<ShapeNode> ShapeNode::createFilledCircle(const Vec2 ¢er, float radius,
|
|||
* @param width 边框线宽
|
||||
* @return 新创建的三角形形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createTriangle(const Vec2 &p1, const Vec2 &p2,
|
||||
SharedPtr<ShapeNode> ShapeNode::createTriangle(const Vec2 &p1, const Vec2 &p2,
|
||||
const Vec2 &p3, const Color &color,
|
||||
float width) {
|
||||
auto node = makePtr<ShapeNode>();
|
||||
auto node = makeShared<ShapeNode>();
|
||||
node->shapeType_ = ShapeType::Triangle;
|
||||
node->color_ = color;
|
||||
node->lineWidth_ = width;
|
||||
|
|
@ -153,7 +152,7 @@ Ptr<ShapeNode> ShapeNode::createTriangle(const Vec2 &p1, const Vec2 &p2,
|
|||
* @param color 三角形填充颜色
|
||||
* @return 新创建的填充三角形形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createFilledTriangle(const Vec2 &p1, const Vec2 &p2,
|
||||
SharedPtr<ShapeNode> ShapeNode::createFilledTriangle(const Vec2 &p1, const Vec2 &p2,
|
||||
const Vec2 &p3,
|
||||
const Color &color) {
|
||||
auto node = createTriangle(p1, p2, p3, color, 0);
|
||||
|
|
@ -168,9 +167,9 @@ Ptr<ShapeNode> ShapeNode::createFilledTriangle(const Vec2 &p1, const Vec2 &p2,
|
|||
* @param width 边框线宽
|
||||
* @return 新创建的多边形形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createPolygon(const std::vector<Vec2> &points,
|
||||
SharedPtr<ShapeNode> ShapeNode::createPolygon(const std::vector<Vec2> &points,
|
||||
const Color &color, float width) {
|
||||
auto node = makePtr<ShapeNode>();
|
||||
auto node = makeShared<ShapeNode>();
|
||||
node->shapeType_ = ShapeType::Polygon;
|
||||
node->color_ = color;
|
||||
node->lineWidth_ = width;
|
||||
|
|
@ -185,7 +184,7 @@ Ptr<ShapeNode> ShapeNode::createPolygon(const std::vector<Vec2> &points,
|
|||
* @param color 多边形填充颜色
|
||||
* @return 新创建的填充多边形形状节点智能指针
|
||||
*/
|
||||
Ptr<ShapeNode> ShapeNode::createFilledPolygon(const std::vector<Vec2> &points,
|
||||
SharedPtr<ShapeNode> ShapeNode::createFilledPolygon(const std::vector<Vec2> &points,
|
||||
const Color &color) {
|
||||
auto node = createPolygon(points, color, 0);
|
||||
node->filled_ = true;
|
||||
|
|
@ -444,4 +443,4 @@ void ShapeNode::generateRenderCommand(std::vector<RenderCommand> &commands,
|
|||
commands.push_back(std::move(cmd));
|
||||
}
|
||||
|
||||
} // namespace extra2d
|
||||
}
|
||||
|
|
|
|||
|
|
@ -68,15 +68,15 @@ void Sprite::setFlipY(bool flip) { flipY_ = flip; }
|
|||
* @brief 创建空精灵
|
||||
* @return 新创建的精灵智能指针
|
||||
*/
|
||||
Ptr<Sprite> Sprite::create() { return makePtr<Sprite>(); }
|
||||
SharedPtr<Sprite> Sprite::create() { return makeShared<Sprite>(); }
|
||||
|
||||
/**
|
||||
* @brief 创建带纹理的精灵
|
||||
* @param texture 精灵使用的纹理
|
||||
* @return 新创建的精灵智能指针
|
||||
*/
|
||||
Ptr<Sprite> Sprite::create(Ptr<Texture> texture) {
|
||||
return makePtr<Sprite>(texture);
|
||||
SharedPtr<Sprite> Sprite::create(Ptr<Texture> texture) {
|
||||
return makeShared<Sprite>(texture);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
@ -85,8 +85,8 @@ Ptr<Sprite> Sprite::create(Ptr<Texture> texture) {
|
|||
* @param rect 纹理区域
|
||||
* @return 新创建的精灵智能指针
|
||||
*/
|
||||
Ptr<Sprite> Sprite::create(Ptr<Texture> texture, const Rect &rect) {
|
||||
auto sprite = makePtr<Sprite>(texture);
|
||||
SharedPtr<Sprite> Sprite::create(Ptr<Texture> texture, const Rect &rect) {
|
||||
auto sprite = makeShared<Sprite>(texture);
|
||||
sprite->setTextureRect(rect);
|
||||
return sprite;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -28,15 +28,15 @@ void SceneService::update(float deltaTime) {
|
|||
}
|
||||
}
|
||||
|
||||
void SceneService::runWithScene(Ptr<Scene> scene) {
|
||||
void SceneService::runWithScene(SharedPtr<Scene> scene) {
|
||||
manager_.runWithScene(scene);
|
||||
}
|
||||
|
||||
void SceneService::replaceScene(Ptr<Scene> scene) {
|
||||
void SceneService::replaceScene(SharedPtr<Scene> scene) {
|
||||
manager_.replaceScene(scene);
|
||||
}
|
||||
|
||||
void SceneService::pushScene(Ptr<Scene> scene) {
|
||||
void SceneService::pushScene(SharedPtr<Scene> scene) {
|
||||
manager_.pushScene(scene);
|
||||
}
|
||||
|
||||
|
|
@ -52,19 +52,19 @@ void SceneService::popToScene(const std::string& name) {
|
|||
manager_.popToScene(name);
|
||||
}
|
||||
|
||||
Ptr<Scene> SceneService::getCurrentScene() const {
|
||||
SharedPtr<Scene> SceneService::getCurrentScene() const {
|
||||
return manager_.getCurrentScene();
|
||||
}
|
||||
|
||||
Ptr<Scene> SceneService::getPreviousScene() const {
|
||||
SharedPtr<Scene> SceneService::getPreviousScene() const {
|
||||
return manager_.getPreviousScene();
|
||||
}
|
||||
|
||||
Ptr<Scene> SceneService::getRootScene() const {
|
||||
SharedPtr<Scene> SceneService::getRootScene() const {
|
||||
return manager_.getRootScene();
|
||||
}
|
||||
|
||||
Ptr<Scene> SceneService::getSceneByName(const std::string& name) const {
|
||||
SharedPtr<Scene> SceneService::getSceneByName(const std::string& name) const {
|
||||
return manager_.getSceneByName(name);
|
||||
}
|
||||
|
||||
|
|
@ -104,7 +104,7 @@ void SceneService::purgeCachedScenes() {
|
|||
manager_.purgeCachedScenes();
|
||||
}
|
||||
|
||||
void SceneService::enterScene(Ptr<Scene> scene) {
|
||||
void SceneService::enterScene(SharedPtr<Scene> scene) {
|
||||
manager_.enterScene(scene);
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue