计时功能优化
This commit is contained in:
parent
d1ad592df7
commit
c7115a1162
|
|
@ -6,7 +6,6 @@ e2d::Action::Action()
|
||||||
, _done(false)
|
, _done(false)
|
||||||
, _initialized(false)
|
, _initialized(false)
|
||||||
, _target(nullptr)
|
, _target(nullptr)
|
||||||
, _last(0)
|
|
||||||
{
|
{
|
||||||
ActionManager::getInstance()->__add(this);
|
ActionManager::getInstance()->__add(this);
|
||||||
}
|
}
|
||||||
|
|
@ -24,7 +23,6 @@ bool e2d::Action::isRunning()
|
||||||
void e2d::Action::resume()
|
void e2d::Action::resume()
|
||||||
{
|
{
|
||||||
_running = true;
|
_running = true;
|
||||||
_last = Game::getInstance()->getTotalDuration().seconds();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::Action::pause()
|
void e2d::Action::pause()
|
||||||
|
|
@ -56,7 +54,7 @@ void e2d::Action::reset()
|
||||||
{
|
{
|
||||||
_initialized = false;
|
_initialized = false;
|
||||||
_done = false;
|
_done = false;
|
||||||
_last = Game::getInstance()->getTotalDuration().seconds();
|
_started = Time::now();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool e2d::Action::_isDone()
|
bool e2d::Action::_isDone()
|
||||||
|
|
@ -74,7 +72,7 @@ void e2d::Action::_startWithTarget(Node* target)
|
||||||
void e2d::Action::_init()
|
void e2d::Action::_init()
|
||||||
{
|
{
|
||||||
_initialized = true;
|
_initialized = true;
|
||||||
_last = Game::getInstance()->getTotalDuration().seconds();
|
_started = Time::now();
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::Action::_update()
|
void e2d::Action::_update()
|
||||||
|
|
|
||||||
|
|
@ -56,8 +56,7 @@ void e2d::Animate::_update()
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto game = Game::getInstance();
|
while ((Time::now() - _started).seconds() >= _animation->getInterval())
|
||||||
while ((game->getTotalDuration().seconds() - _last) >= _animation->getInterval())
|
|
||||||
{
|
{
|
||||||
auto& frames = _animation->getFrames();
|
auto& frames = _animation->getFrames();
|
||||||
auto target = dynamic_cast<Sprite*>(_target);
|
auto target = dynamic_cast<Sprite*>(_target);
|
||||||
|
|
@ -67,7 +66,7 @@ void e2d::Animate::_update()
|
||||||
target->open(frames[_frameIndex]);
|
target->open(frames[_frameIndex]);
|
||||||
}
|
}
|
||||||
|
|
||||||
_last += _animation->getInterval();
|
_started += Duration(_animation->getInterval());
|
||||||
++_frameIndex;
|
++_frameIndex;
|
||||||
|
|
||||||
if (_frameIndex == frames.size())
|
if (_frameIndex == frames.size())
|
||||||
|
|
@ -81,7 +80,6 @@ void e2d::Animate::_update()
|
||||||
void e2d::Animate::_resetTime()
|
void e2d::Animate::_resetTime()
|
||||||
{
|
{
|
||||||
Action::_resetTime();
|
Action::_resetTime();
|
||||||
_last = Game::getInstance()->getTotalDuration().seconds();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::Animate::reset()
|
void e2d::Animate::reset()
|
||||||
|
|
|
||||||
|
|
@ -31,7 +31,7 @@ void e2d::Delay::_update()
|
||||||
{
|
{
|
||||||
Action::_update();
|
Action::_update();
|
||||||
|
|
||||||
_delta = Game::getInstance()->getTotalDuration().seconds() - _last;
|
_delta = (Time::now() - _started).seconds();
|
||||||
|
|
||||||
if (_delta >= _delay)
|
if (_delta >= _delay)
|
||||||
{
|
{
|
||||||
|
|
@ -42,5 +42,5 @@ void e2d::Delay::_update()
|
||||||
void e2d::Delay::_resetTime()
|
void e2d::Delay::_resetTime()
|
||||||
{
|
{
|
||||||
Action::_resetTime();
|
Action::_resetTime();
|
||||||
_last = Game::getInstance()->getTotalDuration().seconds() - _delta;
|
_started = Time::now() - Duration(_delta);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -28,7 +28,7 @@ void e2d::FiniteTimeAction::_update()
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
_delta = std::min((Game::getInstance()->getTotalDuration().seconds() - _last) / _duration, 1.f);
|
_delta = std::min((Time::now() - _started).seconds() / _duration, 1.f);
|
||||||
|
|
||||||
if (_delta >= 1)
|
if (_delta >= 1)
|
||||||
{
|
{
|
||||||
|
|
@ -40,5 +40,5 @@ void e2d::FiniteTimeAction::_update()
|
||||||
void e2d::FiniteTimeAction::_resetTime()
|
void e2d::FiniteTimeAction::_resetTime()
|
||||||
{
|
{
|
||||||
Action::_resetTime();
|
Action::_resetTime();
|
||||||
_last = Game::getInstance()->getTotalDuration().seconds() - _delta * _duration;
|
_started = Time::now() - Duration(_delta * _duration);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -12,8 +12,6 @@ e2d::Game::Game()
|
||||||
, _config()
|
, _config()
|
||||||
{
|
{
|
||||||
CoInitialize(nullptr);
|
CoInitialize(nullptr);
|
||||||
|
|
||||||
_start = _last = _now = Time::now();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::Game::~Game()
|
e2d::Game::~Game()
|
||||||
|
|
@ -39,26 +37,25 @@ void e2d::Game::destroyInstance()
|
||||||
|
|
||||||
void e2d::Game::start()
|
void e2d::Game::start()
|
||||||
{
|
{
|
||||||
SceneManager::getInstance()->update();
|
_quit = false;
|
||||||
|
|
||||||
|
const int minInterval = 5;
|
||||||
|
Time last = Time::now();
|
||||||
HWND hWnd = Window::getInstance()->getHWnd();
|
HWND hWnd = Window::getInstance()->getHWnd();
|
||||||
|
|
||||||
::ShowWindow(hWnd, SW_SHOWNORMAL);
|
::ShowWindow(hWnd, SW_SHOWNORMAL);
|
||||||
::UpdateWindow(hWnd);
|
::UpdateWindow(hWnd);
|
||||||
Window::getInstance()->poll();
|
Window::getInstance()->poll();
|
||||||
|
SceneManager::getInstance()->update();
|
||||||
_quit = false;
|
|
||||||
_last = _now = Time::now();
|
|
||||||
|
|
||||||
const Duration minInterval(15);
|
|
||||||
|
|
||||||
while (!_quit)
|
while (!_quit)
|
||||||
{
|
{
|
||||||
_now = Time::now();
|
auto now = Time::now();
|
||||||
Duration interval = _now - _last;
|
auto dur = now - last;
|
||||||
|
|
||||||
if (minInterval < interval)
|
if (dur.milliseconds() > minInterval)
|
||||||
{
|
{
|
||||||
_last = _now;
|
last = now;
|
||||||
Input::getInstance()->update();
|
Input::getInstance()->update();
|
||||||
Timer::getInstance()->update();
|
Timer::getInstance()->update();
|
||||||
ActionManager::getInstance()->update();
|
ActionManager::getInstance()->update();
|
||||||
|
|
@ -72,7 +69,7 @@ void e2d::Game::start()
|
||||||
// ID2D1HwndRenderTarget 在渲染时会等待显示器刷新,即开启了垂直同步,
|
// ID2D1HwndRenderTarget 在渲染时会等待显示器刷新,即开启了垂直同步,
|
||||||
// 它起到了非常稳定的延时作用,所以大部分时候不需要手动挂起线程进行延时。
|
// 它起到了非常稳定的延时作用,所以大部分时候不需要手动挂起线程进行延时。
|
||||||
// 下面的代码仅在一些情况下(例如窗口最小化时)挂起线程,防止占用过高 CPU 。
|
// 下面的代码仅在一些情况下(例如窗口最小化时)挂起线程,防止占用过高 CPU 。
|
||||||
int wait = (minInterval - interval).milliseconds();
|
int wait = minInterval - dur.milliseconds();
|
||||||
if (wait > 1)
|
if (wait > 1)
|
||||||
{
|
{
|
||||||
std::this_thread::sleep_for(std::chrono::milliseconds(wait));
|
std::this_thread::sleep_for(std::chrono::milliseconds(wait));
|
||||||
|
|
@ -90,7 +87,6 @@ void e2d::Game::resume()
|
||||||
{
|
{
|
||||||
if (_paused && !_quit)
|
if (_paused && !_quit)
|
||||||
{
|
{
|
||||||
_last = _now = Time::now();
|
|
||||||
Timer::getInstance()->updateTime();
|
Timer::getInstance()->updateTime();
|
||||||
ActionManager::getInstance()->updateTime();
|
ActionManager::getInstance()->updateTime();
|
||||||
}
|
}
|
||||||
|
|
@ -120,11 +116,6 @@ const e2d::Config& e2d::Game::getConfig()
|
||||||
return _config;
|
return _config;
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::Duration e2d::Game::getTotalDuration() const
|
|
||||||
{
|
|
||||||
return std::move(_now - _start);
|
|
||||||
}
|
|
||||||
|
|
||||||
void e2d::Game::quit()
|
void e2d::Game::quit()
|
||||||
{
|
{
|
||||||
_quit = true;
|
_quit = true;
|
||||||
|
|
|
||||||
|
|
@ -107,15 +107,14 @@ void e2d::Renderer::render()
|
||||||
|
|
||||||
void e2d::Renderer::_renderFps()
|
void e2d::Renderer::_renderFps()
|
||||||
{
|
{
|
||||||
++_renderTimes;
|
int duration = (Time::now() - _lastRenderTime).milliseconds();
|
||||||
|
|
||||||
auto& now = Time::now();
|
++_renderTimes;
|
||||||
int duration = (now - _lastRenderTime).milliseconds();
|
|
||||||
if (duration >= 100)
|
if (duration >= 100)
|
||||||
{
|
{
|
||||||
String fpsText = String::format(L"FPS: %.1f", (1000.f / duration * _renderTimes));
|
String fpsText = String::format(L"FPS: %.1f", (1000.f / duration * _renderTimes));
|
||||||
_renderTimes = 0;
|
_lastRenderTime = Time::now();
|
||||||
_lastRenderTime = now;
|
_renderTimes = 0;
|
||||||
|
|
||||||
auto writeFactory = Renderer::getWriteFactory();
|
auto writeFactory = Renderer::getWriteFactory();
|
||||||
if (!_fpsFormat)
|
if (!_fpsFormat)
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,9 @@
|
||||||
#include <imm.h>
|
#include <imm.h>
|
||||||
#pragma comment (lib ,"imm32.lib")
|
#pragma comment (lib ,"imm32.lib")
|
||||||
|
|
||||||
|
#define WINDOW_STYLE WS_OVERLAPPEDWINDOW & ~WS_MAXIMIZEBOX & ~WS_THICKFRAME
|
||||||
|
#define REGISTER_CLASS L"Easy2DApp"
|
||||||
|
|
||||||
|
|
||||||
e2d::Window * e2d::Window::_instance = nullptr;
|
e2d::Window * e2d::Window::_instance = nullptr;
|
||||||
|
|
||||||
|
|
@ -51,9 +54,7 @@ bool e2d::Window::createMutex(const String & mutex)
|
||||||
if (mutex.isEmpty())
|
if (mutex.isEmpty())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
// 创建进程互斥体
|
HANDLE hMutex = ::CreateMutex(nullptr, TRUE, LPCWSTR(L"Easy2DApp-" + mutex));
|
||||||
String fullMutexName = L"Easy2DApp-" + mutex;
|
|
||||||
HANDLE hMutex = ::CreateMutex(nullptr, TRUE, (LPCWSTR)fullMutexName);
|
|
||||||
|
|
||||||
if (hMutex == nullptr)
|
if (hMutex == nullptr)
|
||||||
{
|
{
|
||||||
|
|
@ -68,7 +69,7 @@ bool e2d::Window::createMutex(const String & mutex)
|
||||||
if (!this->_title.isEmpty())
|
if (!this->_title.isEmpty())
|
||||||
{
|
{
|
||||||
// 获取窗口句柄
|
// 获取窗口句柄
|
||||||
HWND hProgramWnd = ::FindWindow(L"Easy2DApp", (LPCTSTR)this->_title);
|
HWND hProgramWnd = ::FindWindow(REGISTER_CLASS, (LPCTSTR)_title);
|
||||||
if (hProgramWnd)
|
if (hProgramWnd)
|
||||||
{
|
{
|
||||||
// 获取窗口显示状态
|
// 获取窗口显示状态
|
||||||
|
|
@ -85,79 +86,59 @@ bool e2d::Window::createMutex(const String & mutex)
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
HWND e2d::Window::__create()
|
HWND e2d::Window::__registerWindow()
|
||||||
{
|
{
|
||||||
// 注册窗口类
|
|
||||||
WNDCLASSEX wcex = { 0 };
|
WNDCLASSEX wcex = { 0 };
|
||||||
wcex.cbSize = sizeof(WNDCLASSEX);
|
wcex.cbSize = sizeof(WNDCLASSEX);
|
||||||
wcex.lpszClassName = L"Easy2DApp";
|
wcex.lpszClassName = REGISTER_CLASS;
|
||||||
wcex.style = CS_HREDRAW | CS_VREDRAW | CS_DBLCLKS;
|
wcex.style = CS_HREDRAW | CS_VREDRAW | CS_DBLCLKS;
|
||||||
wcex.lpfnWndProc = Window::WndProc;
|
wcex.lpfnWndProc = Window::WndProc;
|
||||||
wcex.cbClsExtra = 0;
|
wcex.hIcon = nullptr;
|
||||||
wcex.cbWndExtra = sizeof(LONG_PTR);
|
wcex.cbClsExtra = 0;
|
||||||
wcex.hInstance = HINST_THISCOMPONENT;
|
wcex.cbWndExtra = sizeof(LONG_PTR);
|
||||||
wcex.hbrBackground = nullptr;
|
wcex.hInstance = HINST_THISCOMPONENT;
|
||||||
wcex.lpszMenuName = nullptr;
|
wcex.hbrBackground = nullptr;
|
||||||
wcex.hCursor = ::LoadCursor(nullptr, IDC_ARROW);
|
wcex.lpszMenuName = nullptr;
|
||||||
|
wcex.hCursor = ::LoadCursor(nullptr, IDC_ARROW);
|
||||||
|
|
||||||
if (this->_iconID != 0)
|
if (_iconID != 0)
|
||||||
{
|
{
|
||||||
wcex.hIcon = (HICON)::LoadImage(
|
wcex.hIcon = (HICON)::LoadImage(
|
||||||
HINST_THISCOMPONENT,
|
HINST_THISCOMPONENT,
|
||||||
MAKEINTRESOURCE(this->_iconID),
|
MAKEINTRESOURCE(_iconID),
|
||||||
IMAGE_ICON,
|
IMAGE_ICON,
|
||||||
0,
|
0,
|
||||||
0,
|
0,
|
||||||
LR_DEFAULTCOLOR | LR_CREATEDIBSECTION | LR_DEFAULTSIZE
|
LR_DEFAULTCOLOR | LR_CREATEDIBSECTION | LR_DEFAULTSIZE
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
|
||||||
wcex.hIcon = nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
// 注册窗口类
|
||||||
RegisterClassEx(&wcex);
|
RegisterClassEx(&wcex);
|
||||||
|
|
||||||
// 因为 CreateWindow 函数使用的是像素大小,获取系统的 DPI 以使它
|
|
||||||
// 适应窗口缩放
|
|
||||||
float dpiScaleX = 0.f, dpiScaleY = 0.f;
|
|
||||||
Renderer::getFactory()->GetDesktopDpi(&dpiScaleX, &dpiScaleY);
|
|
||||||
|
|
||||||
int nWidth = static_cast<int>(ceil(_size.width * dpiScaleX / 96.f));
|
|
||||||
int nHeight = static_cast<int>(ceil(_size.height * dpiScaleY / 96.f));
|
|
||||||
|
|
||||||
// 计算窗口大小
|
// 计算窗口大小
|
||||||
DWORD dwStyle = WS_OVERLAPPEDWINDOW & ~WS_MAXIMIZEBOX & ~WS_THICKFRAME;
|
Rect wRect = __adjustWindow(int(_size.width), int(_size.height));
|
||||||
RECT wr = { 0, 0, static_cast<LONG>(nWidth), static_cast<LONG>(nHeight) };
|
|
||||||
::AdjustWindowRectEx(&wr, dwStyle, FALSE, NULL);
|
|
||||||
// 获取新的宽高
|
|
||||||
nWidth = static_cast<int>(wr.right - wr.left);
|
|
||||||
nHeight = static_cast<int>(wr.bottom - wr.top);
|
|
||||||
|
|
||||||
// 获取屏幕分辨率
|
|
||||||
int screenWidth = ::GetSystemMetrics(SM_CXSCREEN);
|
|
||||||
int screenHeight = ::GetSystemMetrics(SM_CYSCREEN);
|
|
||||||
|
|
||||||
// 创建窗口
|
// 创建窗口
|
||||||
HWND hWnd = ::CreateWindowEx(
|
HWND hWnd = ::CreateWindowEx(
|
||||||
NULL,
|
NULL,
|
||||||
L"Easy2DApp",
|
REGISTER_CLASS,
|
||||||
(LPCTSTR)_title,
|
(LPCTSTR)_title,
|
||||||
dwStyle,
|
WINDOW_STYLE,
|
||||||
(screenWidth - nWidth) / 2, (screenHeight - nHeight) / 2,
|
int(wRect.origin.x),
|
||||||
nWidth, nHeight,
|
int(wRect.origin.y),
|
||||||
|
int(wRect.size.width),
|
||||||
|
int(wRect.size.height),
|
||||||
nullptr,
|
nullptr,
|
||||||
nullptr,
|
nullptr,
|
||||||
HINST_THISCOMPONENT,
|
HINST_THISCOMPONENT,
|
||||||
nullptr
|
nullptr
|
||||||
);
|
);
|
||||||
|
|
||||||
HRESULT hr = hWnd ? S_OK : E_FAIL;
|
if (hWnd)
|
||||||
|
|
||||||
if (SUCCEEDED(hr))
|
|
||||||
{
|
{
|
||||||
// 禁用输入法
|
// 禁用输入法
|
||||||
this->setTypewritingEnabled(false);
|
setTypewritingEnabled(false);
|
||||||
// 禁用控制台关闭按钮
|
// 禁用控制台关闭按钮
|
||||||
HWND consoleHWnd = ::GetConsoleWindow();
|
HWND consoleHWnd = ::GetConsoleWindow();
|
||||||
if (consoleHWnd)
|
if (consoleHWnd)
|
||||||
|
|
@ -170,11 +151,35 @@ HWND e2d::Window::__create()
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
::UnregisterClass(L"Easy2DApp", HINST_THISCOMPONENT);
|
::UnregisterClass(REGISTER_CLASS, HINST_THISCOMPONENT);
|
||||||
}
|
}
|
||||||
return hWnd;
|
return hWnd;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
e2d::Rect e2d::Window::__adjustWindow(int width, int height)
|
||||||
|
{
|
||||||
|
float dpiScaleX = 0.f, dpiScaleY = 0.f;
|
||||||
|
Renderer::getFactory()->GetDesktopDpi(&dpiScaleX, &dpiScaleY);
|
||||||
|
|
||||||
|
Rect result;
|
||||||
|
RECT wRECT = { 0, 0, LONG(ceil(width * dpiScaleX / 96.f)), LONG(ceil(height * dpiScaleY / 96.f)) };
|
||||||
|
int maxWidth = ::GetSystemMetrics(SM_CXSCREEN);
|
||||||
|
int maxHeight = ::GetSystemMetrics(SM_CYSCREEN);
|
||||||
|
|
||||||
|
// 计算合适的窗口大小
|
||||||
|
::AdjustWindowRectEx(&wRECT, WINDOW_STYLE, FALSE, NULL);
|
||||||
|
width = static_cast<int>(wRECT.right - wRECT.left);
|
||||||
|
height = static_cast<int>(wRECT.bottom - wRECT.top);
|
||||||
|
|
||||||
|
// 当输入的窗口大小比分辨率大时,给出警告
|
||||||
|
WARN_IF(maxWidth < width || maxHeight < height, "The window is larger than screen!");
|
||||||
|
width = std::min(width, maxWidth);
|
||||||
|
height = std::min(height, maxHeight);
|
||||||
|
|
||||||
|
float x = float((maxWidth - width) / 2), y = float((maxHeight - height) / 2);
|
||||||
|
return std::move(Rect(x, y, float(width), float(height)));
|
||||||
|
}
|
||||||
|
|
||||||
void e2d::Window::poll()
|
void e2d::Window::poll()
|
||||||
{
|
{
|
||||||
while (::PeekMessage(&_msg, nullptr, 0, 0, PM_REMOVE))
|
while (::PeekMessage(&_msg, nullptr, 0, 0, PM_REMOVE))
|
||||||
|
|
@ -213,7 +218,7 @@ HWND e2d::Window::getHWnd()
|
||||||
{
|
{
|
||||||
if (!_hWnd)
|
if (!_hWnd)
|
||||||
{
|
{
|
||||||
_hWnd = this->__create();
|
_hWnd = __registerWindow();
|
||||||
if (_hWnd == nullptr)
|
if (_hWnd == nullptr)
|
||||||
{
|
{
|
||||||
throw SystemException(L"注册窗口失败");
|
throw SystemException(L"注册窗口失败");
|
||||||
|
|
@ -224,37 +229,24 @@ HWND e2d::Window::getHWnd()
|
||||||
|
|
||||||
void e2d::Window::setSize(int width, int height)
|
void e2d::Window::setSize(int width, int height)
|
||||||
{
|
{
|
||||||
this->_size = Size(static_cast<float>(width), static_cast<float>(height));
|
_size = Size(static_cast<float>(width), static_cast<float>(height));
|
||||||
if (_hWnd)
|
if (_hWnd)
|
||||||
{
|
{
|
||||||
float dpiScaleX = 0.f, dpiScaleY = 0.f;
|
Rect wRect = __adjustWindow(width, height);
|
||||||
Renderer::getFactory()->GetDesktopDpi(&dpiScaleX, &dpiScaleY);
|
::MoveWindow(
|
||||||
|
_hWnd,
|
||||||
width = static_cast<int>(ceil(width * dpiScaleX / 96.f));
|
int(wRect.origin.x),
|
||||||
height = static_cast<int>(ceil(height * dpiScaleY / 96.f));
|
int(wRect.origin.y),
|
||||||
// 计算窗口大小
|
int(wRect.size.width),
|
||||||
DWORD dwStyle = WS_OVERLAPPEDWINDOW & ~WS_MAXIMIZEBOX & ~WS_THICKFRAME;
|
int(wRect.size.height),
|
||||||
RECT wr = { 0, 0, static_cast<LONG>(width), static_cast<LONG>(height) };
|
TRUE
|
||||||
::AdjustWindowRectEx(&wr, dwStyle, FALSE, NULL);
|
);
|
||||||
// 获取新的宽高
|
|
||||||
width = static_cast<int>(wr.right - wr.left);
|
|
||||||
height = static_cast<int>(wr.bottom - wr.top);
|
|
||||||
// 获取屏幕分辨率
|
|
||||||
int screenWidth = ::GetSystemMetrics(SM_CXSCREEN);
|
|
||||||
int screenHeight = ::GetSystemMetrics(SM_CYSCREEN);
|
|
||||||
// 当输入的窗口大小比分辨率大时,给出警告
|
|
||||||
WARN_IF(screenWidth < width || screenHeight < height, "The window is larger than screen!");
|
|
||||||
// 取最小值
|
|
||||||
width = std::min(width, screenWidth);
|
|
||||||
height = std::min(height, screenHeight);
|
|
||||||
// 修改窗口大小,并设置窗口在屏幕居中
|
|
||||||
::MoveWindow(_hWnd, (screenWidth - width) / 2, (screenHeight - height) / 2, width, height, TRUE);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::Window::setTitle(const String& title)
|
void e2d::Window::setTitle(const String& title)
|
||||||
{
|
{
|
||||||
this->_title = title;
|
_title = title;
|
||||||
if (_hWnd)
|
if (_hWnd)
|
||||||
{
|
{
|
||||||
::SetWindowText(_hWnd, (LPCWSTR)title);
|
::SetWindowText(_hWnd, (LPCWSTR)title);
|
||||||
|
|
|
||||||
|
|
@ -7,13 +7,8 @@ e2d::Duration::Duration()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::Duration::Duration(int ms)
|
e2d::Duration::Duration(float seconds)
|
||||||
: _ms(ms)
|
: _ms(static_cast<long long>(seconds * 1000.f))
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
e2d::Duration::Duration(const std::chrono::milliseconds& ms)
|
|
||||||
: _ms(ms)
|
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -59,12 +54,16 @@ bool e2d::Duration::operator<=(const Duration & other) const
|
||||||
|
|
||||||
e2d::Duration e2d::Duration::operator+(Duration const & other) const
|
e2d::Duration e2d::Duration::operator+(Duration const & other) const
|
||||||
{
|
{
|
||||||
return std::move(Duration(_ms + other._ms));
|
Duration d;
|
||||||
|
d._ms = _ms + other._ms;
|
||||||
|
return std::move(d);
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::Duration e2d::Duration::operator-(Duration const & other) const
|
e2d::Duration e2d::Duration::operator-(Duration const & other) const
|
||||||
{
|
{
|
||||||
return std::move(Duration(_ms - other._ms));
|
Duration d;
|
||||||
|
d._ms = _ms - other._ms;
|
||||||
|
return std::move(d);
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::Duration & e2d::Duration::operator+=(Duration const &other)
|
e2d::Duration & e2d::Duration::operator+=(Duration const &other)
|
||||||
|
|
|
||||||
|
|
@ -7,11 +7,6 @@ e2d::Time::Time()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::Time::Time(const steady_clock::time_point& time)
|
|
||||||
: _timePoint(time)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
time_t e2d::Time::getTimeStamp() const
|
time_t e2d::Time::getTimeStamp() const
|
||||||
{
|
{
|
||||||
auto& duration = time_point_cast<milliseconds>(_timePoint).time_since_epoch();
|
auto& duration = time_point_cast<milliseconds>(_timePoint).time_since_epoch();
|
||||||
|
|
@ -25,7 +20,16 @@ bool e2d::Time::isZero() const
|
||||||
|
|
||||||
e2d::Time e2d::Time::operator+(Duration const & other) const
|
e2d::Time e2d::Time::operator+(Duration const & other) const
|
||||||
{
|
{
|
||||||
return std::move(Time(_timePoint + milliseconds(other.milliseconds())));
|
Time t;
|
||||||
|
t._timePoint = _timePoint + milliseconds(other.milliseconds());
|
||||||
|
return std::move(t);
|
||||||
|
}
|
||||||
|
|
||||||
|
e2d::Time e2d::Time::operator-(Duration const & other) const
|
||||||
|
{
|
||||||
|
Time t;
|
||||||
|
t._timePoint = _timePoint - milliseconds(other.milliseconds());
|
||||||
|
return std::move(t);
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::Time & e2d::Time::operator+=(Duration const & other)
|
e2d::Time & e2d::Time::operator+=(Duration const & other)
|
||||||
|
|
@ -34,11 +38,6 @@ e2d::Time & e2d::Time::operator+=(Duration const & other)
|
||||||
return (*this);
|
return (*this);
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::Time e2d::Time::operator-(Duration const & other) const
|
|
||||||
{
|
|
||||||
return std::move(Time(_timePoint - milliseconds(other.milliseconds())));
|
|
||||||
}
|
|
||||||
|
|
||||||
e2d::Time & e2d::Time::operator-=(Duration const &other)
|
e2d::Time & e2d::Time::operator-=(Duration const &other)
|
||||||
{
|
{
|
||||||
_timePoint -= milliseconds(other.milliseconds());
|
_timePoint -= milliseconds(other.milliseconds());
|
||||||
|
|
@ -47,11 +46,13 @@ e2d::Time & e2d::Time::operator-=(Duration const &other)
|
||||||
|
|
||||||
e2d::Duration e2d::Time::operator-(Time const & other) const
|
e2d::Duration e2d::Time::operator-(Time const & other) const
|
||||||
{
|
{
|
||||||
auto& ms = duration_cast<milliseconds>(_timePoint - other._timePoint);
|
auto ms = duration_cast<milliseconds>(_timePoint - other._timePoint).count();
|
||||||
return std::move(Duration(ms));
|
return std::move(Duration(static_cast<float>(ms) / 1000.f));
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::Time e2d::Time::now()
|
e2d::Time e2d::Time::now()
|
||||||
{
|
{
|
||||||
return std::move(Time(steady_clock::now()));
|
Time t;
|
||||||
|
t._timePoint = steady_clock::now();
|
||||||
|
return std::move(t);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -22,8 +22,7 @@ void e2d::SceneManager::destroyInstance()
|
||||||
}
|
}
|
||||||
|
|
||||||
e2d::SceneManager::SceneManager()
|
e2d::SceneManager::SceneManager()
|
||||||
: _saveCurrScene(true)
|
: _currScene(nullptr)
|
||||||
, _currScene(nullptr)
|
|
||||||
, _nextScene(nullptr)
|
, _nextScene(nullptr)
|
||||||
, _transition(nullptr)
|
, _transition(nullptr)
|
||||||
, _scenes()
|
, _scenes()
|
||||||
|
|
@ -34,7 +33,7 @@ e2d::SceneManager::~SceneManager()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::SceneManager::push(Scene * scene, Transition * transition /* = nullptr */, bool saveCurrentScene /* = true */)
|
void e2d::SceneManager::push(Scene * scene, bool saveCurrentScene)
|
||||||
{
|
{
|
||||||
if (!scene)
|
if (!scene)
|
||||||
return;
|
return;
|
||||||
|
|
@ -44,58 +43,59 @@ void e2d::SceneManager::push(Scene * scene, Transition * transition /* = nullptr
|
||||||
_nextScene = scene;
|
_nextScene = scene;
|
||||||
_nextScene->retain();
|
_nextScene->retain();
|
||||||
|
|
||||||
// 设置切换场景动作
|
// 初始化场景切换动画
|
||||||
if (transition)
|
if (_transition && !_transition->init(_currScene, _nextScene))
|
||||||
{
|
{
|
||||||
if (_transition)
|
WARN("Transition initialize failed!");
|
||||||
{
|
_transition->release();
|
||||||
_transition->_stop();
|
_transition = nullptr;
|
||||||
_transition->release();
|
|
||||||
}
|
|
||||||
_transition = transition;
|
|
||||||
transition->retain();
|
|
||||||
transition->_init(_currScene, _nextScene);
|
|
||||||
transition->_update();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (_currScene)
|
if (saveCurrentScene && _currScene)
|
||||||
{
|
{
|
||||||
_saveCurrScene = saveCurrentScene;
|
_scenes.push(_currScene);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::SceneManager::pop(Transition * transition /* = nullptr */)
|
e2d::Scene* e2d::SceneManager::pop()
|
||||||
{
|
{
|
||||||
// 栈为空时,调用返回场景函数失败
|
// 栈为空时,调用返回场景函数失败
|
||||||
if (_scenes.size() == 0)
|
if (_scenes.size() == 0)
|
||||||
{
|
{
|
||||||
WARN("Scene stack is empty!");
|
WARN("Scene stack is empty!");
|
||||||
return;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
// 从栈顶取出场景指针,作为下一场景
|
|
||||||
_nextScene = _scenes.top();
|
_nextScene = _scenes.top();
|
||||||
_scenes.pop();
|
_scenes.pop();
|
||||||
|
|
||||||
// 返回上一场景时,不保存当前场景
|
// 初始化场景切换动画
|
||||||
if (_currScene)
|
if (_transition && !_transition->init(_currScene, _nextScene))
|
||||||
{
|
{
|
||||||
_saveCurrScene = false;
|
WARN("Transition initialize failed!");
|
||||||
|
_transition->release();
|
||||||
|
_transition = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
// 设置切换场景动作
|
return _nextScene;
|
||||||
|
}
|
||||||
|
|
||||||
|
void e2d::SceneManager::setTransition(Transition * transition)
|
||||||
|
{
|
||||||
if (transition)
|
if (transition)
|
||||||
{
|
{
|
||||||
transition->retain();
|
if (_transition)
|
||||||
transition->_init(_currScene, _nextScene);
|
{
|
||||||
transition->_update();
|
_transition->stop();
|
||||||
|
_transition->release();
|
||||||
|
}
|
||||||
_transition = transition;
|
_transition = transition;
|
||||||
|
_transition->retain();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::SceneManager::clear()
|
void e2d::SceneManager::clear()
|
||||||
{
|
{
|
||||||
// 清空场景栈
|
|
||||||
while (!_scenes.empty())
|
while (!_scenes.empty())
|
||||||
{
|
{
|
||||||
_scenes.top()->release();
|
_scenes.top()->release();
|
||||||
|
|
@ -108,7 +108,7 @@ e2d::Scene * e2d::SceneManager::getCurrentScene()
|
||||||
return _currScene;
|
return _currScene;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::stack<e2d::Scene*> e2d::SceneManager::getSceneStack()
|
const std::stack<e2d::Scene*>& e2d::SceneManager::getSceneStack()
|
||||||
{
|
{
|
||||||
return _scenes;
|
return _scenes;
|
||||||
}
|
}
|
||||||
|
|
@ -120,19 +120,13 @@ bool e2d::SceneManager::isTransitioning()
|
||||||
|
|
||||||
void e2d::SceneManager::update()
|
void e2d::SceneManager::update()
|
||||||
{
|
{
|
||||||
if (_transition == nullptr)
|
if (_currScene) _currScene->update();
|
||||||
{
|
if (_nextScene) _nextScene->update();
|
||||||
// 更新场景内容
|
|
||||||
if (_currScene)
|
|
||||||
{
|
|
||||||
_currScene->update();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// 更新场景动作
|
|
||||||
_transition->_update();
|
|
||||||
|
|
||||||
|
if (_transition)
|
||||||
|
{
|
||||||
|
_transition->update();
|
||||||
|
|
||||||
if (_transition->isDone())
|
if (_transition->isDone())
|
||||||
{
|
{
|
||||||
_transition->release();
|
_transition->release();
|
||||||
|
|
@ -144,26 +138,17 @@ void e2d::SceneManager::update()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// 下一场景指针不为空时,切换场景
|
|
||||||
if (_nextScene)
|
if (_nextScene)
|
||||||
{
|
{
|
||||||
if (_currScene)
|
if (_currScene)
|
||||||
{
|
{
|
||||||
// 执行当前场景的 onExit 函数
|
|
||||||
_currScene->onExit();
|
_currScene->onExit();
|
||||||
|
if (_scenes.empty() || _scenes.top() != _currScene)
|
||||||
// 若要保存当前场景,把它放入栈中
|
|
||||||
if (_saveCurrScene)
|
|
||||||
{
|
|
||||||
_scenes.push(_currScene);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
{
|
||||||
_currScene->release();
|
_currScene->release();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// 执行下一场景的 onEnter 函数
|
|
||||||
_nextScene->onEnter();
|
_nextScene->onEnter();
|
||||||
|
|
||||||
_currScene = _nextScene;
|
_currScene = _nextScene;
|
||||||
|
|
@ -175,15 +160,11 @@ void e2d::SceneManager::render()
|
||||||
{
|
{
|
||||||
if (_transition)
|
if (_transition)
|
||||||
{
|
{
|
||||||
_transition->_render();
|
_transition->render();
|
||||||
}
|
}
|
||||||
else
|
else if (_currScene)
|
||||||
{
|
{
|
||||||
// 绘制当前场景
|
_currScene->render();
|
||||||
if (_currScene)
|
|
||||||
{
|
|
||||||
_currScene->render();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -6,8 +6,7 @@ e2d::Task::Task(const Function & func, const String & name)
|
||||||
, _stopped(false)
|
, _stopped(false)
|
||||||
, _runTimes(0)
|
, _runTimes(0)
|
||||||
, _totalTimes(-1)
|
, _totalTimes(-1)
|
||||||
, _delay(0.f)
|
, _delay()
|
||||||
, _lastTime(0.f)
|
|
||||||
, _callback(func)
|
, _callback(func)
|
||||||
, _name(name)
|
, _name(name)
|
||||||
{
|
{
|
||||||
|
|
@ -17,9 +16,8 @@ e2d::Task::Task(const Function & func, float delay, int times, const String & na
|
||||||
: _running(true)
|
: _running(true)
|
||||||
, _stopped(false)
|
, _stopped(false)
|
||||||
, _runTimes(0)
|
, _runTimes(0)
|
||||||
, _totalTimes(times)
|
|
||||||
, _delay(std::max(delay, 0.f))
|
, _delay(std::max(delay, 0.f))
|
||||||
, _lastTime(0.f)
|
, _totalTimes(times)
|
||||||
, _callback(func)
|
, _callback(func)
|
||||||
, _name(name)
|
, _name(name)
|
||||||
{
|
{
|
||||||
|
|
@ -38,17 +36,24 @@ void e2d::Task::resume()
|
||||||
|
|
||||||
void e2d::Task::update()
|
void e2d::Task::update()
|
||||||
{
|
{
|
||||||
if (_callback)
|
if (_totalTimes == 0)
|
||||||
{
|
{
|
||||||
_callback();
|
_stopped = true;
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
++_runTimes;
|
++_runTimes;
|
||||||
_lastTime += _delay;
|
_lastTime += _delay;
|
||||||
|
|
||||||
|
if (_callback)
|
||||||
|
{
|
||||||
|
_callback();
|
||||||
|
}
|
||||||
|
|
||||||
if (_runTimes == _totalTimes)
|
if (_runTimes == _totalTimes)
|
||||||
{
|
{
|
||||||
_stopped = true;
|
_stopped = true;
|
||||||
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -56,11 +61,11 @@ bool e2d::Task::isReady() const
|
||||||
{
|
{
|
||||||
if (_running)
|
if (_running)
|
||||||
{
|
{
|
||||||
if (_delay == 0)
|
if (_delay.milliseconds() == 0)
|
||||||
{
|
{
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if ((Game::getInstance()->getTotalDuration().seconds() - _lastTime) >= _delay)
|
if (Time::now() - _lastTime >= _delay)
|
||||||
{
|
{
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
@ -80,5 +85,5 @@ e2d::String e2d::Task::getName() const
|
||||||
|
|
||||||
void e2d::Task::updateTime()
|
void e2d::Task::updateTime()
|
||||||
{
|
{
|
||||||
_lastTime = Game::getInstance()->getTotalDuration().seconds();
|
_lastTime = Time::now();
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -6,14 +6,20 @@ e2d::BoxTransition::BoxTransition(float duration)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::BoxTransition::_init(Scene * prev, Scene * next)
|
bool e2d::BoxTransition::init(Scene * prev, Scene * next)
|
||||||
{
|
{
|
||||||
Transition::_init(prev, next);
|
if (Transition::init(prev, next))
|
||||||
_inLayerParam.opacity = 0;
|
{
|
||||||
|
_inLayerParam.opacity = 0;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::BoxTransition::_updateCustom()
|
void e2d::BoxTransition::update()
|
||||||
{
|
{
|
||||||
|
Transition::update();
|
||||||
|
|
||||||
if (_delta <= 0.5)
|
if (_delta <= 0.5)
|
||||||
{
|
{
|
||||||
_outLayerParam.contentBounds = D2D1::RectF(
|
_outLayerParam.contentBounds = D2D1::RectF(
|
||||||
|
|
@ -35,11 +41,11 @@ void e2d::BoxTransition::_updateCustom()
|
||||||
);
|
);
|
||||||
if (_delta >= 1)
|
if (_delta >= 1)
|
||||||
{
|
{
|
||||||
this->_stop();
|
this->stop();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::BoxTransition::_reset()
|
void e2d::BoxTransition::reset()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -6,24 +6,30 @@ e2d::EmergeTransition::EmergeTransition(float duration)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::EmergeTransition::_init(Scene * prev, Scene * next)
|
bool e2d::EmergeTransition::init(Scene * prev, Scene * next)
|
||||||
{
|
{
|
||||||
Transition::_init(prev, next);
|
if (Transition::init(prev, next))
|
||||||
_outLayerParam.opacity = 1;
|
{
|
||||||
_inLayerParam.opacity = 0;
|
_outLayerParam.opacity = 1;
|
||||||
|
_inLayerParam.opacity = 0;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::EmergeTransition::_updateCustom()
|
void e2d::EmergeTransition::update()
|
||||||
{
|
{
|
||||||
|
Transition::update();
|
||||||
|
|
||||||
_outLayerParam.opacity = 1 - _delta;
|
_outLayerParam.opacity = 1 - _delta;
|
||||||
_inLayerParam.opacity = _delta;
|
_inLayerParam.opacity = _delta;
|
||||||
|
|
||||||
if (_delta >= 1)
|
if (_delta >= 1)
|
||||||
{
|
{
|
||||||
this->_stop();
|
this->stop();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::EmergeTransition::_reset()
|
void e2d::EmergeTransition::reset()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -6,15 +6,21 @@ e2d::FadeTransition::FadeTransition(float duration)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::FadeTransition::_init(Scene * prev, Scene * next)
|
bool e2d::FadeTransition::init(Scene * prev, Scene * next)
|
||||||
{
|
{
|
||||||
Transition::_init(prev, next);
|
if (Transition::init(prev, next))
|
||||||
_outLayerParam.opacity = 1;
|
{
|
||||||
_inLayerParam.opacity = 0;
|
_outLayerParam.opacity = 1;
|
||||||
|
_inLayerParam.opacity = 0;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::FadeTransition::_updateCustom()
|
void e2d::FadeTransition::update()
|
||||||
{
|
{
|
||||||
|
Transition::update();
|
||||||
|
|
||||||
if (_delta < 0.5)
|
if (_delta < 0.5)
|
||||||
{
|
{
|
||||||
_outLayerParam.opacity = 1 - _delta * 2;
|
_outLayerParam.opacity = 1 - _delta * 2;
|
||||||
|
|
@ -26,11 +32,11 @@ void e2d::FadeTransition::_updateCustom()
|
||||||
_inLayerParam.opacity = (_delta - 0.5f) * 2;
|
_inLayerParam.opacity = (_delta - 0.5f) * 2;
|
||||||
if (_delta >= 1)
|
if (_delta >= 1)
|
||||||
{
|
{
|
||||||
this->_stop();
|
this->stop();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::FadeTransition::_reset()
|
void e2d::FadeTransition::reset()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -7,39 +7,44 @@ e2d::MoveTransition::MoveTransition(float duration, Direction direction)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::MoveTransition::_init(Scene * prev, Scene * next)
|
bool e2d::MoveTransition::init(Scene * prev, Scene * next)
|
||||||
{
|
{
|
||||||
Transition::_init(prev, next);
|
if (Transition::init(prev, next))
|
||||||
|
{
|
||||||
|
float width = _windowSize.width;
|
||||||
|
float height = _windowSize.height;
|
||||||
|
if (_direction == Direction::Up)
|
||||||
|
{
|
||||||
|
_posDelta = Vector2(0, -height);
|
||||||
|
_startPos = Point(0, height);
|
||||||
|
}
|
||||||
|
else if (_direction == Direction::Down)
|
||||||
|
{
|
||||||
|
_posDelta = Vector2(0, height);
|
||||||
|
_startPos = Point(0, -height);
|
||||||
|
}
|
||||||
|
else if (_direction == Direction::Left)
|
||||||
|
{
|
||||||
|
_posDelta = Vector2(-width, 0);
|
||||||
|
_startPos = Point(width, 0);
|
||||||
|
}
|
||||||
|
else if (_direction == Direction::Right)
|
||||||
|
{
|
||||||
|
_posDelta = Vector2(width, 0);
|
||||||
|
_startPos = Point(-width, 0);
|
||||||
|
}
|
||||||
|
|
||||||
float width = _windowSize.width;
|
if (_outScene) _outScene->getRoot()->setPos(0, 0);
|
||||||
float height = _windowSize.height;
|
_inScene->getRoot()->setPos(_startPos);
|
||||||
if (_direction == Direction::Up)
|
return true;
|
||||||
{
|
|
||||||
_posDelta = Vector2(0, -height);
|
|
||||||
_startPos = Point(0, height);
|
|
||||||
}
|
}
|
||||||
else if (_direction == Direction::Down)
|
return false;
|
||||||
{
|
|
||||||
_posDelta = Vector2(0, height);
|
|
||||||
_startPos = Point(0, -height);
|
|
||||||
}
|
|
||||||
else if (_direction == Direction::Left)
|
|
||||||
{
|
|
||||||
_posDelta = Vector2(-width, 0);
|
|
||||||
_startPos = Point(width, 0);
|
|
||||||
}
|
|
||||||
else if (_direction == Direction::Right)
|
|
||||||
{
|
|
||||||
_posDelta = Vector2(width, 0);
|
|
||||||
_startPos = Point(-width, 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (_outScene) _outScene->getRoot()->setPos(0, 0);
|
|
||||||
_inScene->getRoot()->setPos(_startPos);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::MoveTransition::_updateCustom()
|
void e2d::MoveTransition::update()
|
||||||
{
|
{
|
||||||
|
Transition::update();
|
||||||
|
|
||||||
if (_outScene)
|
if (_outScene)
|
||||||
{
|
{
|
||||||
_outScene->getRoot()->setPos(_posDelta * _delta);
|
_outScene->getRoot()->setPos(_posDelta * _delta);
|
||||||
|
|
@ -51,11 +56,11 @@ void e2d::MoveTransition::_updateCustom()
|
||||||
|
|
||||||
if (_delta >= 1)
|
if (_delta >= 1)
|
||||||
{
|
{
|
||||||
this->_stop();
|
this->stop();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::MoveTransition::_reset()
|
void e2d::MoveTransition::reset()
|
||||||
{
|
{
|
||||||
if (_outScene) _outScene->getRoot()->setPos(0, 0);
|
if (_outScene) _outScene->getRoot()->setPos(0, 0);
|
||||||
_inScene->getRoot()->setPos(0, 0);
|
_inScene->getRoot()->setPos(0, 0);
|
||||||
|
|
|
||||||
|
|
@ -4,7 +4,7 @@
|
||||||
|
|
||||||
e2d::Transition::Transition(float duration)
|
e2d::Transition::Transition(float duration)
|
||||||
: _end(false)
|
: _end(false)
|
||||||
, _last()
|
, _started()
|
||||||
, _delta(0)
|
, _delta(0)
|
||||||
, _outScene(nullptr)
|
, _outScene(nullptr)
|
||||||
, _inScene(nullptr)
|
, _inScene(nullptr)
|
||||||
|
|
@ -29,7 +29,7 @@ bool e2d::Transition::isDone()
|
||||||
return _end;
|
return _end;
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::Transition::_init(Scene * prev, Scene * next)
|
bool e2d::Transition::init(Scene * prev, Scene * next)
|
||||||
{
|
{
|
||||||
auto renderer = Renderer::getInstance();
|
auto renderer = Renderer::getInstance();
|
||||||
// ´´½¨Í¼²ã
|
// ´´½¨Í¼²ã
|
||||||
|
|
@ -42,10 +42,10 @@ void e2d::Transition::_init(Scene * prev, Scene * next)
|
||||||
|
|
||||||
if (FAILED(hr))
|
if (FAILED(hr))
|
||||||
{
|
{
|
||||||
throw SystemException(L"场景过渡动画图层创建失败");
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
_last = Game::getInstance()->getTotalDuration();
|
_started = Time::now();
|
||||||
_outScene = prev;
|
_outScene = prev;
|
||||||
_inScene = next;
|
_inScene = next;
|
||||||
if (_outScene) _outScene->retain();
|
if (_outScene) _outScene->retain();
|
||||||
|
|
@ -61,35 +61,24 @@ void e2d::Transition::_init(Scene * prev, Scene * next)
|
||||||
renderer->getSolidColorBrush(),
|
renderer->getSolidColorBrush(),
|
||||||
D2D1_LAYER_OPTIONS_NONE
|
D2D1_LAYER_OPTIONS_NONE
|
||||||
);
|
);
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::Transition::_update()
|
void e2d::Transition::update()
|
||||||
{
|
{
|
||||||
// 计算动作进度
|
|
||||||
if (_duration == 0)
|
if (_duration == 0)
|
||||||
{
|
{
|
||||||
_delta = 1;
|
_delta = 1;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
_delta = (Game::getInstance()->getTotalDuration() - _last).seconds() / _duration;
|
_delta = (Time::now() - _started).seconds() / _duration;
|
||||||
_delta = std::min(_delta, 1.f);
|
_delta = std::min(_delta, 1.f);
|
||||||
}
|
}
|
||||||
|
|
||||||
this->_updateCustom();
|
|
||||||
|
|
||||||
// 更新场景内容
|
|
||||||
if (_outScene)
|
|
||||||
{
|
|
||||||
_outScene->update();
|
|
||||||
}
|
|
||||||
if (_inScene)
|
|
||||||
{
|
|
||||||
_inScene->update();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::Transition::_render()
|
void e2d::Transition::render()
|
||||||
{
|
{
|
||||||
auto pRT = Renderer::getInstance()->getRenderTarget();
|
auto pRT = Renderer::getInstance()->getRenderTarget();
|
||||||
|
|
||||||
|
|
@ -132,8 +121,8 @@ void e2d::Transition::_render()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void e2d::Transition::_stop()
|
void e2d::Transition::stop()
|
||||||
{
|
{
|
||||||
_end = true;
|
_end = true;
|
||||||
_reset();
|
reset();
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -85,7 +85,7 @@ protected:
|
||||||
bool _done;
|
bool _done;
|
||||||
bool _initialized;
|
bool _initialized;
|
||||||
Node * _target;
|
Node * _target;
|
||||||
float _last;
|
Time _started;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -118,9 +118,6 @@ public:
|
||||||
// 获取游戏配置
|
// 获取游戏配置
|
||||||
const Config& getConfig();
|
const Config& getConfig();
|
||||||
|
|
||||||
// 获取游戏总时长
|
|
||||||
Duration getTotalDuration() const;
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
Game();
|
Game();
|
||||||
|
|
||||||
|
|
@ -132,9 +129,6 @@ private:
|
||||||
bool _quit;
|
bool _quit;
|
||||||
bool _paused;
|
bool _paused;
|
||||||
Config _config;
|
Config _config;
|
||||||
Time _start;
|
|
||||||
Time _now;
|
|
||||||
Time _last;
|
|
||||||
|
|
||||||
static Game * _instance;
|
static Game * _instance;
|
||||||
};
|
};
|
||||||
|
|
@ -243,7 +237,13 @@ private:
|
||||||
E2D_DISABLE_COPY(Window);
|
E2D_DISABLE_COPY(Window);
|
||||||
|
|
||||||
// 注册窗口
|
// 注册窗口
|
||||||
HWND __create();
|
HWND __registerWindow();
|
||||||
|
|
||||||
|
// 根据客户区大小计算合适的窗口区域
|
||||||
|
Rect __adjustWindow(
|
||||||
|
int width,
|
||||||
|
int height
|
||||||
|
);
|
||||||
|
|
||||||
// Win32 窗口消息回调程序
|
// Win32 窗口消息回调程序
|
||||||
static LRESULT CALLBACK WndProc(
|
static LRESULT CALLBACK WndProc(
|
||||||
|
|
@ -342,12 +342,6 @@ public:
|
||||||
Color color
|
Color color
|
||||||
);
|
);
|
||||||
|
|
||||||
// 渲染游戏画面
|
|
||||||
void render();
|
|
||||||
|
|
||||||
// 删除设备相关资源
|
|
||||||
void discardDeviceResources();
|
|
||||||
|
|
||||||
// 获取文字渲染器
|
// 获取文字渲染器
|
||||||
TextRenderer * getTextRenderer();
|
TextRenderer * getTextRenderer();
|
||||||
|
|
||||||
|
|
@ -357,6 +351,12 @@ public:
|
||||||
// 获取 ID2D1SolidColorBrush 对象
|
// 获取 ID2D1SolidColorBrush 对象
|
||||||
ID2D1SolidColorBrush * getSolidColorBrush();
|
ID2D1SolidColorBrush * getSolidColorBrush();
|
||||||
|
|
||||||
|
// 渲染游戏画面
|
||||||
|
void render();
|
||||||
|
|
||||||
|
// 删除设备相关资源
|
||||||
|
void discardDeviceResources();
|
||||||
|
|
||||||
// 获取 ID2D1Factory 对象
|
// 获取 ID2D1Factory 对象
|
||||||
static ID2D1Factory * getFactory();
|
static ID2D1Factory * getFactory();
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -414,11 +414,7 @@ public:
|
||||||
Duration();
|
Duration();
|
||||||
|
|
||||||
explicit Duration(
|
explicit Duration(
|
||||||
int ms
|
float seconds
|
||||||
);
|
|
||||||
|
|
||||||
explicit Duration(
|
|
||||||
const std::chrono::milliseconds& ms
|
|
||||||
);
|
);
|
||||||
|
|
||||||
// 获取毫秒数
|
// 获取毫秒数
|
||||||
|
|
@ -451,10 +447,6 @@ class Time
|
||||||
public:
|
public:
|
||||||
Time();
|
Time();
|
||||||
|
|
||||||
explicit Time(
|
|
||||||
const std::chrono::steady_clock::time_point& time
|
|
||||||
);
|
|
||||||
|
|
||||||
// 获取时间戳
|
// 获取时间戳
|
||||||
time_t getTimeStamp() const;
|
time_t getTimeStamp() const;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -25,13 +25,15 @@ public:
|
||||||
// 场景入栈
|
// 场景入栈
|
||||||
void push(
|
void push(
|
||||||
Scene * scene, /* 下一个场景的指针 */
|
Scene * scene, /* 下一个场景的指针 */
|
||||||
Transition * transition = nullptr, /* 场景切换动作 */
|
|
||||||
bool saveCurrentScene = true /* 是否保存当前场景 */
|
bool saveCurrentScene = true /* 是否保存当前场景 */
|
||||||
);
|
);
|
||||||
|
|
||||||
// 场景出栈
|
// 场景出栈
|
||||||
void pop(
|
Scene* pop();
|
||||||
Transition * transition = nullptr /* 场景切换动作 */
|
|
||||||
|
// 设置场景切换动作
|
||||||
|
void setTransition(
|
||||||
|
Transition * transition /* 场景切换动作 */
|
||||||
);
|
);
|
||||||
|
|
||||||
// 清空保存的所有场景
|
// 清空保存的所有场景
|
||||||
|
|
@ -41,7 +43,7 @@ public:
|
||||||
Scene * getCurrentScene();
|
Scene * getCurrentScene();
|
||||||
|
|
||||||
// 获取场景栈
|
// 获取场景栈
|
||||||
std::stack<Scene*> getSceneStack();
|
const std::stack<Scene*>& getSceneStack();
|
||||||
|
|
||||||
// 是否正在进行转场动作
|
// 是否正在进行转场动作
|
||||||
bool isTransitioning();
|
bool isTransitioning();
|
||||||
|
|
@ -70,7 +72,6 @@ private:
|
||||||
E2D_DISABLE_COPY(SceneManager);
|
E2D_DISABLE_COPY(SceneManager);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
bool _saveCurrScene;
|
|
||||||
Scene * _currScene;
|
Scene * _currScene;
|
||||||
Scene * _nextScene;
|
Scene * _nextScene;
|
||||||
Transition * _transition;
|
Transition * _transition;
|
||||||
|
|
|
||||||
|
|
@ -308,8 +308,8 @@ private:
|
||||||
bool _stopped;
|
bool _stopped;
|
||||||
int _runTimes;
|
int _runTimes;
|
||||||
int _totalTimes;
|
int _totalTimes;
|
||||||
float _delay;
|
Duration _delay;
|
||||||
float _lastTime;
|
Time _lastTime;
|
||||||
String _name;
|
String _name;
|
||||||
Function _callback;
|
Function _callback;
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -5,15 +5,10 @@ namespace e2d
|
||||||
{
|
{
|
||||||
|
|
||||||
|
|
||||||
class SceneManager;
|
|
||||||
|
|
||||||
|
|
||||||
// 场景过渡
|
// 场景过渡
|
||||||
class Transition :
|
class Transition :
|
||||||
public Ref
|
public Ref
|
||||||
{
|
{
|
||||||
friend class SceneManager;
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
explicit Transition(float duration);
|
explicit Transition(float duration);
|
||||||
|
|
||||||
|
|
@ -22,36 +17,32 @@ public:
|
||||||
// 场景过渡动画是否结束
|
// 场景过渡动画是否结束
|
||||||
bool isDone();
|
bool isDone();
|
||||||
|
|
||||||
protected:
|
|
||||||
// 初始化场景过渡动画
|
// 初始化场景过渡动画
|
||||||
virtual void _init(
|
virtual bool init(
|
||||||
Scene * prev,
|
Scene * prev,
|
||||||
Scene * next
|
Scene * next
|
||||||
);
|
);
|
||||||
|
|
||||||
// 更新场景过渡动画
|
// 更新场景过渡动画
|
||||||
virtual void _update();
|
virtual void update();
|
||||||
|
|
||||||
// 更新场景过渡动画
|
|
||||||
virtual void _updateCustom() = 0;
|
|
||||||
|
|
||||||
// 渲染场景过渡动画
|
// 渲染场景过渡动画
|
||||||
virtual void _render();
|
virtual void render();
|
||||||
|
|
||||||
// 重置场景过渡动画
|
|
||||||
virtual void _reset() = 0;
|
|
||||||
|
|
||||||
// 停止场景过渡动画
|
// 停止场景过渡动画
|
||||||
virtual void _stop();
|
virtual void stop();
|
||||||
|
|
||||||
|
// ÖØÖó¡¾°¹ý¶É¶¯»
|
||||||
|
virtual void reset() = 0;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
bool _end;
|
bool _end;
|
||||||
float _duration;
|
float _duration;
|
||||||
float _delta;
|
float _delta;
|
||||||
Duration _last;
|
Time _started;
|
||||||
Size _windowSize;
|
Size _windowSize;
|
||||||
Scene * _outScene;
|
Scene* _outScene;
|
||||||
Scene * _inScene;
|
Scene* _inScene;
|
||||||
ID2D1Layer * _outLayer;
|
ID2D1Layer * _outLayer;
|
||||||
ID2D1Layer * _inLayer;
|
ID2D1Layer * _inLayer;
|
||||||
D2D1_LAYER_PARAMETERS _outLayerParam;
|
D2D1_LAYER_PARAMETERS _outLayerParam;
|
||||||
|
|
@ -68,16 +59,15 @@ public:
|
||||||
float duration /* 动画持续时长 */
|
float duration /* 动画持续时长 */
|
||||||
);
|
);
|
||||||
|
|
||||||
protected:
|
|
||||||
// 更新动画
|
// 更新动画
|
||||||
virtual void _updateCustom() override;
|
virtual void update() override;
|
||||||
|
|
||||||
virtual void _init(
|
virtual bool init(
|
||||||
Scene * prev,
|
Scene * prev,
|
||||||
Scene * next
|
Scene * next
|
||||||
) override;
|
) override;
|
||||||
|
|
||||||
virtual void _reset() override;
|
virtual void reset() override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -90,16 +80,15 @@ public:
|
||||||
float duration /* 浮现动画持续时长 */
|
float duration /* 浮现动画持续时长 */
|
||||||
);
|
);
|
||||||
|
|
||||||
protected:
|
|
||||||
// 更新动画
|
// 更新动画
|
||||||
virtual void _updateCustom() override;
|
virtual void update() override;
|
||||||
|
|
||||||
virtual void _init(
|
virtual bool init(
|
||||||
Scene * prev,
|
Scene * prev,
|
||||||
Scene * next
|
Scene * next
|
||||||
) override;
|
) override;
|
||||||
|
|
||||||
virtual void _reset() override;
|
virtual void reset() override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -112,16 +101,15 @@ public:
|
||||||
float duration /* 动画持续时长 */
|
float duration /* 动画持续时长 */
|
||||||
);
|
);
|
||||||
|
|
||||||
protected:
|
|
||||||
// 更新动画
|
// 更新动画
|
||||||
virtual void _updateCustom() override;
|
virtual void update() override;
|
||||||
|
|
||||||
virtual void _init(
|
virtual bool init(
|
||||||
Scene * prev,
|
Scene * prev,
|
||||||
Scene * next
|
Scene * next
|
||||||
) override;
|
) override;
|
||||||
|
|
||||||
virtual void _reset() override;
|
virtual void reset() override;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -135,16 +123,15 @@ public:
|
||||||
Direction direction = Direction::Left /* 场景移动方向 */
|
Direction direction = Direction::Left /* 场景移动方向 */
|
||||||
);
|
);
|
||||||
|
|
||||||
protected:
|
|
||||||
// 更新动画
|
// 更新动画
|
||||||
virtual void _updateCustom() override;
|
virtual void update() override;
|
||||||
|
|
||||||
virtual void _init(
|
virtual bool init(
|
||||||
Scene * prev,
|
Scene * prev,
|
||||||
Scene * next
|
Scene * next
|
||||||
) override;
|
) override;
|
||||||
|
|
||||||
virtual void _reset() override;
|
virtual void reset() override;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
Direction _direction;
|
Direction _direction;
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue