Added picking event

This commit is contained in:
viktorljung
2015-12-10 16:33:33 +01:00
parent aa805f9a41
commit bb900c5110
5 changed files with 94 additions and 26 deletions
+69
View File
@@ -0,0 +1,69 @@
#ifndef Events_Picking_h__
#define Events_Picking_h__
#include "../OpenGL.h"
#include "../GLM.h"
#include "../Core/EventBroker.h"
#include "Util/ScreenCoords.h"
#include "FrameBuffer.h"
#include "../Core/Entity.h"
#include "Util/UnorderedMapVec2.h"
namespace Events
{
/** Thrown Every frame, use functions to pick*/
struct Picking : Event
{
public:
Picking(FrameBuffer* pickingBuffer, GLuint* depthBuffer, glm::mat4 projectionMatrix, glm::mat4 viewMatrix, Rectangle resolution, const std::unordered_map<glm::vec2, EntityID>* pickingColorsToEntity)
: PickingBuffer(pickingBuffer)
, DepthBuffer(depthBuffer)
, ProjectionMatrix(projectionMatrix)
, ViewMatrix(viewMatrix)
, Resolution(resolution)
, PickingColorsToEntity(pickingColorsToEntity)
{ }
struct PickData
{
//Picked Entity
EntityID Entity;
//World position of the "pick"
glm::vec3 Position;
};
PickData Pick(glm::vec2 screenCoord) const
{
PickData pickData;
ScreenCoords::PixelData data = ScreenCoords::ToPixelData(screenCoord, PickingBuffer, *DepthBuffer);
auto it = PickingColorsToEntity->find(glm::vec2(data.Color[0], data.Color[1]));
if (it != PickingColorsToEntity->end()) {
pickData.Entity = it->second;
} else {
pickData.Entity = -1;
}
pickData.Position = ScreenCoords::ToWorldPos(screenCoord.x, Resolution.Width - screenCoord.y, data.Depth, Resolution, ProjectionMatrix, ViewMatrix);
return pickData;
}
private:
FrameBuffer* PickingBuffer;
GLuint* DepthBuffer;
const glm::mat4 ProjectionMatrix;
const glm::mat4 ViewMatrix;
const Rectangle Resolution;
const std::unordered_map<glm::vec2, EntityID>* PickingColorsToEntity;
};
}
#endif
+9 -2
View File
@@ -11,15 +11,24 @@
#include "FrameBuffer.h"
#include "../Core/World.h"
#include "../Core/EventBroker.h"
#include "EPicking.h"
class Renderer : public IRenderer
{
public:
Renderer(EventBroker* eventBroker)
: m_EventBroker(eventBroker)
{ }
virtual void Initialize() override;
virtual void Update(double dt) override;
virtual void Draw(RenderQueueCollection& rq) override;
private:
//----------------------Variables----------------------//
EventBroker* m_EventBroker;
Texture* m_ErrorTexture;
Texture* m_WhiteTexture;
float m_CameraMoveSpeed;
@@ -31,8 +40,6 @@ private:
Model* m_UnitQuad;
Model* m_UnitSphere;
std::unordered_map<glm::vec2, EntityID> m_PickingColorsToEntity;
//----------------------Functions----------------------//
+13 -22
View File
@@ -3,7 +3,6 @@
void Renderer::Initialize()
{
InitializeWindow();
// Create default camera
m_DefaultCamera = new ::Camera((float)m_Resolution.Width / m_Resolution.Height, glm::radians(45.f), 0.01f, 5000.f);
m_DefaultCamera->SetPosition(glm::vec3(0, 0, 10));
@@ -116,26 +115,6 @@ void Renderer::InputUpdate(double dt)
static double mousePosX, mousePosY;
glfwGetCursorPos(m_Window, &mousePosX, &mousePosY);
if (glfwGetMouseButton(m_Window, GLFW_MOUSE_BUTTON_1) == GLFW_PRESS) {
ScreenCoords::PixelData data = ScreenCoords::ToPixelData(mousePosX, m_Resolution.Height - mousePosY, &m_PickingBuffer, m_DepthBuffer);
glm::vec3 viewPos = ScreenCoords::ToWorldPos(mousePosX, m_Resolution.Height - mousePosY, data.Depth, m_Resolution, m_Camera->ProjectionMatrix(), m_Camera->ViewMatrix());
// glm::vec3 worldPos = glm::vec3(glm::inverse(m_Camera->ViewMatrix()) * glm::vec4(viewPos, 1.f));
//printf("R: %f, G: %f, Depth: %f\n", data.Color[0], data.Color[1], data.Depth);
//printf("view: x: %f, y: %f z: %f, Length: %f\n\n", viewPos.x, viewPos.y, viewPos.z, glm::length(viewPos));
//printf("\n\n---------------------------\n");
auto got = m_PickingColorsToEntity.find(glm::vec2(data.Color[0], data.Color[1]));
if (got == m_PickingColorsToEntity.end())
printf("Color (R:%f, G:%f) not found.\n", data.Color[0], data.Color[1]);
else
printf("R:%f G:%f, EntityID: %i\n", got->first.r, got->first.g, got->second);
//printf("----\n");
//for (auto i : m_PickingColorsToEntity) {
// printf("Entity: %i, Color: R: %f, G: %f\n", i.second, i.first.r, i.first.g);
//}
//printf("---------------------------\n\n");
}
if (glfwGetKey(m_Window, GLFW_KEY_SPACE) == GLFW_PRESS) {
@@ -161,7 +140,8 @@ void Renderer::InputUpdate(double dt)
void Renderer::Update(double dt)
{
InputUpdate(dt);
m_EventBroker->Process<Renderer>();
InputUpdate(dt);
}
@@ -276,6 +256,17 @@ void Renderer::PickingPass(RenderQueueCollection& rq)
m_PickingBuffer.Unbind();
GLERROR("PickingPass Error");
//Publish pick event every frame with the pick data that can be picked by the event
Events::Picking pickEvent = Events::Picking(
&m_PickingBuffer,
&m_DepthBuffer,
m_Camera->ProjectionMatrix(),
m_Camera->ViewMatrix(),
m_Resolution,
&m_PickingColorsToEntity);
m_EventBroker->Publish(pickEvent);
}
@@ -56,3 +56,4 @@ ScreenCoords::PixelData ScreenCoords::ToPixelData(glm::vec2 screenCoord, FrameBu
{
return ToPixelData(screenCoord.x, screenCoord.y, PickDataBuffer, DepthBuffer);
}
+2 -2
View File
@@ -16,7 +16,7 @@ Game::Game(int argc, char* argv[])
m_RenderQueueFactory = new RenderQueueFactory();
// Create the renderer
m_Renderer = new Renderer();
m_Renderer = new Renderer(m_EventBroker);
m_Renderer->SetFullscreen(m_Config->Get<bool>("Video.Fullscreen", false));
m_Renderer->SetVSYNC(m_Config->Get<bool>("Video.VSYNC", false));
m_Renderer->SetResolution(Rectangle(
@@ -65,12 +65,12 @@ void Game::Tick()
m_EventBroker->Swap();
m_InputManager->Update(dt);
m_Renderer->Update(dt);
m_EventBroker->Swap();
// Iterate through systems and update world!
m_SystemPipeline->Update(m_World, dt);
testTick(dt);
m_Renderer->Update(dt);
m_RenderQueueFactory->Update(m_World);
m_Renderer->Draw(m_RenderQueueFactory->RenderQueues());