ToyEngine/Exp3/ParticleWorld.cpp

145 lines
4.1 KiB
C++
Raw Permalink Normal View History

2023-06-02 15:07:13 +08:00
#include "ParticleWorld.h"
2023-06-03 01:04:32 +08:00
#include <Particle.h>
#include <RenderingSystem.h>
2023-06-02 15:07:13 +08:00
ParticleWorld::ParticleWorld()
{
light.lightDirection = glm::normalize(glm::vec3((cos(lightPitch) * cos(lightYaw)), (sin(lightPitch)), (cos(lightPitch) * sin(lightYaw))));
light.radiance = 15.f * lightColor;
{
auto p0 = std::make_shared<Particle>(1);
p0->setPosition({ 0,1,0 });
p0->setFixed(true);
auto p1 = std::make_shared<Particle>(1);
p1->setPosition({ 0,0,0 });
p1->setEnableGravity(true);
addActor(p0);
addActor(p1);
physicsManager.addSpring(p0, p1, 2, 5, 0.1);
}
for (int i = 0, particleCount = 5; i < particleCount; i++)
{
auto particle = std::make_shared<Particle>(1);
particle->setPosition({ 5, 0, glm::mix(-3.1f,2.f,(double)i / (particleCount - 1)) });
if (i == 0 || i == particleCount - 1)
particle->setFixed(true);
else
particle->setEnableGravity(true);
particles.push_back(particle);
addActor(particle);
if (i != 0)
{
float ks = 10, kd = 0.1;
physicsManager.addRubberBand(particles[i - 1], particle, 0.01, ks, kd);
}
}
{
2023-06-04 00:59:02 +08:00
star = std::make_shared<Particle>(100);
star->setPosition({ -10,0,0 });
star->setFixed(true);
2023-06-02 15:07:13 +08:00
2023-06-04 00:59:02 +08:00
auto p = std::make_shared<Particle>(1);
p->setPosition({ -15,0,0 });
p->setSpeed(glm::vec3(0, 0, 1) * glm::sqrt(G * star->getMass() / glm::distance(star->getPosition(), p->getPosition())));
2023-06-02 15:07:13 +08:00
2023-06-04 00:59:02 +08:00
addActor(star);
addActor(p);
2023-06-02 15:07:13 +08:00
2023-06-04 00:59:02 +08:00
physicsManager.addGravitation(star, p, G);
2023-06-02 15:07:13 +08:00
}
}
void ParticleWorld::logicalTick(float deltaTime)
{
World::logicalTick(deltaTime);
}
void ParticleWorld::rendererTick(float deltaTime)
{
World::rendererTick(deltaTime);
for (auto iter = particles.begin(); iter != particles.end(); )
{
if (glm::length2((*iter)->getPosition()) > 1e4)
{
removeActor(*iter);
iter = particles.erase(iter);
}
else iter++;
}
}
void ParticleWorld::cursorPosCallback(GLFWwindow* window, double xpos, double ypos)
{
static bool firstMouse = true;
static float lastX;
static float lastY;
float xoffset = xpos - lastX;
float yoffset = lastY - ypos;
lastX = xpos;
lastY = ypos;
if (firstMouse)
{
firstMouse = false;
return;
}
if (glfwGetMouseButton(window, GLFW_MOUSE_BUTTON_RIGHT) == GLFW_PRESS)
camera.processMouseMovement(xoffset, yoffset);
}
void ParticleWorld::mouseButtonCallback(GLFWwindow* window, int button, int action, int mods)
{
if (button == GLFW_MOUSE_BUTTON_LEFT && action == GLFW_PRESS)
2023-06-04 00:59:02 +08:00
{
auto p = std::make_shared<Particle>(1);
p->setPosition(camera.Position + glm::vec3(0, -0.3, 0));
p->setSpeed(5.f * glm::normalize(camera.Front));
addActor(p);
physicsManager.addGravitation(star, p, G);
particles.push_back(p);
}
2023-06-02 15:07:13 +08:00
}
void ParticleWorld::scrollCallback(GLFWwindow* window, double xoffset, double yoffset)
{
if (glfwGetKey(window, GLFW_KEY_LEFT_CONTROL) == GLFW_PRESS)
lightPitch = glm::mod(lightPitch + yoffset / 100., glm::pi<double>());
else if (glfwGetKey(window, GLFW_KEY_LEFT_ALT) == GLFW_PRESS)
lightYaw = glm::mod(lightYaw + yoffset / 100., 2 * glm::pi<double>());
else if (glfwGetKey(window, GLFW_KEY_R) == GLFW_PRESS)
light.radiance = glm::clamp((light.radiance / lightColor).x + (float)yoffset, 0.f, 100.f) * lightColor;
else if (glfwGetKey(window, GLFW_KEY_E) == GLFW_PRESS)
RenderingSystem::instance().exposure = glm::clamp(RenderingSystem::instance().exposure + (float)yoffset * 0.1f, 0.f, 2.f);
else camera.processMouseScroll(yoffset);
light.lightDirection = glm::normalize(glm::vec3((cos(lightPitch) * cos(lightYaw)), (sin(lightPitch)), (cos(lightPitch) * sin(lightYaw))));
}
void ParticleWorld::processInput(GLFWwindow* window, float deltaTime)
{
if (glfwGetKey(window, GLFW_KEY_W) == GLFW_PRESS)
camera.processKeyboard(FORWARD, deltaTime);
if (glfwGetKey(window, GLFW_KEY_S) == GLFW_PRESS)
camera.processKeyboard(BACKWARD, deltaTime);
if (glfwGetKey(window, GLFW_KEY_A) == GLFW_PRESS)
camera.processKeyboard(LEFT, deltaTime);
if (glfwGetKey(window, GLFW_KEY_D) == GLFW_PRESS)
camera.processKeyboard(RIGHT, deltaTime);
if (glfwGetKey(window, GLFW_KEY_SPACE) == GLFW_PRESS)
camera.processKeyboard(UP, deltaTime);
if (glfwGetKey(window, GLFW_KEY_LEFT_SHIFT) == GLFW_PRESS)
camera.processKeyboard(DOWN, deltaTime);
}