feat(渲染): 实现节点层级变换支持
refactor(场景图): 简化形状节点渲染逻辑 feat(输入): 添加输入事件到事件服务的连接 docs(模块系统): 更新文档说明模块配置和平台支持 test(示例): 添加场景图测试示例展示节点变换
This commit is contained in:
parent
8c56c29cd2
commit
6c6cac55f7
|
|
@ -22,7 +22,9 @@
|
||||||
#include <extra2d/platform/iinput.h>
|
#include <extra2d/platform/iinput.h>
|
||||||
#include <extra2d/platform/iwindow.h>
|
#include <extra2d/platform/iwindow.h>
|
||||||
#include <extra2d/platform/keys.h>
|
#include <extra2d/platform/keys.h>
|
||||||
|
#include <extra2d/platform/input_module.h>
|
||||||
#include <extra2d/platform/platform_module.h>
|
#include <extra2d/platform/platform_module.h>
|
||||||
|
#include <extra2d/platform/window_module.h>
|
||||||
|
|
||||||
// Graphics
|
// Graphics
|
||||||
#include <extra2d/graphics/camera.h>
|
#include <extra2d/graphics/camera.h>
|
||||||
|
|
@ -54,6 +56,12 @@
|
||||||
#include <extra2d/utils/random.h>
|
#include <extra2d/utils/random.h>
|
||||||
#include <extra2d/utils/timer.h>
|
#include <extra2d/utils/timer.h>
|
||||||
|
|
||||||
|
// Services
|
||||||
|
#include <extra2d/services/event_service.h>
|
||||||
|
#include <extra2d/services/scene_service.h>
|
||||||
|
#include <extra2d/services/timer_service.h>
|
||||||
|
#include <extra2d/services/camera_service.h>
|
||||||
|
|
||||||
// Application
|
// Application
|
||||||
#include <extra2d/app/application.h>
|
#include <extra2d/app/application.h>
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -5,6 +5,7 @@
|
||||||
#include <extra2d/graphics/render_config.h>
|
#include <extra2d/graphics/render_config.h>
|
||||||
#include <extra2d/graphics/vram_manager.h>
|
#include <extra2d/graphics/vram_manager.h>
|
||||||
#include <extra2d/platform/iinput.h>
|
#include <extra2d/platform/iinput.h>
|
||||||
|
#include <extra2d/platform/input_module.h>
|
||||||
#include <extra2d/platform/platform_init_module.h>
|
#include <extra2d/platform/platform_init_module.h>
|
||||||
#include <extra2d/platform/window_module.h>
|
#include <extra2d/platform/window_module.h>
|
||||||
#include <extra2d/services/scene_service.h>
|
#include <extra2d/services/scene_service.h>
|
||||||
|
|
@ -53,6 +54,7 @@ bool Application::init(const AppConfig& config) {
|
||||||
register_config_module();
|
register_config_module();
|
||||||
register_platform_module();
|
register_platform_module();
|
||||||
register_window_module();
|
register_window_module();
|
||||||
|
register_input_module();
|
||||||
register_render_module();
|
register_render_module();
|
||||||
|
|
||||||
auto* configInit = ModuleRegistry::instance().getInitializer(get_config_module_id());
|
auto* configInit = ModuleRegistry::instance().getInitializer(get_config_module_id());
|
||||||
|
|
@ -74,6 +76,7 @@ bool Application::init(const std::string& configPath) {
|
||||||
register_config_module();
|
register_config_module();
|
||||||
register_platform_module();
|
register_platform_module();
|
||||||
register_window_module();
|
register_window_module();
|
||||||
|
register_input_module();
|
||||||
register_render_module();
|
register_render_module();
|
||||||
|
|
||||||
auto* configInit = ModuleRegistry::instance().getInitializer(get_config_module_id());
|
auto* configInit = ModuleRegistry::instance().getInitializer(get_config_module_id());
|
||||||
|
|
@ -90,7 +93,7 @@ bool Application::init(const std::string& configPath) {
|
||||||
void Application::registerCoreServices() {
|
void Application::registerCoreServices() {
|
||||||
auto& locator = ServiceLocator::instance();
|
auto& locator = ServiceLocator::instance();
|
||||||
|
|
||||||
if (!locator.hasService<IEventService>()) {
|
if (!locator.hasService<ISceneService>()) {
|
||||||
locator.registerService<ISceneService>(makeShared<SceneService>());
|
locator.registerService<ISceneService>(makeShared<SceneService>());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -98,10 +101,6 @@ void Application::registerCoreServices() {
|
||||||
locator.registerService<ITimerService>(makeShared<TimerService>());
|
locator.registerService<ITimerService>(makeShared<TimerService>());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!locator.hasService<IEventService>()) {
|
|
||||||
locator.registerService<IEventService>(makeShared<EventService>());
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!locator.hasService<ICameraService>()) {
|
if (!locator.hasService<ICameraService>()) {
|
||||||
auto cameraService = makeShared<CameraService>();
|
auto cameraService = makeShared<CameraService>();
|
||||||
if (window_) {
|
if (window_) {
|
||||||
|
|
@ -119,6 +118,12 @@ void Application::registerCoreServices() {
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Application::initModules() {
|
bool Application::initModules() {
|
||||||
|
auto& locator = ServiceLocator::instance();
|
||||||
|
|
||||||
|
if (!locator.hasService<IEventService>()) {
|
||||||
|
locator.registerService<IEventService>(makeShared<EventService>());
|
||||||
|
}
|
||||||
|
|
||||||
auto initOrder = ModuleRegistry::instance().getInitializationOrder();
|
auto initOrder = ModuleRegistry::instance().getInitializationOrder();
|
||||||
|
|
||||||
for (ModuleId moduleId : initOrder) {
|
for (ModuleId moduleId : initOrder) {
|
||||||
|
|
|
||||||
|
|
@ -698,9 +698,15 @@ void GLRenderer::addShapeVertex(float x, float y, const Color &color) {
|
||||||
if (shapeVertexCount_ >= MAX_SHAPE_VERTICES) {
|
if (shapeVertexCount_ >= MAX_SHAPE_VERTICES) {
|
||||||
flushShapeBatch();
|
flushShapeBatch();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
glm::vec4 pos(x, y, 0.0f, 1.0f);
|
||||||
|
if (!transformStack_.empty()) {
|
||||||
|
pos = transformStack_.back() * pos;
|
||||||
|
}
|
||||||
|
|
||||||
ShapeVertex &v = shapeVertexCache_[shapeVertexCount_++];
|
ShapeVertex &v = shapeVertexCache_[shapeVertexCount_++];
|
||||||
v.x = x;
|
v.x = pos.x;
|
||||||
v.y = y;
|
v.y = pos.y;
|
||||||
v.r = color.r;
|
v.r = color.r;
|
||||||
v.g = color.g;
|
v.g = color.g;
|
||||||
v.b = color.b;
|
v.b = color.b;
|
||||||
|
|
@ -717,9 +723,15 @@ void GLRenderer::addLineVertex(float x, float y, const Color &color) {
|
||||||
if (lineVertexCount_ >= MAX_LINE_VERTICES) {
|
if (lineVertexCount_ >= MAX_LINE_VERTICES) {
|
||||||
flushLineBatch();
|
flushLineBatch();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
glm::vec4 pos(x, y, 0.0f, 1.0f);
|
||||||
|
if (!transformStack_.empty()) {
|
||||||
|
pos = transformStack_.back() * pos;
|
||||||
|
}
|
||||||
|
|
||||||
ShapeVertex &v = lineVertexCache_[lineVertexCount_++];
|
ShapeVertex &v = lineVertexCache_[lineVertexCount_++];
|
||||||
v.x = x;
|
v.x = pos.x;
|
||||||
v.y = y;
|
v.y = pos.y;
|
||||||
v.r = color.r;
|
v.r = color.r;
|
||||||
v.g = color.g;
|
v.g = color.g;
|
||||||
v.b = color.b;
|
v.b = color.b;
|
||||||
|
|
|
||||||
|
|
@ -1,10 +1,13 @@
|
||||||
#include <extra2d/platform/input_module.h>
|
#include <extra2d/platform/input_module.h>
|
||||||
#include <extra2d/config/module_registry.h>
|
#include <extra2d/config/module_registry.h>
|
||||||
|
#include <extra2d/core/service_locator.h>
|
||||||
#include <extra2d/platform/window_module.h>
|
#include <extra2d/platform/window_module.h>
|
||||||
#include <extra2d/services/event_service.h>
|
#include <extra2d/services/event_service.h>
|
||||||
#include <extra2d/utils/logger.h>
|
#include <extra2d/utils/logger.h>
|
||||||
#include <nlohmann/json.hpp>
|
#include <nlohmann/json.hpp>
|
||||||
|
|
||||||
|
#include "backends/sdl2/sdl2_input.h"
|
||||||
|
|
||||||
using json = nlohmann::json;
|
using json = nlohmann::json;
|
||||||
|
|
||||||
namespace extra2d {
|
namespace extra2d {
|
||||||
|
|
@ -146,6 +149,20 @@ bool InputModuleInitializer::initialize(const IModuleConfig* config) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SDL2Input* sdl2Input = dynamic_cast<SDL2Input*>(input_);
|
||||||
|
if (sdl2Input) {
|
||||||
|
auto eventService = ServiceLocator::instance().getService<IEventService>();
|
||||||
|
if (eventService) {
|
||||||
|
sdl2Input->setEventCallback([eventService](const Event& event) {
|
||||||
|
Event mutableEvent = event;
|
||||||
|
eventService->dispatch(mutableEvent);
|
||||||
|
});
|
||||||
|
E2D_LOG_INFO("Input events connected to EventService");
|
||||||
|
} else {
|
||||||
|
E2D_LOG_WARN("EventService not available - input events will not be dispatched");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
initialized_ = true;
|
initialized_ = true;
|
||||||
E2D_LOG_INFO("Input module initialized");
|
E2D_LOG_INFO("Input module initialized");
|
||||||
E2D_LOG_INFO(" Deadzone: {}", config_.deadzone);
|
E2D_LOG_INFO(" Deadzone: {}", config_.deadzone);
|
||||||
|
|
|
||||||
|
|
@ -520,11 +520,15 @@ void Node::onRender(RenderBackend &renderer) {
|
||||||
if (!visible_)
|
if (!visible_)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
renderer.pushTransform(getLocalTransform());
|
||||||
|
|
||||||
onDraw(renderer);
|
onDraw(renderer);
|
||||||
|
|
||||||
for (auto &child : children_) {
|
for (auto &child : children_) {
|
||||||
child->onRender(renderer);
|
child->onRender(renderer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
renderer.popTransform();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
||||||
|
|
@ -268,25 +268,24 @@ Rect ShapeNode::getBounds() const {
|
||||||
* @param renderer 渲染后端引用
|
* @param renderer 渲染后端引用
|
||||||
*
|
*
|
||||||
* 根据形状类型调用相应的渲染方法进行绘制
|
* 根据形状类型调用相应的渲染方法进行绘制
|
||||||
|
* 注意:变换矩阵已由 Node::onRender 通过 pushTransform 应用,
|
||||||
|
* 此处直接使用本地坐标即可。
|
||||||
*/
|
*/
|
||||||
void ShapeNode::onDraw(RenderBackend &renderer) {
|
void ShapeNode::onDraw(RenderBackend &renderer) {
|
||||||
if (points_.empty()) {
|
if (points_.empty()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
Vec2 offset = getPosition();
|
|
||||||
|
|
||||||
switch (shapeType_) {
|
switch (shapeType_) {
|
||||||
case ShapeType::Point:
|
case ShapeType::Point:
|
||||||
if (!points_.empty()) {
|
if (!points_.empty()) {
|
||||||
renderer.fillCircle(points_[0] + offset, lineWidth_ * 0.5f, color_, 8);
|
renderer.fillCircle(points_[0], lineWidth_ * 0.5f, color_, 8);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case ShapeType::Line:
|
case ShapeType::Line:
|
||||||
if (points_.size() >= 2) {
|
if (points_.size() >= 2) {
|
||||||
renderer.drawLine(points_[0] + offset, points_[1] + offset, color_,
|
renderer.drawLine(points_[0], points_[1], color_, lineWidth_);
|
||||||
lineWidth_);
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
|
@ -295,11 +294,11 @@ void ShapeNode::onDraw(RenderBackend &renderer) {
|
||||||
if (filled_) {
|
if (filled_) {
|
||||||
Rect rect(points_[0].x, points_[0].y, points_[2].x - points_[0].x,
|
Rect rect(points_[0].x, points_[0].y, points_[2].x - points_[0].x,
|
||||||
points_[2].y - points_[0].y);
|
points_[2].y - points_[0].y);
|
||||||
renderer.fillRect(Rect(rect.origin + offset, rect.size), color_);
|
renderer.fillRect(rect, color_);
|
||||||
} else {
|
} else {
|
||||||
for (size_t i = 0; i < points_.size(); ++i) {
|
for (size_t i = 0; i < points_.size(); ++i) {
|
||||||
Vec2 start = points_[i] + offset;
|
Vec2 start = points_[i];
|
||||||
Vec2 end = points_[(i + 1) % points_.size()] + offset;
|
Vec2 end = points_[(i + 1) % points_.size()];
|
||||||
renderer.drawLine(start, end, color_, lineWidth_);
|
renderer.drawLine(start, end, color_, lineWidth_);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -310,41 +309,31 @@ void ShapeNode::onDraw(RenderBackend &renderer) {
|
||||||
if (points_.size() >= 2) {
|
if (points_.size() >= 2) {
|
||||||
float radius = points_[1].x;
|
float radius = points_[1].x;
|
||||||
if (filled_) {
|
if (filled_) {
|
||||||
renderer.fillCircle(points_[0] + offset, radius, color_, segments_);
|
renderer.fillCircle(points_[0], radius, color_, segments_);
|
||||||
} else {
|
} else {
|
||||||
renderer.drawCircle(points_[0] + offset, radius, color_, segments_,
|
renderer.drawCircle(points_[0], radius, color_, segments_, lineWidth_);
|
||||||
lineWidth_);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case ShapeType::Triangle:
|
case ShapeType::Triangle:
|
||||||
if (points_.size() >= 3) {
|
if (points_.size() >= 3) {
|
||||||
Vec2 p1 = points_[0] + offset;
|
|
||||||
Vec2 p2 = points_[1] + offset;
|
|
||||||
Vec2 p3 = points_[2] + offset;
|
|
||||||
if (filled_) {
|
if (filled_) {
|
||||||
renderer.fillTriangle(p1, p2, p3, color_);
|
renderer.fillTriangle(points_[0], points_[1], points_[2], color_);
|
||||||
} else {
|
} else {
|
||||||
renderer.drawLine(p1, p2, color_, lineWidth_);
|
renderer.drawLine(points_[0], points_[1], color_, lineWidth_);
|
||||||
renderer.drawLine(p2, p3, color_, lineWidth_);
|
renderer.drawLine(points_[1], points_[2], color_, lineWidth_);
|
||||||
renderer.drawLine(p3, p1, color_, lineWidth_);
|
renderer.drawLine(points_[2], points_[0], color_, lineWidth_);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case ShapeType::Polygon:
|
case ShapeType::Polygon:
|
||||||
if (!points_.empty()) {
|
if (!points_.empty()) {
|
||||||
std::vector<Vec2> transformedPoints;
|
|
||||||
transformedPoints.reserve(points_.size());
|
|
||||||
for (const auto &p : points_) {
|
|
||||||
transformedPoints.push_back(p + offset);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (filled_) {
|
if (filled_) {
|
||||||
renderer.fillPolygon(transformedPoints, color_);
|
renderer.fillPolygon(points_, color_);
|
||||||
} else {
|
} else {
|
||||||
renderer.drawPolygon(transformedPoints, color_, lineWidth_);
|
renderer.drawPolygon(points_, color_, lineWidth_);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
|
||||||
File diff suppressed because it is too large
Load Diff
|
|
@ -1,30 +1,112 @@
|
||||||
/**
|
/**
|
||||||
* @file main.cpp
|
* @file main.cpp
|
||||||
* @brief Extra2D 基础示例程序
|
* @brief Extra2D 场景图测试示例
|
||||||
*
|
*
|
||||||
* 演示如何使用 Extra2D 引擎创建一个简单的窗口应用程序。
|
* 演示场景图功能:
|
||||||
|
* - 节点层级关系
|
||||||
|
* - 变换(位置、旋转、缩放)
|
||||||
|
* - 形状节点渲染
|
||||||
|
* - 输入事件处理
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <extra2d/extra2d.h>
|
#include <extra2d/extra2d.h>
|
||||||
#include <extra2d/graphics/render_config.h>
|
|
||||||
#include <extra2d/platform/window_config.h>
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
|
|
||||||
using namespace extra2d;
|
using namespace extra2d;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief 创建场景图测试
|
||||||
|
*/
|
||||||
|
void createSceneGraph(Scene *scene) {
|
||||||
|
float width = scene->getWidth();
|
||||||
|
float height = scene->getHeight();
|
||||||
|
|
||||||
|
auto root = makeShared<Node>();
|
||||||
|
root->setName("Root");
|
||||||
|
root->setPos(width / 2, height / 2);
|
||||||
|
scene->addChild(root);
|
||||||
|
|
||||||
|
auto parent1 = makeShared<Node>();
|
||||||
|
parent1->setName("Parent1");
|
||||||
|
parent1->setPos(-200, 0);
|
||||||
|
root->addChild(parent1);
|
||||||
|
|
||||||
|
auto rect1 = ShapeNode::createFilledRect(Rect(-50, -50, 100, 100),
|
||||||
|
Color(1.0f, 0.4f, 0.4f, 1.0f));
|
||||||
|
rect1->setName("RedRect");
|
||||||
|
parent1->addChild(rect1);
|
||||||
|
|
||||||
|
auto child1 = makeShared<Node>();
|
||||||
|
child1->setName("Child1");
|
||||||
|
child1->setPos(80, 0);
|
||||||
|
child1->setRotation(45);
|
||||||
|
child1->setScale(0.5f);
|
||||||
|
parent1->addChild(child1);
|
||||||
|
|
||||||
|
auto smallRect = ShapeNode::createFilledRect(Rect(-30, -30, 60, 60),
|
||||||
|
Color(1.0f, 0.8f, 0.4f, 1.0f));
|
||||||
|
smallRect->setName("OrangeRect");
|
||||||
|
child1->addChild(smallRect);
|
||||||
|
|
||||||
|
auto parent2 = makeShared<Node>();
|
||||||
|
parent2->setName("Parent2");
|
||||||
|
parent2->setPos(200, 0);
|
||||||
|
root->addChild(parent2);
|
||||||
|
|
||||||
|
auto circle1 = ShapeNode::createFilledCircle(Vec2(0, 0), 60,
|
||||||
|
Color(0.4f, 0.4f, 1.0f, 1.0f));
|
||||||
|
circle1->setName("BlueCircle");
|
||||||
|
parent2->addChild(circle1);
|
||||||
|
|
||||||
|
auto child2 = makeShared<Node>();
|
||||||
|
child2->setName("Child2");
|
||||||
|
child2->setPos(0, 100);
|
||||||
|
parent2->addChild(child2);
|
||||||
|
|
||||||
|
auto triangle = ShapeNode::createFilledTriangle(
|
||||||
|
Vec2(0, -40), Vec2(-35, 30), Vec2(35, 30), Color(0.4f, 1.0f, 0.4f, 1.0f));
|
||||||
|
triangle->setName("GreenTriangle");
|
||||||
|
child2->addChild(triangle);
|
||||||
|
|
||||||
|
auto line = ShapeNode::createLine(Vec2(-300, -200), Vec2(300, -200),
|
||||||
|
Color(1.0f, 1.0f, 1.0f, 1.0f), 2.0f);
|
||||||
|
line->setName("BottomLine");
|
||||||
|
root->addChild(line);
|
||||||
|
|
||||||
|
auto polygon = ShapeNode::createFilledPolygon(
|
||||||
|
{Vec2(0, -50), Vec2(50, 0), Vec2(30, 50), Vec2(-30, 50), Vec2(-50, 0)},
|
||||||
|
Color(1.0f, 0.4f, 1.0f, 1.0f));
|
||||||
|
polygon->setName("PurplePolygon");
|
||||||
|
polygon->setPos(0, -150);
|
||||||
|
root->addChild(polygon);
|
||||||
|
|
||||||
|
std::cout << "\n=== Scene Graph Structure ===" << std::endl;
|
||||||
|
std::cout << "Scene (root)" << std::endl;
|
||||||
|
std::cout << " └── Root (center)" << std::endl;
|
||||||
|
std::cout << " ├── Parent1 (left)" << std::endl;
|
||||||
|
std::cout << " │ ├── RedRect (100x100)" << std::endl;
|
||||||
|
std::cout << " │ └── Child1 (rotated 45°, scaled 0.5)" << std::endl;
|
||||||
|
std::cout << " │ └── OrangeRect (60x60)" << std::endl;
|
||||||
|
std::cout << " ├── Parent2 (right)" << std::endl;
|
||||||
|
std::cout << " │ ├── BlueCircle (radius 60)" << std::endl;
|
||||||
|
std::cout << " │ └── Child2 (below)" << std::endl;
|
||||||
|
std::cout << " │ └── GreenTriangle" << std::endl;
|
||||||
|
std::cout << " ├── BottomLine" << std::endl;
|
||||||
|
std::cout << " └── PurplePolygon (pentagon)" << std::endl;
|
||||||
|
std::cout << "=============================\n" << std::endl;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief 主函数
|
* @brief 主函数
|
||||||
*
|
|
||||||
* 初始化应用程序,创建场景,运行主循环。
|
|
||||||
*/
|
*/
|
||||||
int main(int argc, char *argv[]) {
|
int main(int argc, char *argv[]) {
|
||||||
(void)argc;
|
(void)argc;
|
||||||
(void)argv;
|
(void)argv;
|
||||||
|
|
||||||
std::cout << "Extra2D Demo - Starting..." << std::endl;
|
std::cout << "Extra2D Scene Graph Demo - Starting..." << std::endl;
|
||||||
|
|
||||||
AppConfig config = AppConfig::createDefault();
|
AppConfig config = AppConfig::createDefault();
|
||||||
config.appName = "Extra2D Demo";
|
config.appName = "Extra2D Scene Graph Demo";
|
||||||
config.appVersion = "1.0.0";
|
config.appVersion = "1.0.0";
|
||||||
|
|
||||||
Application &app = Application::get();
|
Application &app = Application::get();
|
||||||
|
|
@ -37,15 +119,40 @@ int main(int argc, char *argv[]) {
|
||||||
std::cout << "Application initialized successfully!" << std::endl;
|
std::cout << "Application initialized successfully!" << std::endl;
|
||||||
std::cout << "Window: " << app.window().width() << "x"
|
std::cout << "Window: " << app.window().width() << "x"
|
||||||
<< app.window().height() << std::endl;
|
<< app.window().height() << std::endl;
|
||||||
std::cout << "Running main loop. Press ESC or close window to exit."
|
|
||||||
|
auto eventService = app.events();
|
||||||
|
if (eventService) {
|
||||||
|
eventService->addListener(EventType::KeyPressed, [](Event &e) {
|
||||||
|
auto &keyEvent = std::get<KeyEvent>(e.data);
|
||||||
|
|
||||||
|
if (keyEvent.keyCode == static_cast<int>(Key::Escape)) {
|
||||||
|
e.handled = true;
|
||||||
|
Application::get().quit();
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
eventService->addListener(EventType::MouseButtonPressed, [](Event &e) {
|
||||||
|
auto &mouseEvent = std::get<MouseButtonEvent>(e.data);
|
||||||
|
std::cout << "[Click] Button " << mouseEvent.button << " at ("
|
||||||
|
<< mouseEvent.position.x << ", " << mouseEvent.position.y << ")"
|
||||||
<< std::endl;
|
<< std::endl;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
auto scene = Scene::create();
|
auto scene = Scene::create();
|
||||||
scene->setBackgroundColor(Colors::SkyBlue);
|
scene->setBackgroundColor(Color(0.12f, 0.12f, 0.16f, 1.0f));
|
||||||
scene->setViewportSize(static_cast<float>(app.window().width()),
|
scene->setViewportSize(static_cast<float>(app.window().width()),
|
||||||
static_cast<float>(app.window().height()));
|
static_cast<float>(app.window().height()));
|
||||||
|
|
||||||
|
createSceneGraph(scene.get());
|
||||||
|
|
||||||
app.enterScene(scene);
|
app.enterScene(scene);
|
||||||
|
|
||||||
|
std::cout << "\nControls:" << std::endl;
|
||||||
|
std::cout << " ESC - Exit" << std::endl;
|
||||||
|
std::cout << " Mouse Click - Print position" << std::endl;
|
||||||
|
std::cout << "\nRunning main loop...\n" << std::endl;
|
||||||
|
|
||||||
app.run();
|
app.run();
|
||||||
|
|
||||||
std::cout << "Shutting down..." << std::endl;
|
std::cout << "Shutting down..." << std::endl;
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue