Path: blob/master/modules/jolt_physics/objects/jolt_area_3d.h
10278 views
/**************************************************************************/1/* jolt_area_3d.h */2/**************************************************************************/3/* This file is part of: */4/* GODOT ENGINE */5/* https://godotengine.org */6/**************************************************************************/7/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */8/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */9/* */10/* Permission is hereby granted, free of charge, to any person obtaining */11/* a copy of this software and associated documentation files (the */12/* "Software"), to deal in the Software without restriction, including */13/* without limitation the rights to use, copy, modify, merge, publish, */14/* distribute, sublicense, and/or sell copies of the Software, and to */15/* permit persons to whom the Software is furnished to do so, subject to */16/* the following conditions: */17/* */18/* The above copyright notice and this permission notice shall be */19/* included in all copies or substantial portions of the Software. */20/* */21/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */22/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */23/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */24/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */25/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */26/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */27/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */28/**************************************************************************/2930#pragma once3132#include "jolt_shaped_object_3d.h"3334#include "servers/physics_server_3d.h"3536class JoltBody3D;37class JoltSoftBody3D;3839class JoltArea3D final : public JoltShapedObject3D {40public:41typedef PhysicsServer3D::AreaSpaceOverrideMode OverrideMode;4243private:44struct BodyIDHasher {45static uint32_t hash(const JPH::BodyID &p_id) { return hash_fmix32(p_id.GetIndexAndSequenceNumber()); }46};4748struct ShapeIDPair {49JPH::SubShapeID other;50JPH::SubShapeID self;5152ShapeIDPair(JPH::SubShapeID p_other, JPH::SubShapeID p_self) :53other(p_other), self(p_self) {}5455static uint32_t hash(const ShapeIDPair &p_pair) {56uint32_t hash = hash_murmur3_one_32(p_pair.other.GetValue());57hash = hash_murmur3_one_32(p_pair.self.GetValue(), hash);58return hash_fmix32(hash);59}6061friend bool operator==(const ShapeIDPair &p_lhs, const ShapeIDPair &p_rhs) {62return (p_lhs.other == p_rhs.other) && (p_lhs.self == p_rhs.self);63}64};6566struct ShapeIndexPair {67int other = -1;68int self = -1;6970ShapeIndexPair() = default;7172ShapeIndexPair(int p_other, int p_self) :73other(p_other), self(p_self) {}7475static uint32_t hash(const ShapeIndexPair &p_pair) {76uint32_t hash = hash_murmur3_one_32(p_pair.other);77hash = hash_murmur3_one_32(p_pair.self, hash);78return hash_fmix32(hash);79}8081friend bool operator==(const ShapeIndexPair &p_lhs, const ShapeIndexPair &p_rhs) {82return (p_lhs.other == p_rhs.other) && (p_lhs.self == p_rhs.self);83}84};8586struct Overlap {87HashMap<ShapeIDPair, ShapeIndexPair, ShapeIDPair> shape_pairs;88HashMap<ShapeIndexPair, int, ShapeIndexPair> ref_counts;89LocalVector<ShapeIndexPair> pending_added;90LocalVector<ShapeIndexPair> pending_removed;91RID rid;92ObjectID instance_id;93};9495typedef HashMap<JPH::BodyID, Overlap, BodyIDHasher> OverlapsById;9697SelfList<JoltArea3D> call_queries_element;9899OverlapsById bodies_by_id;100OverlapsById areas_by_id;101102Vector3 gravity_vector = Vector3(0, -1, 0);103104Callable body_monitor_callback;105Callable area_monitor_callback;106107float priority = 0.0f;108float gravity = 9.8f;109float point_gravity_distance = 0.0f;110float linear_damp = 0.1f;111float angular_damp = 0.1f;112113OverrideMode gravity_mode = PhysicsServer3D::AREA_SPACE_OVERRIDE_DISABLED;114OverrideMode linear_damp_mode = PhysicsServer3D::AREA_SPACE_OVERRIDE_DISABLED;115OverrideMode angular_damp_mode = PhysicsServer3D::AREA_SPACE_OVERRIDE_DISABLED;116117bool monitorable = false;118bool point_gravity = false;119120virtual JPH::BroadPhaseLayer _get_broad_phase_layer() const override;121virtual JPH::ObjectLayer _get_object_layer() const override;122123virtual JPH::EMotionType _get_motion_type() const override { return JPH::EMotionType::Kinematic; }124125bool _should_sleep() const { return !is_monitoring(); }126127virtual void _add_to_space() override;128129void _enqueue_call_queries();130void _dequeue_call_queries();131132void _add_shape_pair(Overlap &p_overlap, const JPH::BodyID &p_body_id, const JPH::SubShapeID &p_other_shape_id, const JPH::SubShapeID &p_self_shape_id);133bool _remove_shape_pair(Overlap &p_overlap, const JPH::SubShapeID &p_other_shape_id, const JPH::SubShapeID &p_self_shape_id);134135void _flush_events(OverlapsById &p_objects, const Callable &p_callback);136137void _report_event(const Callable &p_callback, PhysicsServer3D::AreaBodyStatus p_status, const RID &p_other_rid, ObjectID p_other_instance_id, int p_other_shape_index, int p_self_shape_index) const;138139void _notify_body_entered(const JPH::BodyID &p_body_id);140void _notify_body_exited(const JPH::BodyID &p_body_id);141142void _remove_all_overlaps();143144void _update_sleeping();145void _update_group_filter();146void _update_default_gravity();147148virtual void _space_changing() override;149virtual void _space_changed() override;150void _events_changed();151void _body_monitoring_changed();152void _area_monitoring_changed();153void _monitorable_changed();154void _gravity_changed();155156public:157JoltArea3D();158159bool is_default_area() const;160void set_default_area(bool p_value);161162void set_transform(Transform3D p_transform);163164Variant get_param(PhysicsServer3D::AreaParameter p_param) const;165void set_param(PhysicsServer3D::AreaParameter p_param, const Variant &p_value);166167bool has_body_monitor_callback() const { return body_monitor_callback.is_valid(); }168void set_body_monitor_callback(const Callable &p_callback);169170bool has_area_monitor_callback() const { return area_monitor_callback.is_valid(); }171void set_area_monitor_callback(const Callable &p_callback);172173bool is_monitoring_bodies() const { return has_body_monitor_callback(); }174bool is_monitoring_areas() const { return has_area_monitor_callback(); }175bool is_monitoring() const { return is_monitoring_bodies() || is_monitoring_areas(); }176177bool is_monitorable() const { return monitorable; }178void set_monitorable(bool p_monitorable);179180bool can_monitor(const JoltBody3D &p_other) const;181bool can_monitor(const JoltSoftBody3D &p_other) const;182bool can_monitor(const JoltArea3D &p_other) const;183184virtual bool can_interact_with(const JoltBody3D &p_other) const override;185virtual bool can_interact_with(const JoltSoftBody3D &p_other) const override;186virtual bool can_interact_with(const JoltArea3D &p_other) const override;187188virtual Vector3 get_velocity_at_position(const Vector3 &p_position) const override;189190virtual bool reports_contacts() const override { return false; }191192bool is_point_gravity() const { return point_gravity; }193void set_point_gravity(bool p_enabled);194195float get_priority() const { return priority; }196void set_priority(float p_priority) { priority = p_priority; }197198float get_gravity() const { return gravity; }199void set_gravity(float p_gravity);200201float get_point_gravity_distance() const { return point_gravity_distance; }202void set_point_gravity_distance(float p_distance);203204float get_linear_damp() const { return linear_damp; }205void set_area_linear_damp(float p_damp) { linear_damp = p_damp; }206207float get_angular_damp() const { return angular_damp; }208void set_area_angular_damp(float p_damp) { angular_damp = p_damp; }209210OverrideMode get_gravity_mode() const { return gravity_mode; }211void set_gravity_mode(OverrideMode p_mode);212213OverrideMode get_linear_damp_mode() const { return linear_damp_mode; }214void set_linear_damp_mode(OverrideMode p_mode) { linear_damp_mode = p_mode; }215216OverrideMode get_angular_damp_mode() const { return angular_damp_mode; }217void set_angular_damp_mode(OverrideMode p_mode) { angular_damp_mode = p_mode; }218219Vector3 get_gravity_vector() const { return gravity_vector; }220void set_gravity_vector(const Vector3 &p_vector);221222Vector3 compute_gravity(const Vector3 &p_position) const;223224void body_shape_entered(const JPH::BodyID &p_body_id, const JPH::SubShapeID &p_other_shape_id, const JPH::SubShapeID &p_self_shape_id);225bool body_shape_exited(const JPH::BodyID &p_body_id, const JPH::SubShapeID &p_other_shape_id, const JPH::SubShapeID &p_self_shape_id);226227void area_shape_entered(const JPH::BodyID &p_body_id, const JPH::SubShapeID &p_other_shape_id, const JPH::SubShapeID &p_self_shape_id);228bool area_shape_exited(const JPH::BodyID &p_body_id, const JPH::SubShapeID &p_other_shape_id, const JPH::SubShapeID &p_self_shape_id);229230bool shape_exited(const JPH::BodyID &p_body_id, const JPH::SubShapeID &p_other_shape_id, const JPH::SubShapeID &p_self_shape_id);231void body_exited(const JPH::BodyID &p_body_id, bool p_notify = true);232void area_exited(const JPH::BodyID &p_body_id);233234void call_queries();235236virtual bool has_custom_center_of_mass() const override { return false; }237virtual Vector3 get_center_of_mass_custom() const override { return Vector3(); }238};239240241