Commit 445d7ad9 authored by Florian Oetke's avatar Florian Oetke
Browse files

enemy death visualization

parent ac4d5d15
Pipeline #3306 passed with stage
in 2 minutes and 41 seconds
particle: = particles/*.json
particle_def:test_particles = particles/test_particles.json
particle_sys:test_particles = particles/test_particle_system.json
particle_def: = particles/*.json
particle_sys: = particles/*.json
{
"Transform":{
"scale": {"x": 1.0, "y": 1.0, "z": 1.0}
},
"Particle_system": {
"cfg": "particle_sys:enemy_death_particle_system"
}
}
......@@ -3,7 +3,7 @@
},
"Directional_light": {
"source_radius": 1.0,
"intensity": 4000.0,
"intensity": 1000.0,
"color": {
"r": 1,
"g": 1,
......
......@@ -3,7 +3,7 @@ dummy
##----############
#| |---------##
#| p h |#
#| |---- b |#
#| |---- bbb |#
##----####| |#
##########| b G|#
###########-----##
......
{
"substance_id": "default",
"albedo_aid": "tetr_defaultmaterial_albedo.ktx",
"normal_aid": "tetr_defaultmaterial_normal.ktx",
"brdf_aid": "tetr_defaultmaterial_brdf.ktx",
"emission_aid": "default_white.ktx"
}
{
"emitters": [{
"spawn": [
{"particles_per_second": 300, "stddev":150, "time": 0.5},
{"particles_per_second": 0, "stddev":0, "time": 999}
],
"spawn_loop": false,
"size": {"x":0.2, "y":0.2},
"direction": {"mean":{"elevation":0.1, "azimuth":0}, "stddev":{"elevation":0.1, "azimuth":0.1}},
"ttl": {"mean": 3, "stddev": 0.0},
"velocity": {"mean": 15, "stddev": 8.0},
"emit_script_id": "comp_shader:particle_spawn_sphere",
"type_id": "particle_def:enemy_death_particles"
}],
"effectors": [
{
"force": 10,
"force_dir": {"y":-1},
"distance_decay": 0,
"scale_with_mass": false
}
]
}
{
"keyframes": [
{
"time": 0,
"color": {"mean":{"hue":0, "saturation":1, "alpha":20}, "stddev":{"hue":0.001}},
"size": {"mean": {"x": 0.5, "y":0.5, "z":0.5}, "stddev":{"x": 0.3, "y":0.3, "z":0.3}},
"rotation": {"mean":{"angle":0}, "stddev":{"elevation":1, "azimuth":1, "angle": 1}},
"drag": 0.1
},
{
"time": 1,
"color": {"mean":{"hue":0, "saturation":1, "value":0.1, "alpha":0}, "stddev":{"hue":0.01}},
"size": {"mean": {"x": 0.01, "y":0.01, "z":0.01}},
"rotation": {"mean":{"angle":1}, "stddev":{"elevation":1, "azimuth":1, "angle": 1}},
"drag": 1.0
}
],
"symmetric_scaling": false,
"rotate_with_velocity": false,
"blend": "solid",
"geometry": "mesh",
"model_id": "model:tetr",
"update_script_id": "comp_shader:particle_update_simple"
}
......@@ -18,15 +18,16 @@ namespace phase_shifter::gameplay {
Beat_system::Beat_system(mirrage::util::Message_bus& bus, mirrage::asset::Asset_manager& assets)
: _bus(bus), _assets(assets)
{
auto input = _assets.open(mirrage::asset::AID("beat:pulse")).get_or_throw();
auto input = _assets.open(mirrage::asset::AID("beat:pulse")).get_or_throw();
std::string line;
int i = 0;
while(std::getline(input, line)) {
_time_stamps.push_back(static_cast<float>(atof(line.substr(1, line.length() - 4).c_str())));
i++;
}
_state.avg_beat_time = static_cast<float>(_time_stamps[_time_stamps.size() - 1]) / _time_stamps.size();
_state.avg_beat_time =
static_cast<float>(_time_stamps[_time_stamps.size() - 1]) / _time_stamps.size();
}
void Beat_system::update(mirrage::util::Time dt)
......@@ -47,20 +48,19 @@ namespace phase_shifter::gameplay {
_beat_index >= 0 ? _acc - _time_stamps[_beat_index] : _acc,
_beat_index + 1 < size ? _time_stamps[_beat_index + 1] - _acc : 999,
_state.avg_beat_time,
size - 1 - _beat_index
};
size - 1 - _beat_index};
}
auto Beat_system::graphic_time_scale() const -> float
{
constexpr auto t1_len = 0.05f;
constexpr auto t2_len = 0.6f;
constexpr auto factor = (1.f - (1.f - t1_len - t2_len) * 0.01f) / (t1_len + t2_len) * 2.f;
constexpr auto factor = (1.f - (1.f - t1_len - t2_len) * 0.05f) / (t1_len + t2_len) * 2.f;
auto to = _state.time_to_beat / _state.avg_beat_time;
auto from = _state.time_to_beat / _state.avg_beat_time;
return mirrage::util::max(0.01f,
return mirrage::util::max(0.05f,
factor * (1.f - smootherstep(0.f, t1_len, to)),
factor * (1.f - smootherstep(0.f, t2_len, from)));
}
......@@ -76,12 +76,8 @@ namespace phase_shifter::gameplay {
}
}
const std::vector<float>& Beat_system::time_stamps() const {
return _time_stamps;
}
const std::vector<float>& Beat_system::time_stamps() const { return _time_stamps; }
int Beat_system::beat_index() const {
return _beat_index;
}
int Beat_system::beat_index() const { return _beat_index; }
} // namespace phase_shifter::gameplay
......@@ -11,6 +11,21 @@
namespace phase_shifter::gameplay {
using namespace mirrage::util::unit_literals;
namespace {
[[maybe_unused]] float normalize_angle(float a)
{
if(a > mirrage::util::PI) {
return a - 2 * mirrage::util::PI;
} else if(a <= -mirrage::util::PI) {
return a + 2 * mirrage::util::PI;
} else {
return a;
}
}
} // namespace
bool rect_circle_intersects(float rect_x,
float rect_y,
float rect_w,
......@@ -78,8 +93,24 @@ namespace phase_shifter::gameplay {
_ecs.list<Entity_handle, Transform_comp, Killable_comp>()) {
auto circle = rotate_point({k_transform.position.x, k_transform.position.z}, angle);
if(rect_circle_intersects(topleft.x, topleft.y, width, height, circle.x, circle.y, 1)) {
// calc attack angle
auto target_dir = glm::vec2(k_transform.position.x, k_transform.position.z)
- dash.last_position;
auto attacker_angle = std::atan2(move.last_step.y, move.last_step.x);
auto attack_angle = normalize_angle(std::atan2(target_dir.y, target_dir.x)
- std::atan2(move.last_step.y, move.last_step.x));
if(attack_angle < (-15_deg).value())
attack_angle = (-45_deg).value();
else if(attack_angle > (15_deg).value())
attack_angle = (45_deg).value();
else
attack_angle = 0;
auto attack_direction = rotate_point({1, 0}, attack_angle + attacker_angle);
_bus.send<Enemy_killed_msg>(k_transform.position,
k_transform.position - transform.position);
glm::vec3(attack_direction.x, 0.f, attack_direction.y));
_ecs.erase(entity);
}
}
......
......@@ -2,14 +2,28 @@
#include "../messages.hpp"
#include <mirrage/ecs/entity_manager.hpp>
namespace phase_shifter::ui {
using namespace mirrage::util::unit_literals;
Effect_system::Effect_system(mirrage::util::Message_bus& bus, mirrage::ecs::Entity_manager& ecs)
: _bus(bus), _mailbox(bus), _ecs(ecs)
{
_mailbox.subscribe_to([&](Enemy_killed_msg& e) {
// TODO
auto entity = _ecs.entity_builder("enemy_tombstone")
.rotation(glm::rotation(
glm::vec3{1.f, 0.f, 0.f},
glm::vec3(e.attack_direction.x, 0, -e.attack_direction.z)))
.position(e.position)
.create();
_actions.defer(5_s, [&, entity] {
_ecs.erase(entity);
LOG(plog::debug) << "erased";
});
});
_mailbox.subscribe_to([&](Win_msg& e) {
......@@ -21,6 +35,10 @@ namespace phase_shifter::ui {
});
}
void Effect_system::update(mirrage::util::Time) { _mailbox.update_subscriptions(); }
void Effect_system::update(mirrage::util::Time dt)
{
_mailbox.update_subscriptions();
_actions.update(dt);
}
} // namespace phase_shifter::ui
#pragma once
#include <mirrage/utils/defer.hpp>
#include <mirrage/utils/messagebus.hpp>
#include <mirrage/utils/units.hpp>
#include <vector>
namespace mirrage::ecs {
class Entity_manager;
......@@ -17,9 +17,10 @@ namespace phase_shifter::ui {
void update(mirrage::util::Time);
private:
mirrage::util::Message_bus& _bus;
mirrage::util::Mailbox_collection _mailbox;
mirrage::ecs::Entity_manager& _ecs;
mirrage::util::Message_bus& _bus;
mirrage::util::Mailbox_collection _mailbox;
mirrage::ecs::Entity_manager& _ecs;
mirrage::util::Deferred_action_container _actions;
};
} // namespace phase_shifter::ui
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment