add mouse picking, add more hdr environment maps
This commit is contained in:
+121
-13
@@ -149,7 +149,7 @@ namespace Prism
|
||||
|
||||
auto secondEntity = m_Scene->CreateEntity("Gun Entity");
|
||||
secondEntity->Transform() = glm::translate(glm::mat4(1.0f), { 5, 5, 5 }) * glm::scale(glm::mat4(1.0f), {10, 10, 10});
|
||||
mesh = CreateRef<Mesh>("assets/models/m1911/m1911.fbx");
|
||||
mesh = CreateRef<Mesh>("assets/models/m1911/m1911Materials.fbx");
|
||||
secondEntity->SetMesh(mesh);
|
||||
}
|
||||
|
||||
@@ -208,9 +208,12 @@ namespace Prism
|
||||
// Editor
|
||||
m_CheckerboardTex = Texture2D::Create("assets/editor/Checkerboard.tga");
|
||||
|
||||
// lights
|
||||
m_Light.Direction = {-0.5f, -0.5f, 1.0f};
|
||||
m_Light.Radiance = {1.0f, 1.0f, 1.0f};
|
||||
// set lights
|
||||
auto& light = m_Scene->GetLight();
|
||||
light.Direction = { -0.5f, -0.5f, 1.0f };
|
||||
light.Radiance = { 1.0f, 1.0f, 1.0f };
|
||||
|
||||
m_CurrentlySelectedTransform = &m_MeshEntity->Transform();
|
||||
}
|
||||
|
||||
void EditorLayer::OnDetach()
|
||||
@@ -228,7 +231,6 @@ namespace Prism
|
||||
m_MeshMaterial->Set("u_AlbedoColor", m_AlbedoInput.Color);
|
||||
m_MeshMaterial->Set("u_Metalness", m_MetalnessInput.Value);
|
||||
m_MeshMaterial->Set("u_Roughness", m_RoughnessInput.Value);
|
||||
m_MeshMaterial->Set("lights", m_Light);
|
||||
m_MeshMaterial->Set("u_AlbedoTexToggle", m_AlbedoInput.UseTexture ? 1.0f : 0.0f);
|
||||
m_MeshMaterial->Set("u_NormalTexToggle", m_NormalInput.UseTexture ? 1.0f : 0.0f);
|
||||
m_MeshMaterial->Set("u_MetalnessTexToggle", m_MetalnessInput.UseTexture ? 1.0f : 0.0f);
|
||||
@@ -236,7 +238,8 @@ namespace Prism
|
||||
m_MeshMaterial->Set("u_EnvMapRotation", m_EnvMapRotation);
|
||||
|
||||
m_SphereBaseMaterial->Set("u_AlbedoColor", m_AlbedoInput.Color);
|
||||
m_SphereBaseMaterial->Set("lights", m_Light);
|
||||
// m_SphereBaseMaterial->Set("lights", m_Light);
|
||||
m_SphereBaseMaterial->Set("lights", m_Scene->GetLight());
|
||||
m_SphereBaseMaterial->Set("u_RadiancePrefilter", m_RadiancePrefilter ? 1.0f : 0.0f);
|
||||
m_SphereBaseMaterial->Set("u_AlbedoTexToggle", m_AlbedoInput.UseTexture ? 1.0f : 0.0f);
|
||||
m_SphereBaseMaterial->Set("u_NormalTexToggle", m_NormalInput.UseTexture ? 1.0f : 0.0f);
|
||||
@@ -264,8 +267,19 @@ namespace Prism
|
||||
Renderer::BeginRenderPass(SceneRenderer::GetFinalRenderPass(), false);
|
||||
auto viewProj = m_Scene->GetCamera().GetViewProjection();
|
||||
Renderer2D::BeginScene(viewProj, false);
|
||||
// Prism::Renderer2D::DrawQuad({ 0, 0, 0 }, { 4.0f, 5.0f }, { 1.0f, 1.0f, 0.5f, 1.0f });
|
||||
Renderer::DrawAABB(m_MeshEntity->GetMesh());
|
||||
Renderer::DrawAABB(m_MeshEntity->GetMesh(), m_MeshEntity->Transform());
|
||||
|
||||
Renderer2D::EndScene();
|
||||
Renderer::EndRenderPass();
|
||||
}
|
||||
|
||||
if (!m_SelectedSubmeshes.empty())
|
||||
{
|
||||
Renderer::BeginRenderPass(SceneRenderer::GetFinalRenderPass(), false);
|
||||
const auto viewProj = m_Scene->GetCamera().GetViewProjection();
|
||||
Renderer2D::BeginScene(viewProj, false);
|
||||
const auto& submesh = m_SelectedSubmeshes[0];
|
||||
Renderer::DrawAABB(submesh.Mesh->BoundingBox, m_MeshEntity->GetTransform() * submesh.Mesh->Transform);
|
||||
Renderer2D::EndScene();
|
||||
Renderer::EndRenderPass();
|
||||
}
|
||||
@@ -441,9 +455,10 @@ namespace Prism
|
||||
ImGui::Columns(2);
|
||||
ImGui::AlignTextToFramePadding();
|
||||
|
||||
Property("Light Direction", m_Light.Direction);
|
||||
Property("Light Radiance", m_Light.Radiance, PropertyFlag::ColorProperty);
|
||||
Property("Light Multiplier", m_LightMultiplier, 0.0f, 5.0f);
|
||||
auto& light = m_Scene->GetLight();
|
||||
Property("Light Direction", light.Direction);
|
||||
Property("Light Radiance", light.Radiance, PropertyFlag::ColorProperty);
|
||||
Property("Light Multiplier", light.Multiplier, 0.0f, 5.0f);
|
||||
Property("Exposure", m_ActiveScene->GetCamera().GetExposure(), 0.0f, 5.0f);
|
||||
|
||||
Property("Radiance Prefiltering", m_RadiancePrefilter);
|
||||
@@ -642,6 +657,8 @@ namespace Prism
|
||||
|
||||
ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(0, 0));
|
||||
ImGui::Begin("Viewport");
|
||||
|
||||
auto viewportOffset = ImGui::GetCursorPos(); // includes tab bar
|
||||
auto viewportSize = ImGui::GetContentRegionAvail();
|
||||
SceneRenderer::SetViewportSize((uint32_t)viewportSize.x, (uint32_t)viewportSize.y);
|
||||
m_ActiveScene->GetCamera().SetProjectionMatrix(glm::perspectiveFov(glm::radians(45.0f), viewportSize.x, viewportSize.y, 0.1f, 10000.0f));
|
||||
@@ -649,13 +666,19 @@ namespace Prism
|
||||
ImGui::Image((ImTextureRef)SceneRenderer::GetFinalColorBufferRendererID(), viewportSize, { 0, 1 }, { 1, 0 });
|
||||
|
||||
|
||||
static int counter = 0;
|
||||
auto windowSize = ImGui::GetWindowSize();
|
||||
ImVec2 minBound = ImGui::GetWindowPos();
|
||||
minBound.x += viewportOffset.x;
|
||||
minBound.y += viewportOffset.y;
|
||||
|
||||
ImVec2 maxBound = { minBound.x + windowSize.x, minBound.y + windowSize.y };
|
||||
m_ViewportBounds[0] = { minBound.x, minBound.y };
|
||||
m_ViewportBounds[1] = { maxBound.x, maxBound.y };
|
||||
m_AllowViewportCameraEvents = ImGui::IsMouseHoveringRect(minBound, maxBound);
|
||||
|
||||
// ImGuizmo
|
||||
if (m_GizmoType != -1)
|
||||
if (m_GizmoType != -1 && m_CurrentlySelectedTransform)
|
||||
{
|
||||
const auto rw = (float)ImGui::GetWindowWidth();
|
||||
const auto rh = (float)ImGui::GetWindowHeight();
|
||||
@@ -663,7 +686,15 @@ namespace Prism
|
||||
ImGuizmo::SetDrawlist();
|
||||
ImGuizmo::SetRect(ImGui::GetWindowPos().x, ImGui::GetWindowPos().y, rw, rh);
|
||||
const auto& camera = m_ActiveScene->GetCamera();
|
||||
ImGuizmo::Manipulate(glm::value_ptr(camera.GetViewMatrix()), glm::value_ptr(camera.GetProjectionMatrix()), (ImGuizmo::OPERATION)m_GizmoType, ImGuizmo::LOCAL, glm::value_ptr(m_MeshEntity->Transform()));
|
||||
|
||||
bool snap = Input::IsKeyPressed(PM_KEY_LEFT_CONTROL);
|
||||
ImGuizmo::Manipulate(glm::value_ptr(camera.GetViewMatrix()),
|
||||
glm::value_ptr(camera.GetProjectionMatrix()),
|
||||
(ImGuizmo::OPERATION)m_GizmoType,
|
||||
ImGuizmo::LOCAL,
|
||||
glm::value_ptr(m_MeshEntity->Transform()),
|
||||
nullptr,
|
||||
snap ? &m_SnapValue : nullptr);
|
||||
}
|
||||
|
||||
ImGui::End();
|
||||
@@ -678,6 +709,7 @@ namespace Prism
|
||||
|
||||
EventDispatcher dispatcher(e);
|
||||
dispatcher.Dispatch<KeyPressedEvent>(PM_BIND_EVENT_FN(EditorLayer::OnKeyPressedEvent));
|
||||
dispatcher.Dispatch<MouseButtonPressedEvent>(PM_BIND_EVENT_FN(EditorLayer::OnMouseButtonPressedEvent));
|
||||
}
|
||||
|
||||
bool EditorLayer::OnKeyPressedEvent(KeyPressedEvent& e)
|
||||
@@ -714,9 +746,85 @@ namespace Prism
|
||||
return false;
|
||||
}
|
||||
|
||||
bool EditorLayer::OnMouseButtonPressedEvent(MouseButtonPressedEvent& e)
|
||||
{
|
||||
auto [mx, my] = Input::GetMousePosition();
|
||||
if (e.GetMouseButton() == PM_MOUSE_BUTTON_LEFT && !Input::IsKeyPressed(PM_KEY_LEFT_ALT) && !ImGuizmo::IsOver())
|
||||
{
|
||||
auto [mouseX, mouseY] = GetMouseViewportSpace();
|
||||
if (mouseX > -1.0f && mouseX < 1.0f && mouseY > -1.0f && mouseY < 1.0f)
|
||||
{
|
||||
auto [origin, direction] = CastRay(mouseX, mouseY);
|
||||
|
||||
m_SelectedSubmeshes.clear();
|
||||
const auto mesh = m_MeshEntity->GetMesh();
|
||||
auto& submeshes = mesh->GetSubmeshes();
|
||||
float lastT = std::numeric_limits<float>::max();
|
||||
for (uint32_t i = 0; i < submeshes.size(); i++)
|
||||
{
|
||||
auto& submesh = submeshes[i];
|
||||
Ray ray = {
|
||||
glm::inverse(m_MeshEntity->GetTransform() * submesh.Transform) * glm::vec4(origin, 1.0f),
|
||||
glm::inverse(glm::mat3(m_MeshEntity->GetTransform()) * glm::mat3(submesh.Transform)) * direction
|
||||
};
|
||||
|
||||
float t;
|
||||
bool intersects = ray.IntersectsAABB(submesh.BoundingBox, t);
|
||||
if (intersects)
|
||||
{
|
||||
const auto& triangleCache = mesh->GetTriangleCache(i);
|
||||
for (const auto& triangle : triangleCache)
|
||||
{
|
||||
if (ray.IntersectsTriangle(triangle.V0.Position, triangle.V1.Position, triangle.V2.Position, t))
|
||||
{
|
||||
PM_CLIENT_WARN("INTERSECTION: {0}, t={1}", submesh.NodeName, t);
|
||||
m_SelectedSubmeshes.push_back({ &submesh, t });
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
std::sort(m_SelectedSubmeshes.begin(), m_SelectedSubmeshes.end(), [](auto& a, auto& b) { return a.Distance < b.Distance; });
|
||||
|
||||
// TODO: Handle mesh being deleted, etc.
|
||||
if (!m_SelectedSubmeshes.empty())
|
||||
m_CurrentlySelectedTransform = &m_SelectedSubmeshes[0].Mesh->Transform;
|
||||
else
|
||||
m_CurrentlySelectedTransform = &m_MeshEntity->Transform();
|
||||
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void EditorLayer::ShowBoundingBoxes(bool show, bool onTop)
|
||||
{
|
||||
SceneRenderer::GetOptions().ShowBoundingBoxes = show && !onTop;
|
||||
m_DrawOnTopBoundingBoxes = show && onTop;
|
||||
}
|
||||
|
||||
std::pair<float, float> EditorLayer::GetMouseViewportSpace() const
|
||||
{
|
||||
auto [mx, my] = ImGui::GetMousePos(); // Input::GetMousePosition();
|
||||
mx -= m_ViewportBounds[0].x;
|
||||
my -= m_ViewportBounds[0].y;
|
||||
const auto viewportWidth = m_ViewportBounds[1].x - m_ViewportBounds[0].x;
|
||||
const auto viewportHeight = m_ViewportBounds[1].y - m_ViewportBounds[0].y;
|
||||
|
||||
return { (mx / viewportWidth) * 2.0f - 1.0f, ((my / viewportHeight) * 2.0f - 1.0f) * -1.0f };
|
||||
}
|
||||
|
||||
std::pair<glm::vec3, glm::vec3> EditorLayer::CastRay(const float mx, const float my) const
|
||||
{
|
||||
glm::vec4 mouseClipPos = { mx, my, -1.0f, 1.0f };
|
||||
|
||||
const auto inverseProj = glm::inverse(m_Scene->GetCamera().GetProjectionMatrix());
|
||||
const auto inverseView = glm::inverse(glm::mat3(m_Scene->GetCamera().GetViewMatrix()));
|
||||
|
||||
const glm::vec4 ray = inverseProj * mouseClipPos;
|
||||
glm::vec3 rayPos = m_Scene->GetCamera().GetPosition();
|
||||
glm::vec3 rayDir = inverseView * glm::vec3(ray);
|
||||
|
||||
return { rayPos, rayDir };
|
||||
}
|
||||
}
|
||||
|
||||
+15
-16
@@ -24,9 +24,14 @@ namespace Prism
|
||||
|
||||
private:
|
||||
bool OnKeyPressedEvent(KeyPressedEvent& e);
|
||||
bool OnMouseButtonPressedEvent(MouseButtonPressedEvent& e);
|
||||
|
||||
void ShowBoundingBoxes(bool show, bool onTop = false);
|
||||
|
||||
private:
|
||||
std::pair<float, float> GetMouseViewportSpace() const;
|
||||
std::pair<glm::vec3, glm::vec3> CastRay(float mx, float my) const;
|
||||
|
||||
private:
|
||||
Scope<SceneHierarchyPanel> m_SceneHierarchyPanel;
|
||||
|
||||
@@ -36,25 +41,27 @@ namespace Prism
|
||||
|
||||
Entity* m_MeshEntity = nullptr;
|
||||
|
||||
Ref<Shader> m_BrushShader;
|
||||
Ref<Mesh> m_PlaneMesh;
|
||||
Ref<Material> m_SphereBaseMaterial;
|
||||
|
||||
Ref<Material> m_MeshMaterial;
|
||||
|
||||
Ref<RenderPass> m_GeoPass, m_CompositePass;
|
||||
|
||||
Ref<MaterialInstance> m_GridMaterial;
|
||||
|
||||
std::vector<Ref<MaterialInstance>> m_MetalSphereMaterialInstances;
|
||||
std::vector<Ref<MaterialInstance>> m_DielectricSphereMaterialInstances;
|
||||
|
||||
float m_GridScale = 16.025f, m_GridSize = 0.025f;
|
||||
float m_MeshScale = 1.0f;
|
||||
|
||||
|
||||
// Imguizmo
|
||||
glm::vec2 m_ViewportBounds[2];
|
||||
int m_GizmoType = -1; // -1 = no gizmo
|
||||
float m_SnapValue = 0.5f;
|
||||
|
||||
struct SelectedSubmesh
|
||||
{
|
||||
Submesh* Mesh;
|
||||
float Distance;
|
||||
};
|
||||
std::vector<SelectedSubmesh> m_SelectedSubmeshes;
|
||||
glm::mat4* m_CurrentlySelectedTransform = nullptr;
|
||||
|
||||
// configure button
|
||||
bool m_AllowViewportCameraEvents = false;
|
||||
@@ -97,14 +104,6 @@ namespace Prism
|
||||
RoughnessInput m_RoughnessInput;
|
||||
|
||||
|
||||
struct Light
|
||||
{
|
||||
glm::vec3 Direction;
|
||||
glm::vec3 Radiance;
|
||||
};
|
||||
Light m_Light;
|
||||
float m_LightMultiplier = 0.3f;
|
||||
|
||||
// PBR params
|
||||
bool m_RadiancePrefilter = false;
|
||||
|
||||
|
||||
BIN
Binary file not shown.
BIN
Binary file not shown.
BIN
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -46,7 +46,7 @@ void main()
|
||||
vec4 localPosition = boneTransform * vec4(a_Position, 1.0);
|
||||
|
||||
vs_Output.WorldPosition = vec3(u_Transform * boneTransform * vec4(a_Position, 1.0));
|
||||
vs_Output.Normal = mat3(boneTransform) * a_Normal;
|
||||
vs_Output.Normal = mat3(u_Transform) * mat3(boneTransform) * a_Normal;
|
||||
vs_Output.TexCoord = vec2(a_TexCoord.x, 1.0 - a_TexCoord.y);
|
||||
vs_Output.WorldNormals = mat3(u_Transform) * mat3(a_Tangent, a_Binormal, a_Normal);
|
||||
vs_Output.Binormal = mat3(boneTransform) * a_Binormal;
|
||||
@@ -68,6 +68,7 @@ const vec3 Fdielectric = vec3(0.04);
|
||||
struct Light {
|
||||
vec3 Direction;
|
||||
vec3 Radiance;
|
||||
float Multiplier;
|
||||
};
|
||||
|
||||
in VertexOutput
|
||||
@@ -256,7 +257,7 @@ vec3 Lighting(vec3 F0)
|
||||
for(int i = 0; i < LightCount; i++)
|
||||
{
|
||||
vec3 Li = -lights.Direction;
|
||||
vec3 Lradiance = lights.Radiance;
|
||||
vec3 Lradiance = lights.Radiance * lights.Multiplier;
|
||||
vec3 Lh = normalize(Li + m_Params.View);
|
||||
|
||||
// Calculate angles between surface normal and various light vectors.
|
||||
@@ -288,7 +289,7 @@ vec3 IBL(vec3 F0, vec3 Lr)
|
||||
int u_EnvRadianceTexLevels = textureQueryLevels(u_EnvRadianceTex);
|
||||
float NoV = clamp(m_Params.NdotV, 0.0, 1.0);
|
||||
vec3 R = 2.0 * dot(m_Params.View, m_Params.Normal) * m_Params.Normal - m_Params.View;
|
||||
vec3 specularIrradiance = textureLod(u_EnvRadianceTex, RotateVectorAboutY(u_EnvMapRotation, Lr), (m_Params.Roughness * m_Params.Roughness) * u_EnvRadianceTexLevels).rgb;
|
||||
vec3 specularIrradiance = textureLod(u_EnvRadianceTex, RotateVectorAboutY(u_EnvMapRotation, Lr), (m_Params.Roughness) * u_EnvRadianceTexLevels).rgb;
|
||||
|
||||
// Sample BRDF Lut, 1.0 - roughness for y-coord because texture was generated (in Sparky) for gloss model
|
||||
vec2 specularBRDF = texture(u_BRDFLUTTexture, vec2(m_Params.NdotV, 1.0 - m_Params.Roughness)).rg;
|
||||
@@ -322,7 +323,7 @@ void main()
|
||||
// Fresnel reflectance, metals use albedo
|
||||
vec3 F0 = mix(Fdielectric, m_Params.Albedo, m_Params.Metalness);
|
||||
|
||||
vec3 lightContribution = vec3(0.0);//Lighting(F0);
|
||||
vec3 lightContribution = Lighting(F0);
|
||||
vec3 iblContribution = IBL(F0, Lr);
|
||||
|
||||
color = vec4(lightContribution + iblContribution, 1.0);
|
||||
|
||||
@@ -57,6 +57,7 @@ const vec3 Fdielectric = vec3(0.04);
|
||||
struct Light {
|
||||
vec3 Direction;
|
||||
vec3 Radiance;
|
||||
float Multiplier;
|
||||
};
|
||||
|
||||
in VertexOutput
|
||||
@@ -246,7 +247,7 @@ vec3 Lighting(vec3 F0)
|
||||
for(int i = 0; i < LightCount; i++)
|
||||
{
|
||||
vec3 Li = -lights.Direction;
|
||||
vec3 Lradiance = lights.Radiance;
|
||||
vec3 Lradiance = lights.Radiance * lights.Multiplier;
|
||||
vec3 Lh = normalize(Li + m_Params.View);
|
||||
|
||||
// Calculate angles between surface normal and various light vectors.
|
||||
@@ -271,15 +272,15 @@ vec3 Lighting(vec3 F0)
|
||||
vec3 IBL(vec3 F0, vec3 Lr)
|
||||
{
|
||||
vec3 irradiance = texture(u_EnvIrradianceTex, m_Params.Normal).rgb;
|
||||
// vec3 F = fresnelSchlickRoughness(F0, m_Params.NdotV, m_Params.Roughness);
|
||||
vec3 F = fresnelSchlick(F0, m_Params.NdotV);
|
||||
vec3 F = fresnelSchlickRoughness(F0, m_Params.NdotV, m_Params.Roughness);
|
||||
// vec3 F = fresnelSchlickR(F0, m_Params.NdotV);
|
||||
vec3 kd = (1.0 - F) * (1.0 - m_Params.Metalness);
|
||||
vec3 diffuseIBL = m_Params.Albedo * irradiance;
|
||||
|
||||
int u_EnvRadianceTexLevels = textureQueryLevels(u_EnvRadianceTex);
|
||||
float NoV = clamp(m_Params.NdotV, 0.0, 1.0);
|
||||
vec3 R = 2.0 * dot(m_Params.View, m_Params.Normal) * m_Params.Normal - m_Params.View;
|
||||
vec3 specularIrradiance = textureLod(u_EnvRadianceTex, RotateVectorAboutY(u_EnvMapRotation, Lr), (m_Params.Roughness * m_Params.Roughness) * u_EnvRadianceTexLevels).rgb;
|
||||
vec3 specularIrradiance = textureLod(u_EnvRadianceTex, RotateVectorAboutY(u_EnvMapRotation, Lr), (m_Params.Roughness) * u_EnvRadianceTexLevels).rgb;
|
||||
|
||||
// Sample BRDF Lut, 1.0 - roughness for y-coord because texture was generated (in Sparky) for gloss model
|
||||
vec2 specularBRDF = texture(u_BRDFLUTTexture, vec2(m_Params.NdotV, 1.0 - m_Params.Roughness)).rg;
|
||||
@@ -317,5 +318,5 @@ void main()
|
||||
vec3 iblContribution = IBL(F0, Lr);
|
||||
|
||||
color = vec4(lightContribution + iblContribution, 1.0);
|
||||
color = vec4(iblContribution, 1.0);
|
||||
// color = vec4(iblContribution, 1.0);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user