Skip to content

Commit 79bfa92

Browse files
Add gizmo to visualize max attenuation distance in AkEvent3D
Adds a gizmo in the Godot editor for AkEvent3D nodes to visually indicate the maximum attenuation distance of the associated Wwise Event.
1 parent 025ea4c commit 79bfa92

11 files changed

+158
-55
lines changed

addons/Wwise/editor/images/wwise_audio_speaker.svg

-3
This file was deleted.

addons/Wwise/editor/images/wwise_audio_speaker.svg.import

-37
This file was deleted.

addons/Wwise/native/build_profile_editor.json

+1
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@
3838
"Shortcut",
3939
"StandardMaterial3D",
4040
"Texture2D",
41+
"Theme",
4142
"Thread",
4243
"Time",
4344
"Timer",
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
#pragma once
2+
3+
#include <godot_cpp/classes/editor_interface.hpp>
4+
#include <godot_cpp/classes/editor_settings.hpp>
5+
#include <godot_cpp/variant/string_name.hpp>
6+
7+
using namespace godot;
8+
9+
#define EDITOR_GET(m_var) _EDITOR_GET(m_var)
10+
static Variant _EDITOR_GET(const String& p_setting)
11+
{
12+
Ref<EditorSettings> settings = EditorInterface::get_singleton()->get_editor_settings();
13+
ERR_FAIL_COND_V(!settings.is_valid() || !settings->has_setting(p_setting), Variant());
14+
return settings->get(p_setting);
15+
}
16+
17+
#define SNAME(m_arg) \
18+
( \
19+
[]() -> const StringName& \
20+
{ \
21+
static StringName sname = StringName(m_arg, true); \
22+
return sname; \
23+
})()
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,13 @@
11
#include "ak_event_3d_gizmo_plugin.h"
22

