Cherno视频:https://www.youtube.com/watch?v=4zj-0FQ7Xbg&list=PLlrATfBNZ98dC-V-N3m0Go4deliWHPFwT&index=36
完整代码:https://github.com/DXT00/Hazel_study/tree/cd781b6ae9883f0884ccbf06bc0b5fa789fcdd1b/Hazel
把渲染从Hazel::Applicatioin移到SandBox
并通过按键控制相机移动
方法一:使用Event 控制相机移动
缺点--》有事件就响应,移动不连续
#include <Hazel.h>
#include "imgui/imgui.h"
class ExampleLayer : public Hazel::Layer
{
public:
ExampleLayer()
: Layer("Example"), m_Camera(-1.6f, 1.6f, -0.9f, 0.9f) //对应窗口大小 1280 :720
{
float vertices[3 * 7] = {
//Position //Color
-0.3f,-0.3f,0.0f, 1.0f,0.0f,0.0f,1.0f,
0.3f,-0.3f,0.0f, 0.0f,1.0f,0.0f,1.0f,
0.0f, 0.3f,0.0f, 0.0f,0.0f,1.0f,1.0f,
};
float squareVertices[3 * 4] = {
//Position //Color
-0.5f, -0.5f, 0.0f,
0.5f, -0.5f, 0.0f,
0.5f, 0.5f, 0.0f,
-0.5f, 0.5f, 0.0f,
};
unsigned int indices[3] = { 0,1,2 };
unsigned int squareIndices[6] = { 0,1,2,0,2,3 };
Hazel::BufferLayout layout = {
{ Hazel::ShaderDataType::Float3,"a_Position", false },
{ Hazel::ShaderDataType::Float4,"a_Color", false },
};
Hazel::BufferLayout squareLayout = {
{ Hazel::ShaderDataType::Float3,"a_Position", false },
};
std::shared_ptr< Hazel::VertexBuffer>vertexBuffer;
std::shared_ptr< Hazel::IndexBuffer> indexBuffer;
m_VertexArray.reset(Hazel::VertexArray::Create());
vertexBuffer.reset(Hazel::VertexBuffer::Create(vertices, sizeof(vertices)));
indexBuffer.reset(Hazel::IndexBuffer::Create(indices, 3));
vertexBuffer->SetLayout(layout);
m_VertexArray->AddVertexBuffer(vertexBuffer);
m_VertexArray->SetIndexBuffer(indexBuffer);
std::shared_ptr< Hazel::VertexBuffer>squareVB;
std::shared_ptr< Hazel::IndexBuffer> squareIB;
m_SquareVA.reset(Hazel::VertexArray::Create());
squareVB.reset(Hazel::VertexBuffer::Create(squareVertices, sizeof(squareVertices)));
squareIB.reset(Hazel::IndexBuffer::Create(squareIndices, 6));
squareVB->SetLayout(squareLayout);
m_SquareVA->AddVertexBuffer(squareVB);
m_SquareVA->SetIndexBuffer(squareIB);
const std::string vertexSrc = R"(
#version 330 core
layout(location = 0) in vec3 a_Position;
layout(location = 1) in vec4 a_Color;
out vec3 v_Position;
out vec4 v_Color;
uniform mat4 u_ViewProjection;
void main()
{
v_Position = a_Position;
v_Color = a_Color;
gl_Position = u_ViewProjection * vec4(a_Position,1.0f);
}
)";
const std::string fragmentSrc = R"(
#version 330 core
layout(location = 0) out vec4 color;
layout(location = 1) out vec4 color1;
in vec3 v_Position;
in vec4 v_Color;
void main()
{
color = v_Color;//vec4(v_Position*0.5+0.5, 1.0);
}
)";
const std::string squareVertexSrc = R"(
#version 330 core
layout(location = 0) in vec3 a_Position;
uniform mat4 u_ViewProjection;
out vec3 v_Position;
void main()
{
v_Position = a_Position;
gl_Position = u_ViewProjection * vec4(a_Position,1.0);
}
)";
const std::string squareFragmentSrc = R"(
#version 330 core
layout(location = 0) out vec4 color;
in vec3 v_Position;
void main()
{
color =vec4(v_Position*0.5+0.5, 1.0);
}
)";
//m_Shader = std::make_unique<Shader>(vertexSrc,fragmentSrc);
m_Shader.reset(new Hazel::Shader(vertexSrc, fragmentSrc));
m_SquareShader.reset(new Hazel::Shader(squareVertexSrc, squareFragmentSrc));
}
void OnUpdate() override
{
Hazel::RenderCommand::SetClearColor({ 0.1f, 0.1f, 0.1f, 1 });
Hazel::RenderCommand::Clear();
/* m_Camera.SetPosition({ 0.5f,0.5f,0.0f });
m_Camera.SetRotation(45);*/
Hazel::Renderer::BeginScene(m_Camera);
Hazel::Renderer::Submit(m_SquareVA, m_SquareShader);
Hazel::Renderer::Submit(m_VertexArray, m_Shader);
Hazel::Renderer::EndScene();
}
virtual void OnImGuiRender() override
{
}
void OnEvent(Hazel::Event& event) override
{
Hazel::EventDispatcher dispatcher(event);
dispatcher.Dispatch<Hazel::KeyPressedEvent>(HZ_BIND_EVENT_FN(ExampleLayer::KeyPressedHandle));
}
bool KeyPressedHandle(Hazel::KeyPressedEvent& event) {
if (event.GetKeyCode() == HZ_KEY_LEFT)
{
m_Camera.SetPosition({ m_Camera.GetPosition().x - m_MoveSpeed, m_Camera.GetPosition().y, m_Camera.GetPosition().z });
}
if (event.GetKeyCode() == HZ_KEY_RIGHT)
{
m_Camera.SetPosition({ m_Camera.GetPosition().x + m_MoveSpeed, m_Camera.GetPosition().y, m_Camera.GetPosition().z });
}
if (event.GetKeyCode() == HZ_KEY_UP)
{
m_Camera.SetRotation(m_Camera.GetRotation()+m_RotateSpeed);
}
if (event.GetKeyCode() == HZ_KEY_DOWN)
{
m_Camera.SetRotation(m_Camera.GetRotation()- m_RotateSpeed);
}
return false;
}
public:
inline Hazel::OrthographicCamera& GetCamera() { return m_Camera; }
public:
std::shared_ptr<Hazel::VertexArray> m_VertexArray;
std::shared_ptr<Hazel::Shader> m_Shader;
std::shared_ptr<Hazel::VertexArray> m_SquareVA;
std::shared_ptr<Hazel::Shader> m_SquareShader;
private:
Hazel::OrthographicCamera m_Camera;
glm::vec3 m_CameraPosition = { 0.0f,0.0f,0.0f };
float m_MoveSpeed = 1;
float m_CameraRotation = 0;
float m_RotateSpeed = 10;
};
class Sandbox : public Hazel::Application
{
public:
Sandbox()
{
PushLayer(new ExampleLayer());
}
~Sandbox()
{
}
};
Hazel::Application* Hazel::CreateApplication()
{
return new Sandbox();
}
方法二: 通过Input类在Update()中控制相机移动,旋转,由于帧率一定,所以是连续的!
#include <Hazel.h>
#include "imgui/imgui.h"
class ExampleLayer : public Hazel::Layer
{
public:
ExampleLayer()
: Layer("Example"), m_Camera(-1.6f, 1.6f, -0.9f, 0.9f) //对应窗口大小 1280 :720
{
float vertices[3 * 7] = {
//Position //Color
-0.3f,-0.3f,0.0f, 1.0f,0.0f,0.0f,1.0f,
0.3f,-0.3f,0.0f, 0.0f,1.0f,0.0f,1.0f,
0.0f, 0.3f,0.0f, 0.0f,0.0f,1.0f,1.0f,
};
float squareVertices[3 * 4] = {
//Position //Color
-0.5f, -0.5f, 0.0f,
0.5f, -0.5f, 0.0f,
0.5f, 0.5f, 0.0f,
-0.5f, 0.5f, 0.0f,
};
unsigned int indices[3] = { 0,1,2 };
unsigned int squareIndices[6] = { 0,1,2,0,2,3 };
Hazel::BufferLayout layout = {
{ Hazel::ShaderDataType::Float3,"a_Position", false },
{ Hazel::ShaderDataType::Float4,"a_Color", false },
};
Hazel::BufferLayout squareLayout = {
{ Hazel::ShaderDataType::Float3,"a_Position", false },
};
std::shared_ptr< Hazel::VertexBuffer>vertexBuffer;
std::shared_ptr< Hazel::IndexBuffer> indexBuffer;
m_VertexArray.reset(Hazel::VertexArray::Create());
vertexBuffer.reset(Hazel::VertexBuffer::Create(vertices, sizeof(vertices)));
indexBuffer.reset(Hazel::IndexBuffer::Create(indices, 3));
vertexBuffer->SetLayout(layout);
m_VertexArray->AddVertexBuffer(vertexBuffer);
m_VertexArray->SetIndexBuffer(indexBuffer);
std::shared_ptr< Hazel::VertexBuffer>squareVB;
std::shared_ptr< Hazel::IndexBuffer> squareIB;
m_SquareVA.reset(Hazel::VertexArray::Create());
squareVB.reset(Hazel::VertexBuffer::Create(squareVertices, sizeof(squareVertices)));
squareIB.reset(Hazel::IndexBuffer::Create(squareIndices, 6));
squareVB->SetLayout(squareLayout);
m_SquareVA->AddVertexBuffer(squareVB);
m_SquareVA->SetIndexBuffer(squareIB);
const std::string vertexSrc = R"(
#version 330 core
layout(location = 0) in vec3 a_Position;
layout(location = 1) in vec4 a_Color;
out vec3 v_Position;
out vec4 v_Color;
uniform mat4 u_ViewProjection;
void main()
{
v_Position = a_Position;
v_Color = a_Color;
gl_Position = u_ViewProjection * vec4(a_Position,1.0f);
}
)";
const std::string fragmentSrc = R"(
#version 330 core
layout(location = 0) out vec4 color;
layout(location = 1) out vec4 color1;
in vec3 v_Position;
in vec4 v_Color;
void main()
{
color = v_Color;//vec4(v_Position*0.5+0.5, 1.0);
}
)";
const std::string squareVertexSrc = R"(
#version 330 core
layout(location = 0) in vec3 a_Position;
uniform mat4 u_ViewProjection;
out vec3 v_Position;
void main()
{
v_Position = a_Position;
gl_Position = u_ViewProjection * vec4(a_Position,1.0);
}
)";
const std::string squareFragmentSrc = R"(
#version 330 core
layout(location = 0) out vec4 color;
in vec3 v_Position;
void main()
{
color =vec4(v_Position*0.5+0.5, 1.0);
}
)";
//m_Shader = std::make_unique<Shader>(vertexSrc,fragmentSrc);
m_Shader.reset(new Hazel::Shader(vertexSrc, fragmentSrc));
m_SquareShader.reset(new Hazel::Shader(squareVertexSrc, squareFragmentSrc));
}
void OnUpdate() override
{
if (Hazel::Input::IsKeyPressed(HZ_KEY_LEFT))
{
m_CameraPosition.x -= m_MoveSpeed;
}
else if (Hazel::Input::IsKeyPressed(HZ_KEY_RIGHT))
{
m_CameraPosition.x += m_MoveSpeed;
}
if (Hazel::Input::IsKeyPressed(HZ_KEY_UP))
{
m_CameraPosition.y += m_MoveSpeed;
}
else if (Hazel::Input::IsKeyPressed(HZ_KEY_DOWN))
{
m_CameraPosition.y -= m_MoveSpeed;
}
if (Hazel::Input::IsKeyPressed(HZ_KEY_A))
{
m_CameraRotation -= m_RotateSpeed;
}
else if (Hazel::Input::IsKeyPressed(HZ_KEY_D))
{
m_CameraRotation += m_RotateSpeed;
}
Hazel::RenderCommand::SetClearColor({ 0.1f, 0.1f, 0.1f, 1 });
Hazel::RenderCommand::Clear();
/* m_Camera.SetPosition({ 0.5f,0.5f,0.0f });
m_Camera.SetRotation(45);*/
m_Camera.SetPosition(m_CameraPosition);
m_Camera.SetRotation(m_CameraRotation);
Hazel::Renderer::BeginScene(m_Camera);
Hazel::Renderer::Submit(m_SquareVA, m_SquareShader);
Hazel::Renderer::Submit(m_VertexArray, m_Shader);
Hazel::Renderer::EndScene();
}
virtual void OnImGuiRender() override
{
}
void OnEvent(Hazel::Event& event) override
{
/*Hazel::EventDispatcher dispatcher(event);
dispatcher.Dispatch<Hazel::KeyPressedEvent>(HZ_BIND_EVENT_FN(ExampleLayer::KeyPressedHandle));
*/
}
//bool KeyPressedHandle(Hazel::KeyPressedEvent& event) {
// if (event.GetKeyCode() == HZ_KEY_LEFT)
// {
// m_Camera.SetPosition({ m_Camera.GetPosition().x - m_MoveSpeed, m_Camera.GetPosition().y, m_Camera.GetPosition().z });
// }
// if (event.GetKeyCode() == HZ_KEY_RIGHT)
// {
// m_Camera.SetPosition({ m_Camera.GetPosition().x + m_MoveSpeed, m_Camera.GetPosition().y, m_Camera.GetPosition().z });
// }
// if (event.GetKeyCode() == HZ_KEY_UP)
// {
// m_Camera.SetRotation(m_Camera.GetRotation()+m_RotateSpeed);
// }
// if (event.GetKeyCode() == HZ_KEY_DOWN)
// {
// m_Camera.SetRotation(m_Camera.GetRotation()- m_RotateSpeed);
// }
// return false;
//}
public:
inline Hazel::OrthographicCamera& GetCamera() { return m_Camera; }
public:
std::shared_ptr<Hazel::VertexArray> m_VertexArray;
std::shared_ptr<Hazel::Shader> m_Shader;
std::shared_ptr<Hazel::VertexArray> m_SquareVA;
std::shared_ptr<Hazel::Shader> m_SquareShader;
private:
Hazel::OrthographicCamera m_Camera;
glm::vec3 m_CameraPosition = { 0.0f,0.0f,0.0f };
float m_MoveSpeed = 0.1;
float m_CameraRotation = 0;
float m_RotateSpeed = 10;
};
class Sandbox : public Hazel::Application
{
public:
Sandbox()
{
PushLayer(new ExampleLayer());
}
~Sandbox()
{
}
};
Hazel::Application* Hazel::CreateApplication()
{
return new Sandbox();
}