Working on doors and scripting

This commit is contained in:
Vladislav Khorev committed 2026-05-14 21:28:41 +03:00
1 parent 774397f690
commit 0f2b2e55af
11 files changed
+322 -9

No files matched your search

+4
View File
@@ -93,6 +93,9 @@ namespace ZL {
data.base = parseGameObjectData(item);
data.interactionRadius = item.value("interactionRadius", 2.0f);
data.activateFunctionName = item.value("activateFunction", "");
data.pivotX = item.value("pivotX", 0.0f);
data.pivotY = item.value("pivotY", 0.0f);
data.pivotZ = item.value("pivotZ", 0.0f);
if (!data.base.meshPath.empty())
objects.push_back(std::move(data));
}
@@ -176,6 +179,7 @@ namespace ZL {
intObj.loadedObject = buildLoadedObject(data.base, renderer, zipPath);
intObj.interactionRadius = data.interactionRadius;
intObj.activateFunctionName = data.activateFunctionName;
intObj.pivot = Eigen::Vector3f(data.pivotX, data.pivotY, data.pivotZ);
intObj.loadedObject.mesh.RefreshVBO();
+3
View File
@@ -29,6 +29,9 @@ namespace ZL {
GameObjectData base;
float interactionRadius = 2.0f;
std::string activateFunctionName;
float pivotX = 0.0f;
float pivotY = 0.0f;
float pivotZ = 0.0f;
};
struct NpcData {
+94
View File
@@ -3,6 +3,8 @@
#include "render/TextureManager.h"
#include <iostream>
#include <string>
#include <algorithm>
#include <Eigen/Geometry>
namespace ZL {
extern const std::string textureUniformName;
@@ -10,10 +12,102 @@ namespace ZL {
namespace ZL {
void InteractiveObject::moveTo(const Eigen::Vector3f& target, float durationSec, std::function<void()> onComplete) {
if (isAnimating) return;
AnimTask task;
task.type = AnimTask::Type::Move;
task.startPos = position;
task.startRotY = rotationY;
task.startScale = scale;
task.targetPos = target;
task.targetRotY = rotationY;
task.targetScale = scale;
task.durationMs = durationSec * 1000.f;
task.elapsedMs = 0.f;
task.onComplete = std::move(onComplete);
animTask = std::move(task);
isAnimating = true;
}
void InteractiveObject::rotateTo(float targetRotY, float durationSec, std::function<void()> onComplete) {
if (isAnimating) return;
AnimTask task;
task.type = AnimTask::Type::Rotate;
task.startPos = position;
task.startRotY = rotationY;
task.startScale = scale;
task.targetPos = position;
task.targetRotY = targetRotY;
task.targetScale = scale;
task.durationMs = durationSec * 1000.f;
task.elapsedMs = 0.f;
task.onComplete = std::move(onComplete);
animTask = std::move(task);
isAnimating = true;
}
void InteractiveObject::scaleTo(float targetScale, float durationSec, std::function<void()> onComplete) {
if (isAnimating) return;
AnimTask task;
task.type = AnimTask::Type::Scale;
task.startPos = position;
task.startRotY = rotationY;
task.startScale = scale;
task.targetPos = position;
task.targetRotY = rotationY;
task.targetScale = targetScale;
task.durationMs = durationSec * 1000.f;
task.elapsedMs = 0.f;
task.onComplete = std::move(onComplete);
animTask = std::move(task);
isAnimating = true;
}
void InteractiveObject::update(int64_t deltaMs) {
if (!isAnimating || !animTask) return;
AnimTask& task = *animTask;
task.elapsedMs += static_cast<float>(deltaMs);
const float t = min(task.elapsedMs / task.durationMs, 1.0f);
switch (task.type) {
case AnimTask::Type::Move:
position = task.startPos + (task.targetPos - task.startPos) * t;
break;
case AnimTask::Type::Rotate:
rotationY = task.startRotY + (task.targetRotY - task.startRotY) * t;
break;
case AnimTask::Type::Scale:
scale = task.startScale + (task.targetScale - task.startScale) * t;
break;
}
if (t >= 1.0f) {
// Snap to exact target
position = task.targetPos;
rotationY = task.targetRotY;
scale = task.targetScale;
std::function<void()> cb = std::move(task.onComplete);
animTask.reset();
isAnimating = false;
if (cb) cb();
}
}
void InteractiveObject::draw(Renderer& renderer) const {
if (!isActive || !loadedObject.texture) return;
renderer.PushMatrix();
renderer.TranslateMatrix(position);
if (rotationY != 0.f) {
renderer.TranslateMatrix(pivot);
renderer.RotateMatrix(Eigen::AngleAxisf(rotationY, Eigen::Vector3f::UnitY()).toRotationMatrix());
renderer.TranslateMatrix(-pivot);
}
if (scale != 1.f)
renderer.ScaleMatrix(scale);
renderer.RenderUniform1i(textureUniformName, 0);
glBindTexture(GL_TEXTURE_2D, loadedObject.texture->getTexID());
renderer.DrawVertexRenderStruct(loadedObject.mesh);
+27 -1
View File
@@ -1,6 +1,9 @@
#pragma once
#include <string>
#include <memory>
#include <optional>
#include <functional>
#include <cstdint>
#include <Eigen/Core>
#include "render/Renderer.h"
@@ -17,12 +20,35 @@ namespace ZL {
struct InteractiveObject {
LoadedGameObject loadedObject; // name, texture, mesh
Eigen::Vector3f position;
Eigen::Vector3f pivot = Eigen::Vector3f::Zero(); // local-space offset to rotation pivot
float rotationY = 0.0f; // Y-axis rotation in radians
float scale = 1.0f; // uniform scale
float interactionRadius;
bool isActive = true;
bool isActive = true;
bool isAnimating = false; // true while a timed animation is running
std::string activateFunctionName;
struct AnimTask {
enum class Type { Move, Rotate, Scale } type;
Eigen::Vector3f startPos;
float startRotY;
float startScale;
Eigen::Vector3f targetPos;
float targetRotY;
float targetScale;
float durationMs;
float elapsedMs = 0.f;
std::function<void()> onComplete;
};
std::optional<AnimTask> animTask;
InteractiveObject() : interactionRadius(2.0f) {}
void moveTo(const Eigen::Vector3f& target, float durationSec, std::function<void()> onComplete = {});
void rotateTo(float targetRotY, float durationSec, std::function<void()> onComplete = {});
void scaleTo(float targetScale, float durationSec, std::function<void()> onComplete = {});
void update(int64_t deltaMs);
void draw(Renderer& renderer) const;
};