3+
AkEvent3DGizmoPlugin::AkEvent3DGizmoPlugin()
4+
{
5+
create_icon_material("ak_event_3d_icon",
6+
EditorInterface::get_singleton()->get_editor_theme()->get_icon(
7+
SNAME("Gizmo3DSamplePlayer"), SNAME("EditorIcons")));
8+
create_material("ak_event_3d_material_billboard", Color(1, 1, 1), true, false, true);
9+
}
10+
311
bool AkEvent3DGizmoPlugin::_has_gizmo(Node3D* for_node_3d) const
412
{
513
if (for_node_3d)
@@ -13,22 +21,55 @@ String AkEvent3DGizmoPlugin::_get_gizmo_name() const { return "AkEvent3DGizmo";
1321

1422
int32_t AkEvent3DGizmoPlugin::_get_priority() const { return -1; }
1523

16-
void AkEvent3DGizmoPlugin::_redraw(const Ref<EditorNode3DGizmo>& gizmo)
24+
void AkEvent3DGizmoPlugin::_redraw(const Ref<EditorNode3DGizmo>& p_gizmo)
1725
{
18-
gizmo->clear();
26+
p_gizmo->clear();
1927

20-
if (!texture.is_valid())
28+
float r = 0;
29+
AkEvent3D* ak_event = Object::cast_to<AkEvent3D>(p_gizmo->get_node_3d());
30+
if (ak_event)
2131
{
22-
texture = ResourceLoader::get_singleton()->load(ak_event_speaker_path);
23-
24-
if (!texture.is_valid())
32+
auto event = ak_event->get_event();
33+
if (event.is_valid())
2534
{
26-
return;
35+
auto project_data = WwiseProjectInfo::get_singleton()->get_data();
36+
if (project_data.is_valid())
37+
{
38+
r = project_data->get_event_max_attenuation(event->get_id());
39+
}
2740
}
41+
}
42+
43+
// note (afama): Based on code from:
44+
// https://github.com/godotengine/godot/blob/4.4/editor/plugins/gizmos/audio_stream_player_3d_gizmo_plugin.cpp
45+
// Used to resemble the AudioStreamPlayer3D gizmo.
46+
// License: godotengine.org/license
47+
const Ref<Material> lines_billboard_material = get_material("ak_event_3d_material_billboard", p_gizmo);
48+
49+
PackedVector3Array points_billboard;
2850

29-
create_icon_material("ak_event_3d_icon_material", texture);
51+
for (int i = 0; i < 120; i++)
52+
{
53+
// Create a circle.
54+
const float ra = Math::deg_to_rad((float)(i * 3));
55+
const float rb = Math::deg_to_rad((float)((i + 1) * 3));
56+
const Point2 a = Vector2(Math::sin(ra), Math::cos(ra)) * r;
57+
const Point2 b = Vector2(Math::sin(rb), Math::cos(rb)) * r;
58+
59+
// Draw a billboarded circle.
60+
points_billboard.push_back(Vector3(a.x, a.y, 0));
61+
points_billboard.push_back(Vector3(b.x, b.y, 0));
3062
}
3163

32-
Ref<StandardMaterial3D> material = get_material("ak_event_3d_icon_material", gizmo);
33-
gizmo->add_unscaled_billboard(material, 0.05);
64+
Color color = Color(0.4, 0.8, 1);
65+
66+
if (r > CMP_EPSILON)
67+
{
68+
color.set_h(color.get_h() + 0.5);
69+
}
70+
71+
p_gizmo->add_lines(points_billboard, lines_billboard_material, true, color);
72+
73+
const Ref<Material> icon = get_material("ak_event_3d_icon", p_gizmo);
74+
p_gizmo->add_unscaled_billboard(icon, 0.05);
3475
}
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,12 @@
11
#pragma once
22

3+
#include "editor/editor_utils.h"
4+
#include "editor/wwise_project_data.h"
35
#include <godot_cpp/classes/editor_node3d_gizmo_plugin.hpp>
46
#include <godot_cpp/classes/node3d.hpp>
57
#include <godot_cpp/classes/resource_loader.hpp>
68
#include <godot_cpp/classes/standard_material3d.hpp>
9+
#include <godot_cpp/classes/theme.hpp>
710

811
using namespace godot;
912

@@ -14,13 +17,10 @@ class AkEvent3DGizmoPlugin : public EditorNode3DGizmoPlugin
1417
protected:
1518
static void _bind_methods() {}
1619

17-
private:
18-
const String ak_event_speaker_path = "res://addons/Wwise/editor/images/wwise_audio_speaker.svg";
19-
Ref<Texture2D> texture;
20-
2120
public:
21+
AkEvent3DGizmoPlugin();
2222
virtual bool _has_gizmo(Node3D* for_node_3d) const override;
2323
virtual String _get_gizmo_name() const override;
2424
virtual int32_t _get_priority() const override;
25-
virtual void _redraw(const Ref<EditorNode3DGizmo>& gizmo) override;
25+
virtual void _redraw(const Ref<EditorNode3DGizmo>& p_gizmo) override;
2626
};

addons/Wwise/native/src/editor/wwise_project_data.cpp

+61
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,67 @@ void WwiseProjectData::_bind_methods()
4242
ADD_PROPERTY(PropertyInfo(Variant::ARRAY, "trigger_root"), "set_trigger_root", "get_trigger_root");
4343
}
4444

