134 lines
3.6 KiB
C++
134 lines
3.6 KiB
C++
#include "clue_finder.h"
|
|
#include "core/config/engine.h"
|
|
#include "core/math/math_defs.h"
|
|
#include "scene/3d/mesh_instance_3d.h"
|
|
#include "scene/3d/xr/xr_nodes.h"
|
|
#include "scene/main/node.h"
|
|
#include "scene/resources/material.h"
|
|
#include "scene/resources/texture.h"
|
|
#include "you_done_it/clue_db.h"
|
|
|
|
ClueFinder *ClueFinder::singleton_instance{ nullptr };
|
|
String const ClueFinder::sig_found_marker_changed{ "found_marker_changed" };
|
|
|
|
void ClueFinder::_bind_methods() {
|
|
ClassDB::bind_method(D_METHOD("take_photo"), &ClueFinder::take_photo);
|
|
ADD_SIGNAL(MethodInfo(sig_found_marker_changed, PropertyInfo(Variant::BOOL, "has_marker")));
|
|
BIND_HPROPERTY(Variant::OBJECT, empty_texture, PROPERTY_HINT_RESOURCE_TYPE, "Texture");
|
|
BIND_HPROPERTY(Variant::OBJECT, photo_material, PROPERTY_HINT_RESOURCE_TYPE, "StandardMaterial3D");
|
|
}
|
|
|
|
void ClueFinder::enter_tree() {
|
|
if (singleton_instance == nullptr) {
|
|
singleton_instance = this;
|
|
} else {
|
|
queue_free();
|
|
}
|
|
if (XRController3D * controller{ cast_to<XRController3D>(get_parent()) }) {
|
|
controller->connect("button_pressed", callable_mp(this, &self_type::on_button_pressed));
|
|
}
|
|
}
|
|
|
|
void ClueFinder::exit_tree() {
|
|
if (singleton_instance == this) {
|
|
singleton_instance = nullptr;
|
|
}
|
|
}
|
|
|
|
void ClueFinder::on_button_pressed(String button) {
|
|
if (button == "trigger_click") {
|
|
take_photo();
|
|
}
|
|
if (button == "ax_button") {
|
|
send_photo();
|
|
}
|
|
if (button == "by_button") {
|
|
delete_photo();
|
|
}
|
|
}
|
|
|
|
void ClueFinder::_notification(int what) {
|
|
if (Engine::get_singleton()->is_editor_hint()) {
|
|
return;
|
|
}
|
|
switch (what) {
|
|
case NOTIFICATION_ENTER_TREE:
|
|
enter_tree();
|
|
return;
|
|
case NOTIFICATION_EXIT_TREE:
|
|
exit_tree();
|
|
return;
|
|
default:
|
|
return;
|
|
}
|
|
}
|
|
|
|
ClueFinder *ClueFinder::get_singleton() {
|
|
return singleton_instance;
|
|
}
|
|
|
|
ClueMarker *ClueFinder::find_current_clue() {
|
|
float best_score{ Math::INF };
|
|
ClueMarker *best_marker{ nullptr };
|
|
for (ClueMarker *marker : this->clue_markers) {
|
|
float score{ marker->score_in_view() };
|
|
if (!Math::is_nan(score) && score < best_score) {
|
|
best_marker = marker;
|
|
best_score = score;
|
|
}
|
|
}
|
|
return best_marker;
|
|
}
|
|
|
|
void ClueFinder::register_clue_marker(ClueMarker *marker) {
|
|
this->clue_markers.insert(marker);
|
|
}
|
|
|
|
void ClueFinder::remove_clue_marker(ClueMarker *marker) {
|
|
this->clue_markers.erase(marker);
|
|
}
|
|
|
|
void ClueFinder::take_photo() {
|
|
this->found_marker = find_current_clue();
|
|
if (this->found_marker) {
|
|
Ref<ClueData> clue{ ClueDB::get_singleton()->get_clue(this->found_marker->get_clue_id()) };
|
|
print_line("Found clue: ", this->found_marker->get_clue_id(), " ", clue, " ", clue->get_image());
|
|
photo_material->set_texture(BaseMaterial3D::TEXTURE_ALBEDO, clue->get_image());
|
|
} else {
|
|
photo_material->set_texture(BaseMaterial3D::TEXTURE_ALBEDO, this->empty_texture);
|
|
}
|
|
emit_signal(sig_found_marker_changed, bool(this->found_marker));
|
|
}
|
|
|
|
void ClueFinder::send_photo() {
|
|
if (this->found_marker) {
|
|
this->found_marker->reveal();
|
|
this->found_marker = nullptr;
|
|
emit_signal(sig_found_marker_changed, false);
|
|
photo_material->set_texture(BaseMaterial3D::TEXTURE_ALBEDO, this->empty_texture);
|
|
}
|
|
}
|
|
|
|
void ClueFinder::delete_photo() {
|
|
if (this->found_marker) {
|
|
this->found_marker = nullptr;
|
|
emit_signal(sig_found_marker_changed, false);
|
|
photo_material->set_texture(BaseMaterial3D::TEXTURE_ALBEDO, this->empty_texture);
|
|
}
|
|
}
|
|
|
|
void ClueFinder::set_empty_texture(Ref<Texture> texture) {
|
|
this->empty_texture = texture;
|
|
}
|
|
|
|
Ref<Texture> ClueFinder::get_empty_texture() const {
|
|
return this->empty_texture;
|
|
}
|
|
|
|
void ClueFinder::set_photo_material(Ref<StandardMaterial3D> material) {
|
|
this->photo_material = material;
|
|
}
|
|
|
|
Ref<StandardMaterial3D> ClueFinder::get_photo_material() const {
|
|
return this->photo_material;
|
|
}
|