2019-01-01 12:46:36 +01:00
/**************************************************************************/
2020-03-27 08:44:44 +01:00
/* path_3d_editor_plugin.h */
2014-02-10 02:10:30 +01:00
/**************************************************************************/
/* This file is part of: */
/* GODOT ENGINE */
/* https://godotengine.org */
/**************************************************************************/
/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */
/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */
/* */
/* Permission is hereby granted, free of charge, to any person obtaining */
/* a copy of this software and associated documentation files (the */
/* "Software"), to deal in the Software without restriction, including */
/* without limitation the rights to use, copy, modify, merge, publish, */
/* distribute, sublicense, and/or sell copies of the Software, and to */
/* permit persons to whom the Software is furnished to do so, subject to */
/* the following conditions: */
/* */
/* The above copyright notice and this permission notice shall be */
/* included in all copies or substantial portions of the Software. */
/* */
/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */
/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */
/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */
/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */
/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */
/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */
/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
/**************************************************************************/
2018-01-05 00:50:27 +01:00
2022-07-23 23:41:51 +02:00
# ifndef PATH_3D_EDITOR_PLUGIN_H
# define PATH_3D_EDITOR_PLUGIN_H
2014-07-06 16:49:27 +02:00
2024-04-21 10:11:35 +02:00
# include "editor/plugins/editor_plugin.h"
2021-06-23 16:49:50 +02:00
# include "editor/plugins/node_3d_editor_gizmos.h"
# include "scene/3d/camera_3d.h"
2020-03-26 22:49:16 +01:00
# include "scene/3d/path_3d.h"
2022-02-12 02:46:22 +01:00
2023-09-11 23:50:10 +02:00
class HBoxContainer ;
2022-11-11 20:12:48 +01:00
class MenuButton ;
2024-03-27 05:40:30 +01:00
class ConfirmationDialog ;
2022-11-11 20:12:48 +01:00
2020-04-06 12:40:52 +02:00
class Path3DGizmo : public EditorNode3DGizmo {
GDCLASS ( Path3DGizmo , EditorNode3DGizmo ) ;
2014-07-06 16:49:27 +02:00
2022-11-17 16:42:00 +01:00
// Map handle id to control point id and handle type.
enum HandleType {
HANDLE_TYPE_IN ,
HANDLE_TYPE_OUT ,
HANDLE_TYPE_TILT ,
} ;
struct HandleInfo {
int point_idx ; // Index of control point.
HandleType type ; // Type of this handle.
} ;
2022-04-04 15:06:57 +02:00
Path3D * path = nullptr ;
2014-07-06 16:49:27 +02:00
mutable Vector3 original ;
2018-05-01 12:13:29 +02:00
mutable float orig_in_length ;
mutable float orig_out_length ;
2023-08-20 01:41:53 +02:00
mutable float disk_size = 0.8 ;
2014-07-06 16:49:27 +02:00
2022-11-17 16:42:00 +01:00
// Cache information of secondary handles.
Vector < HandleInfo > _secondary_handles_info ;
2024-02-01 20:18:42 +01:00
void _update_transform_gizmo ( ) ;
2014-07-06 16:49:27 +02:00
public :
2022-01-11 12:33:37 +01:00
virtual String get_handle_name ( int p_id , bool p_secondary ) const override ;
virtual Variant get_handle_value ( int p_id , bool p_secondary ) const override ;
virtual void set_handle ( int p_id , bool p_secondary , Camera3D * p_camera , const Point2 & p_point ) override ;
virtual void commit_handle ( int p_id , bool p_secondary , const Variant & p_restore , bool p_cancel = false ) override ;
2014-07-06 16:49:27 +02:00
2020-07-10 12:34:39 +02:00
virtual void redraw ( ) override ;
2023-08-20 01:41:53 +02:00
Path3DGizmo ( Path3D * p_path = nullptr , float p_disk_size = 0.8 ) ;
2014-07-06 16:49:27 +02:00
} ;
2020-04-06 12:40:52 +02:00
class Path3DGizmoPlugin : public EditorNode3DGizmoPlugin {
GDCLASS ( Path3DGizmoPlugin , EditorNode3DGizmoPlugin ) ;
2018-07-25 00:08:49 +02:00
2023-08-20 01:41:53 +02:00
float disk_size = 0.8 ;
2024-02-01 20:18:42 +01:00
// Locking basis is meant to ensure a predictable behavior during translation of the curve points in "local space transform mode".
// Without the locking, the gizmo/point, in "local space transform mode", wouldn't follow a straight path and would curve and twitch in an unpredictable way.
HashMap < int , Basis > transformation_locked_basis ;
2018-07-25 00:08:49 +02:00
protected :
2020-07-10 12:34:39 +02:00
Ref < EditorNode3DGizmo > create_gizmo ( Node3D * p_spatial ) override ;
2018-07-25 00:08:49 +02:00
public :
2024-02-01 20:18:42 +01:00
virtual bool has_gizmo ( Node3D * p_spatial ) override ;
2020-07-23 00:39:21 +02:00
String get_gizmo_name ( ) const override ;
2024-02-01 20:18:42 +01:00
virtual void redraw ( EditorNode3DGizmo * p_gizmo ) override ;
virtual int subgizmos_intersect_ray ( const EditorNode3DGizmo * p_gizmo , Camera3D * p_camera , const Vector2 & p_point ) const override ;
virtual Vector < int > subgizmos_intersect_frustum ( const EditorNode3DGizmo * p_gizmo , const Camera3D * p_camera , const Vector < Plane > & p_frustum ) const override ;
virtual Transform3D get_subgizmo_transform ( const EditorNode3DGizmo * p_gizmo , int p_id ) const override ;
virtual void set_subgizmo_transform ( const EditorNode3DGizmo * p_gizmo , int p_id , Transform3D p_transform ) override ;
virtual void commit_subgizmos ( const EditorNode3DGizmo * p_gizmo , const Vector < int > & p_ids , const Vector < Transform3D > & p_restore , bool p_cancel = false ) override ;
2020-07-10 12:34:39 +02:00
int get_priority ( ) const override ;
2023-08-20 01:41:53 +02:00
Path3DGizmoPlugin ( float p_disk_size ) ;
2018-07-25 00:08:49 +02:00
} ;
2020-03-27 08:44:44 +01:00
class Path3DEditorPlugin : public EditorPlugin {
GDCLASS ( Path3DEditorPlugin , EditorPlugin ) ;
2014-07-06 16:49:27 +02:00
2024-03-24 13:43:17 +01:00
friend class Path3DGizmo ;
friend class Path3DGizmoPlugin ;
Ref < Path3DGizmoPlugin > path_3d_gizmo_plugin ;
2023-09-11 23:50:10 +02:00
HBoxContainer * topmenu_bar = nullptr ;
2024-09-05 20:07:16 +02:00
HBoxContainer * toolbar = nullptr ;
2022-04-04 15:06:57 +02:00
Button * curve_create = nullptr ;
Button * curve_edit = nullptr ;
2023-06-05 04:54:48 +02:00
Button * curve_edit_curve = nullptr ;
2024-03-24 13:43:17 +01:00
Button * curve_edit_tilt = nullptr ;
2022-04-04 15:06:57 +02:00
Button * curve_del = nullptr ;
Button * curve_close = nullptr ;
2024-03-27 05:40:30 +01:00
Button * curve_clear_points = nullptr ;
2022-04-04 15:06:57 +02:00
MenuButton * handle_menu = nullptr ;
2014-07-06 16:49:27 +02:00
2024-09-05 20:07:16 +02:00
Button * create_curve_button = nullptr ;
2024-03-27 05:40:30 +01:00
ConfirmationDialog * clear_points_dialog = nullptr ;
2023-08-20 01:41:53 +02:00
float disk_size = 0.8 ;
2023-06-05 04:54:48 +02:00
enum Mode {
MODE_CREATE ,
MODE_EDIT ,
MODE_EDIT_CURVE ,
2024-03-24 13:43:17 +01:00
MODE_EDIT_TILT ,
2023-06-05 04:54:48 +02:00
MODE_DELETE ,
ACTION_CLOSE
} ;
2022-04-04 15:06:57 +02:00
Path3D * path = nullptr ;
2014-07-06 16:49:27 +02:00
2022-01-28 18:21:50 +01:00
void _update_theme ( ) ;
2024-09-05 20:07:16 +02:00
void _update_toolbar ( ) ;
2022-01-28 18:21:50 +01:00
2023-06-05 04:54:48 +02:00
void _mode_changed ( int p_mode ) ;
2017-05-25 00:11:20 +02:00
void _close_curve ( ) ;
2018-05-01 12:13:29 +02:00
void _handle_option_pressed ( int p_option ) ;
2022-05-02 16:28:25 +02:00
bool handle_clicked = false ;
2024-09-05 20:07:16 +02:00
bool mirror_handle_angle = true ;
bool mirror_handle_length = true ;
2018-05-01 12:13:29 +02:00
2024-09-05 20:07:16 +02:00
void _create_curve ( ) ;
2024-03-27 05:40:30 +01:00
void _confirm_clear_points ( ) ;
void _clear_points ( ) ;
void _clear_curve_points ( ) ;
void _restore_curve_points ( const PackedVector3Array & p_points ) ;
2018-05-01 12:13:29 +02:00
enum HandleOption {
HANDLE_OPTION_ANGLE ,
HANDLE_OPTION_LENGTH
} ;
2017-05-25 00:11:20 +02:00
2014-07-06 16:49:27 +02:00
protected :
void _notification ( int p_what ) ;
static void _bind_methods ( ) ;
public :
2020-03-26 22:49:16 +01:00
Path3D * get_edited_path ( ) { return path ; }
2014-07-06 16:49:27 +02:00
2020-03-27 08:44:44 +01:00
static Path3DEditorPlugin * singleton ;
2022-09-08 18:38:33 +02:00
virtual EditorPlugin : : AfterGUIInput forward_3d_gui_input ( Camera3D * p_camera , const Ref < InputEvent > & p_event ) override ;
2014-07-06 16:49:27 +02:00
2020-07-10 12:34:39 +02:00
virtual String get_name ( ) const override { return " Path3D " ; }
bool has_main_screen ( ) const override { return false ; }
virtual void edit ( Object * p_object ) override ;
virtual bool handles ( Object * p_object ) const override ;
virtual void make_visible ( bool p_visible ) override ;
2014-07-06 16:49:27 +02:00
2018-05-01 12:13:29 +02:00
bool mirror_angle_enabled ( ) { return mirror_handle_angle ; }
bool mirror_length_enabled ( ) { return mirror_handle_length ; }
bool is_handle_clicked ( ) { return handle_clicked ; }
void set_handle_clicked ( bool clicked ) { handle_clicked = clicked ; }
2022-01-27 10:36:51 +01:00
Path3DEditorPlugin ( ) ;
2020-03-27 08:44:44 +01:00
~ Path3DEditorPlugin ( ) ;
2014-07-06 16:49:27 +02:00
} ;
2022-07-23 23:41:51 +02:00
# endif // PATH_3D_EDITOR_PLUGIN_H