45+
float WwiseProjectData::get_event_max_attenuation(AkUniqueID p_event_id)
46+
{
47+
auto event = get_event_info(p_event_id);
48+
return event.is_valid() ? event->get_max_attenuation() : 0.0f;
49+
}
50+
51+
Ref<WwiseTreeObjectEvent> WwiseProjectData::get_event_info(AkUniqueID p_event_id)
52+
{
53+
Array root_array = get_event_root();
54+
if (root_array.is_empty())
55+
{
56+
return Ref<WwiseTreeObjectEvent>();
57+
}
58+
59+
std::function<Ref<WwiseTreeObjectEvent>(const Ref<WwiseTreeObject>&)> find_event =
60+
[&](const Ref<WwiseTreeObject>& node) -> Ref<WwiseTreeObjectEvent>
61+
{
62+
if (node.is_null())
63+
{
64+
return Ref<WwiseTreeObjectEvent>();
65+
}
66+
67+
if (node->get_id() == p_event_id)
68+
{
69+
Ref<WwiseTreeObjectEvent> event = node;
70+
if (event.is_valid())
71+
{
72+
return event;
73+
}
74+
}
75+
76+
Array children = node->get_children();
77+
for (int i = 0; i < children.size(); ++i)
78+
{
79+
Ref<WwiseTreeObject> child = children[i];
80+
Ref<WwiseTreeObjectEvent> found = find_event(child);
81+
if (found.is_valid())
82+
{
83+
return found;
84+
}
85+
}
86+
87+
return Ref<WwiseTreeObjectEvent>();
88+
};
89+
90+
for (int i = 0; i < root_array.size(); ++i)
91+
{
92+
Ref<WwiseTreeObject> root = root_array[i];
93+
if (root.is_valid())
94+
{
95+
Ref<WwiseTreeObjectEvent> result = find_event(root);
96+
if (result.is_valid())
97+
{
98+
return result;
99+
}
100+
}
101+
}
102+
103+
return Ref<WwiseTreeObjectEvent>();
104+
}
105+
45106
void WwiseProjectData::set_acoustic_texture_root(const Array& p_acoustic_texture)
46107
{
47108
acoustic_texture_root = p_acoustic_texture;

addons/Wwise/native/src/editor/wwise_project_data.h

+4
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
#pragma once
22

33
#include "editor/wwise_tree_object.h"
4+
#include "editor/wwise_tree_object_event.h"
45
#include <functional>
56
#include <godot_cpp/classes/resource.hpp>
67

@@ -24,6 +25,9 @@ class WwiseProjectData : public Resource
2425
Array trigger_root;
2526

2627
public:
28+
float get_event_max_attenuation(AkUniqueID p_event_id);
29+
Ref<WwiseTreeObjectEvent> get_event_info(AkUniqueID p_event_id);
30+
2731
void set_acoustic_texture_root(const Array& p_acoustic_texture);
2832
Array get_acoustic_texture_root() const;
2933

addons/Wwise/native/src/scene/ak_event.cpp

+5
Original file line numberDiff line numberDiff line change
@@ -326,6 +326,11 @@ void AkEvent3D::set_event(const Ref<WwiseEvent>& event)
326326
{
327327
this->event = event;
328328
notify_property_list_changed();
329+
330+
if (Engine::get_singleton()->is_editor_hint())
331+
{
332+
update_gizmos();
333+
}
329334
}
330335

331336
Ref<WwiseEvent> AkEvent3D::get_event() const { return event; }

addons/Wwise/native/vs2022/wwise-gdextension.vcxproj

+5
Original file line numberDiff line numberDiff line change
@@ -686,6 +686,11 @@
686686
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='editor|x64'">true</ExcludedFromBuild>
687687
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='template_release|x64'">true</ExcludedFromBuild>
688688
</ClInclude>
689+
<ClInclude Include="..\src\editor\editor_utils.h">
690+
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='editor|x64'">true</ExcludedFromBuild>
691+
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='template_release|x64'">true</ExcludedFromBuild>
692+
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='template_debug|x64'">true</ExcludedFromBuild>
693+
</ClInclude>
689694
<ClInclude Include="..\src\editor\plugins\ak_android_export_plugin.h">
690695
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='template_debug|x64'">true</ExcludedFromBuild>
691696
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='editor|x64'">true</ExcludedFromBuild>

addons/Wwise/native/vs2022/wwise-gdextension.vcxproj.filters

+3
Original file line numberDiff line numberDiff line change
@@ -449,5 +449,8 @@
449449
<ClInclude Include="..\src\core\wwise_external_source_info.h">
450450
<Filter>Source Files\core</Filter>
451451
</ClInclude>
452+
<ClInclude Include="..\src\editor\editor_utils.h">
453+
<Filter>Source Files\editor</Filter>
454+
</ClInclude>
452455
</ItemGroup>
453456
</Project>

0 commit comments

Comments
 (0)